[wip] adding csrf form management, to be added everywhere

This commit is contained in:
Benjamin Sonntag 2016-05-19 17:04:49 +02:00
parent 7b1e5bba94
commit d9bdfaf1ac
2 changed files with 60 additions and 0 deletions

View File

@ -1073,3 +1073,53 @@ function panel_unlock() {
function panel_islocked() { function panel_islocked() {
return file_exists(ALTERNC_LOCK_PANEL); return file_exists(ALTERNC_LOCK_PANEL);
} }
/** Give a new CSRF uniq token for a form
* the session must be up since the CSRF is linked
* to the session cookie. We also need the $db pdo object
* @return the csrf cookie to add into a csrf hidden field in your form
*/
function csrf_get() {
global $db;
if (!isset($_SESSION["csrf"])) {
$_SESSION["csrf"]=md5(rand().rand().rand());
}
$token=md5(rand().rand().rand());
$db->query("INSERT INTO csrf SET cookie=?, token=?, created=NOW(), used=0;",array($_SESSION["csrf"],$token));
return $token;
}
/** Check a CSRF token against the current session
* a token can be only checked once, it's disabled then
* @param $token string the token to check in the DB + session
* @return $result integer 0 for invalid token, 1 for good token, -1 for expired token (already used)
* if a token is invalid or expired, an $err is raised, that can be displayed
*/
function csrf_check($token) {
global $db,$err;
if (!isset($_SESSION["csrf"])) {
$err->raise("functions", _("The posted form token is incorrect. Maybe you need to allow cookies"));
return 0; // no csrf cookie :/
}
if (!preg_match('#^[0-9a-f]{32}$#',$token)) {
$err->raise("functions", _("The posted form token is invalid"));
return 0; // invalid csrf token
}
if (!preg_match('#^[0-9a-f]{32}$#',$_SESSION["csrf"])) {
unset($_SESSION["csrf"]);
$err->raise("functions", _("Your cookie is invalid"));
return 0; // invalid csrf cookie
}
$db->query("SELECT used FROM csrf WHERE cookie=? AND token=?;",array($_SESSION["csrf"],$token));
if (!$db->next_record()) {
$err->raise("functions", _("Your token is invalid"));
return 0; // invalid csrf cookie
}
if ($db->f("used")) {
$err->raise("functions", _("Your token is expired. Please refill the form."));
return -1; // expired
}
$db->query("UPDATE csrf SET used=1 WHERE cookie=? AND token=?;",array($_SESSION["csrf"],$token));
return 1;
}

View File

@ -0,0 +1,10 @@
CREATE TABLE IF NOT EXISTS `csrf` (
`cookie` char(32) CHARACTER SET ascii COLLATE ascii_bin NOT NULL,
`token` char(32) CHARACTER SET ascii COLLATE ascii_bin NOT NULL,
`created` datetime NOT NULL,
`used` tinyint(3) unsigned NOT NULL DEFAULT '0'
) ENGINE=InnoDB DEFAULT CHARSET=latin1 COMMENT='csrf tokens for AlternC forms';
ALTER TABLE `csrf` ADD PRIMARY KEY (`session`,`token`), ADD KEY `created` (`created`);