added CSRF protection
This commit is contained in:
parent
1f0d4b0cda
commit
c34b040766
|
@ -1,4 +1,5 @@
|
||||||
June 215
|
June 215
|
||||||
|
- Security: added CSRF protection
|
||||||
- Zarafa users: allow to change display format of "Send As"
|
- Zarafa users: allow to change display format of "Send As"
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -591,12 +591,16 @@ class htmlInputField extends htmlElement {
|
||||||
';
|
';
|
||||||
}
|
}
|
||||||
if ($this->checkPasswordStrength) {
|
if ($this->checkPasswordStrength) {
|
||||||
$ajaxPath = "../templates/misc/ajax.php";
|
$tokenSuffix = '?' . getSecurityTokenName() . '=' . getSecurityTokenValue();
|
||||||
|
if (isSelfService()) {
|
||||||
|
$tokenSuffix .= '&selfservice=1';
|
||||||
|
}
|
||||||
|
$ajaxPath = "../templates/misc/ajax.php" . $tokenSuffix;
|
||||||
if (is_file("../../templates/misc/ajax.php")) {
|
if (is_file("../../templates/misc/ajax.php")) {
|
||||||
$ajaxPath = "../../templates/misc/ajax.php";
|
$ajaxPath = "../../templates/misc/ajax.php" . $tokenSuffix;
|
||||||
}
|
}
|
||||||
elseif (is_file("../../../templates/misc/ajax.php")) {
|
elseif (is_file("../../../templates/misc/ajax.php")) {
|
||||||
$ajaxPath = "../../../templates/misc/ajax.php";
|
$ajaxPath = "../../../templates/misc/ajax.php" . $tokenSuffix;
|
||||||
}
|
}
|
||||||
echo '<script type="text/javascript">
|
echo '<script type="text/javascript">
|
||||||
checkPasswordStrength("' . $this->fieldName . '", "' . $ajaxPath . '");
|
checkPasswordStrength("' . $this->fieldName . '", "' . $ajaxPath . '");
|
||||||
|
|
|
@ -1238,7 +1238,8 @@ class accountContainer {
|
||||||
$passwordButton = new htmlButton('accountContainerPassword', _('Set password'));
|
$passwordButton = new htmlButton('accountContainerPassword', _('Set password'));
|
||||||
$passwordButton->setIconClass('passwordButton');
|
$passwordButton->setIconClass('passwordButton');
|
||||||
$passwordButton->setOnClick('passwordShowChangeDialog(\'' . _('Set password') . '\', \'' . _('Ok') . '\', \''
|
$passwordButton->setOnClick('passwordShowChangeDialog(\'' . _('Set password') . '\', \'' . _('Ok') . '\', \''
|
||||||
. _('Cancel') . '\', \'' . _('Set random password') . '\', \'../misc/ajax.php?function=passwordChange\');');
|
. _('Cancel') . '\', \'' . _('Set random password') . '\', \'../misc/ajax.php?function=passwordChange&'
|
||||||
|
. getSecurityTokenName() . '=' . getSecurityTokenValue() . '\');');
|
||||||
$leftButtonGroup->addElement($passwordButton);
|
$leftButtonGroup->addElement($passwordButton);
|
||||||
}
|
}
|
||||||
$table->addElement($leftButtonGroup);
|
$table->addElement($leftButtonGroup);
|
||||||
|
|
|
@ -2972,7 +2972,9 @@ class inetOrgPerson extends baseModule implements passwordService {
|
||||||
"action": "delete",
|
"action": "delete",
|
||||||
"id": id
|
"id": id
|
||||||
};
|
};
|
||||||
jQuery.post(\'../misc/ajax.php?selfservice=1&module=inetOrgPerson&scope=user\', {jsonInput: actionJSON}, function(data) {inetOrgPersonDeleteCertificateHandleReply(data);}, \'json\');
|
jQuery.post(\'../misc/ajax.php?selfservice=1&module=inetOrgPerson&scope=user'
|
||||||
|
. '&' . getSecurityTokenName() . '=' . getSecurityTokenValue()
|
||||||
|
. '\', {jsonInput: actionJSON}, function(data) {inetOrgPersonDeleteCertificateHandleReply(data);}, \'json\');
|
||||||
}
|
}
|
||||||
|
|
||||||
function inetOrgPersonDeleteCertificateHandleReply(data) {
|
function inetOrgPersonDeleteCertificateHandleReply(data) {
|
||||||
|
@ -2990,7 +2992,8 @@ class inetOrgPerson extends baseModule implements passwordService {
|
||||||
element: document.getElementById(elementID),
|
element: document.getElementById(elementID),
|
||||||
listElement: uploadStatus,
|
listElement: uploadStatus,
|
||||||
request: {
|
request: {
|
||||||
endpoint: \'../misc/ajax.php?selfservice=1&module=inetOrgPerson&scope=user\',
|
endpoint: \'../misc/ajax.php?selfservice=1&module=inetOrgPerson&scope=user'
|
||||||
|
. '&' . getSecurityTokenName() . '=' . getSecurityTokenValue() . '\',
|
||||||
forceMultipart: true,
|
forceMultipart: true,
|
||||||
params: {
|
params: {
|
||||||
action: \'ajaxCertUpload\'
|
action: \'ajaxCertUpload\'
|
||||||
|
|
|
@ -305,7 +305,9 @@ class ldapPublicKey extends baseModule {
|
||||||
for (c = 0; c < count; c++) {
|
for (c = 0; c < count; c++) {
|
||||||
actionJSON["sshPublicKey_" + c] = jQuery(\'#sshPublicKey_\' + c).val();
|
actionJSON["sshPublicKey_" + c] = jQuery(\'#sshPublicKey_\' + c).val();
|
||||||
}
|
}
|
||||||
jQuery.post(\'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user\', {jsonInput: actionJSON}, function(data) {ldapPublicKeyDeleteKeyHandleReply(data);}, \'json\');
|
jQuery.post(\'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user'
|
||||||
|
. '&' . getSecurityTokenName() . '=' . getSecurityTokenValue()
|
||||||
|
. '\', {jsonInput: actionJSON}, function(data) {ldapPublicKeyDeleteKeyHandleReply(data);}, \'json\');
|
||||||
}
|
}
|
||||||
|
|
||||||
function ldapPublicKeyDeleteKeyHandleReply(data) {
|
function ldapPublicKeyDeleteKeyHandleReply(data) {
|
||||||
|
@ -324,7 +326,9 @@ class ldapPublicKey extends baseModule {
|
||||||
for (c = 0; c < count; c++) {
|
for (c = 0; c < count; c++) {
|
||||||
actionJSON["sshPublicKey_" + c] = jQuery(\'#sshPublicKey_\' + c).val();
|
actionJSON["sshPublicKey_" + c] = jQuery(\'#sshPublicKey_\' + c).val();
|
||||||
}
|
}
|
||||||
jQuery.post(\'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user\', {jsonInput: actionJSON}, function(data) {ldapPublicKeyAddKeyHandleReply(data);}, \'json\');
|
jQuery.post(\'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user'
|
||||||
|
. '&' . getSecurityTokenName() . '=' . getSecurityTokenValue()
|
||||||
|
. '\', {jsonInput: actionJSON}, function(data) {ldapPublicKeyAddKeyHandleReply(data);}, \'json\');
|
||||||
}
|
}
|
||||||
|
|
||||||
function ldapPublicKeyAddKeyHandleReply(data) {
|
function ldapPublicKeyAddKeyHandleReply(data) {
|
||||||
|
@ -348,7 +352,8 @@ class ldapPublicKey extends baseModule {
|
||||||
element: document.getElementById(elementID),
|
element: document.getElementById(elementID),
|
||||||
listElement: uploadStatus,
|
listElement: uploadStatus,
|
||||||
request: {
|
request: {
|
||||||
endpoint: \'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user\',
|
endpoint: \'../misc/ajax.php?selfservice=1&module=ldapPublicKey&scope=user'
|
||||||
|
. '&' . getSecurityTokenName() . '=' . getSecurityTokenValue() . '\',
|
||||||
forceMultipart: true,
|
forceMultipart: true,
|
||||||
paramsInBody: true,
|
paramsInBody: true,
|
||||||
params: parameters
|
params: parameters
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
$Id$
|
$Id$
|
||||||
|
|
||||||
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
||||||
Copyright (C) 2006 - 2014 Roland Gruber
|
Copyright (C) 2006 - 2015 Roland Gruber
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
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
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -497,4 +497,55 @@ function getClientIPForLogging() {
|
||||||
return $ip;
|
return $ip;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds a security token to the session to prevent CSRF attacks.
|
||||||
|
*/
|
||||||
|
function addSecurityTokenToSession() {
|
||||||
|
$_SESSION[getSecurityTokenName()] = getRandomNumber();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the security token from SESSION matches POST data.
|
||||||
|
*
|
||||||
|
* @param $post use POST, set to false for GET (default: true)
|
||||||
|
*/
|
||||||
|
function validateSecurityToken($post = true) {
|
||||||
|
$vars = $post ? $_POST : $_GET;
|
||||||
|
if (empty($vars)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (empty($vars[getSecurityTokenName()]) || ($vars[getSecurityTokenName()] != $_SESSION[getSecurityTokenName()])) {
|
||||||
|
logNewMessage(LOG_ERR, 'Security token does not match POST data.');
|
||||||
|
die();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds a hidden input field to the given meta HTML table.
|
||||||
|
* Should be used to add token at the end of table.
|
||||||
|
*
|
||||||
|
* @param htmlTable $container table
|
||||||
|
*/
|
||||||
|
function addSecurityTokenToMetaHTML(&$container) {
|
||||||
|
$container->addElement(new htmlHiddenInput(getSecurityTokenName(), $_SESSION[getSecurityTokenName()]), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the name of the security token parameter.
|
||||||
|
*
|
||||||
|
* @return String name
|
||||||
|
*/
|
||||||
|
function getSecurityTokenName() {
|
||||||
|
return 'sec_token';
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the value of the security token parameter.
|
||||||
|
*
|
||||||
|
* @return String value
|
||||||
|
*/
|
||||||
|
function getSecurityTokenValue() {
|
||||||
|
return $_SESSION[getSecurityTokenName()];
|
||||||
|
}
|
||||||
|
|
||||||
?>
|
?>
|
|
@ -3,7 +3,7 @@
|
||||||
$Id$
|
$Id$
|
||||||
|
|
||||||
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
||||||
Copyright (C) 2006 - 2014 Roland Gruber
|
Copyright (C) 2006 - 2015 Roland Gruber
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
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
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -285,6 +285,15 @@ function checkSelfServiceSettings($scope, &$options, &$profile) {
|
||||||
return $return;
|
return $return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns if script runs inside self service.
|
||||||
|
*
|
||||||
|
* @return boolean is self service
|
||||||
|
*/
|
||||||
|
function isSelfService() {
|
||||||
|
return session_name() == 'SELFSERVICE';
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Includes all settings of a self service profile.
|
* Includes all settings of a self service profile.
|
||||||
|
|
|
@ -560,7 +560,7 @@ function checkPasswordStrength(fieldID, ajaxURL) {
|
||||||
"password": value
|
"password": value
|
||||||
};
|
};
|
||||||
// make AJAX call
|
// make AJAX call
|
||||||
jQuery.post(ajaxURL + "?function=passwordStrengthCheck", {jsonInput: pwdJSON}, function(data) {checkPasswordStrengthHandleReply(data, fieldID);}, 'json');
|
jQuery.post(ajaxURL + "&function=passwordStrengthCheck", {jsonInput: pwdJSON}, function(data) {checkPasswordStrengthHandleReply(data, fieldID);}, 'json');
|
||||||
};
|
};
|
||||||
jQuery(field).keyup(check);
|
jQuery(field).keyup(check);
|
||||||
}
|
}
|
||||||
|
|
|
@ -615,6 +615,7 @@ if(!empty($_POST['checklogin'])) {
|
||||||
$_SESSION['sec_session_id'] = session_id();
|
$_SESSION['sec_session_id'] = session_id();
|
||||||
$_SESSION['sec_client_ip'] = $_SERVER['REMOTE_ADDR'];
|
$_SESSION['sec_client_ip'] = $_SERVER['REMOTE_ADDR'];
|
||||||
$_SESSION['sec_sessionTime'] = time();
|
$_SESSION['sec_sessionTime'] = time();
|
||||||
|
addSecurityTokenToSession();
|
||||||
// logging
|
// logging
|
||||||
logNewMessage(LOG_NOTICE, 'User ' . $username . ' (' . $clientSource . ') successfully logged in.');
|
logNewMessage(LOG_NOTICE, 'User ' . $username . ' (' . $clientSource . ') successfully logged in.');
|
||||||
// Load main frame
|
// Load main frame
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
$Id$
|
$Id$
|
||||||
|
|
||||||
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
|
||||||
Copyright (C) 2011 - 2014 Roland Gruber
|
Copyright (C) 2011 - 2015 Roland Gruber
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
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
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -58,6 +58,9 @@ class lamAjax {
|
||||||
* Manages an AJAX request.
|
* Manages an AJAX request.
|
||||||
*/
|
*/
|
||||||
public static function handleRequest() {
|
public static function handleRequest() {
|
||||||
|
// check token
|
||||||
|
validateSecurityToken(false);
|
||||||
|
|
||||||
if (isset($_GET['module']) && isset($_GET['scope']) && in_array($_GET['module'], getAvailableModules($_GET['scope']))) {
|
if (isset($_GET['module']) && isset($_GET['scope']) && in_array($_GET['module'], getAvailableModules($_GET['scope']))) {
|
||||||
if (isset($_GET['useContainer']) && ($_GET['useContainer'] == '1')) {
|
if (isset($_GET['useContainer']) && ($_GET['useContainer'] == '1')) {
|
||||||
if (!isset($_SESSION['account'])) die();
|
if (!isset($_SESSION['account'])) die();
|
||||||
|
@ -76,8 +79,8 @@ class lamAjax {
|
||||||
if (!isset($_POST['jsonInput'])) {
|
if (!isset($_POST['jsonInput'])) {
|
||||||
die();
|
die();
|
||||||
}
|
}
|
||||||
|
|
||||||
$jsonInput = $_POST['jsonInput'];
|
$jsonInput = $_POST['jsonInput'];
|
||||||
|
|
||||||
if ($function == 'passwordChange') {
|
if ($function == 'passwordChange') {
|
||||||
lamAjax::managePasswordChange($jsonInput);
|
lamAjax::managePasswordChange($jsonInput);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue