mirror of
https://github.com/billz/raspap-webgui.git
synced 2025-07-11 13:57:40 +02:00
Merge pull request #1811 from RaspAP/feat/csrf-tokenizer
Feature: CSRF tokenizer class
This commit is contained in:
commit
3bf682d752
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (isset($_POST['blocklist_id'])) {
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$interface = filter_input(INPUT_GET, 'inet', FILTER_SANITIZE_SPECIAL_CHARS);
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (filter_input(INPUT_GET, 'tu') == 'h') {
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
|
@ -1,37 +1,29 @@
|
||||
<?php
|
||||
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
if (isset($_POST['csrf_token'])) {
|
||||
if (csrfValidateRequest() && !CSRFValidate()) {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
$return = 0;
|
||||
$path = "../../config";
|
||||
$configs = array(
|
||||
array("src" => $path .'/hostapd.conf', "tmp" => "/tmp/hostapddata", "dest" => RASPI_HOSTAPD_CONFIG),
|
||||
array("src" => $path .'/dhcpcd.conf', "tmp" => "/tmp/dhcpddata", "dest" => RASPI_DHCPCD_CONFIG),
|
||||
array("src" => $path .'/090_wlan0.conf', "tmp" => "/tmp/dnsmasqdata", "dest" => RASPI_DNSMASQ_PREFIX.'wlan0.conf'),
|
||||
array("src" => $path .'/090_raspap.conf', "tmp" => "/tmp/dnsmasqdata", "dest" => RASPI_DNSMASQ_PREFIX.'raspap.conf'),
|
||||
);
|
||||
$return = 0;
|
||||
$path = "../../config";
|
||||
$configs = array(
|
||||
array("src" => $path .'/hostapd.conf', "tmp" => "/tmp/hostapddata", "dest" => RASPI_HOSTAPD_CONFIG),
|
||||
array("src" => $path .'/dhcpcd.conf', "tmp" => "/tmp/dhcpddata", "dest" => RASPI_DHCPCD_CONFIG),
|
||||
array("src" => $path .'/090_wlan0.conf', "tmp" => "/tmp/dnsmasqdata", "dest" => RASPI_DNSMASQ_PREFIX.'wlan0.conf'),
|
||||
array("src" => $path .'/090_raspap.conf', "tmp" => "/tmp/dnsmasqdata", "dest" => RASPI_DNSMASQ_PREFIX.'raspap.conf'),
|
||||
);
|
||||
|
||||
foreach ($configs as $config) {
|
||||
try {
|
||||
$tmp = file_get_contents($config["src"]);
|
||||
file_put_contents($config["tmp"], $tmp);
|
||||
system("sudo cp ".$config["tmp"]. " ".$config["dest"]);
|
||||
} catch (Exception $e) {
|
||||
$return = $e->getCode();
|
||||
}
|
||||
foreach ($configs as $config) {
|
||||
try {
|
||||
$tmp = file_get_contents($config["src"]);
|
||||
file_put_contents($config["tmp"], $tmp);
|
||||
system("sudo cp ".$config["tmp"]. " ".$config["dest"]);
|
||||
} catch (Exception $e) {
|
||||
$return = $e->getCode();
|
||||
}
|
||||
$jsonData = ['return'=>$return];
|
||||
echo json_encode($jsonData);
|
||||
|
||||
} else {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
$jsonData = ['return'=>$return];
|
||||
echo json_encode($jsonData);
|
||||
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
exec("ls /sys/class/net | grep -v lo", $interfaces);
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
exec('cat '. RASPI_HOSTAPD_CONFIG, $hostapdconfig);
|
||||
@ -18,3 +17,4 @@ foreach ($hostapdconfig as $hostapdconfigline) {
|
||||
};
|
||||
$channel = intval($arrConfig['channel']);
|
||||
echo json_encode($channel);
|
||||
|
||||
|
@ -1,10 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../src/RaspAP/Parsers/IwParser.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (isset($_POST['interface'])) {
|
||||
|
@ -1,10 +1,9 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/functions.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (isset($_POST['interface'])) {
|
||||
|
@ -1,10 +1,10 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
$interface = $_POST['iface'];
|
||||
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/locale.php';
|
||||
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
// fetch wg client.conf
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$entity = escapeshellcmd($_POST['entity']);
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/defaults.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
|
@ -1,11 +1,9 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../src/RaspAP/Plugins/PluginInstaller.php';
|
||||
|
||||
$pluginInstaller = \RaspAP\Plugins\PluginInstaller::getInstance();
|
||||
$plugin_uri = $_POST['plugin_uri'] ?? null;
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$lastActivity = $_SESSION['lastActivity'] ?? time();
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$action = escapeshellcmd($_POST['a']);
|
||||
|
@ -1,27 +1,22 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
require_once '../../includes/defaults.php';
|
||||
require_once '../../includes/functions.php';
|
||||
|
||||
if (isset($_POST['csrf_token'])) {
|
||||
if (csrfValidateRequest() && !CSRFValidate()) {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
$uri = RASPI_API_ENDPOINT;
|
||||
preg_match('/(\d+(\.\d+)+)/', RASPI_VERSION, $matches);
|
||||
$thisRelease = $matches[0];
|
||||
$uri = RASPI_API_ENDPOINT;
|
||||
preg_match('/(\d+(\.\d+)+)/', RASPI_VERSION, $matches);
|
||||
$thisRelease = $matches[0];
|
||||
|
||||
$json = shell_exec("wget --timeout=5 --tries=1 $uri -qO -");
|
||||
$data = json_decode($json, true);
|
||||
$tagName = $data['tag_name'];
|
||||
$updateAvailable = checkReleaseVersion($thisRelease, $tagName);
|
||||
$json = shell_exec("wget --timeout=5 --tries=1 $uri -qO -");
|
||||
$data = json_decode($json, true);
|
||||
$tagName = $data['tag_name'];
|
||||
$updateAvailable = checkReleaseVersion($thisRelease, $tagName);
|
||||
|
||||
$response['tag'] = $tagName;
|
||||
$response['update'] = $updateAvailable;
|
||||
echo json_encode($response);
|
||||
$response['tag'] = $tagName;
|
||||
$response['update'] = $updateAvailable;
|
||||
echo json_encode($response);
|
||||
|
||||
} else {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
|
@ -1,25 +1,18 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (isset($_POST['csrf_token'])) {
|
||||
if (csrfValidateRequest() && !CSRFValidate()) {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
$root = getenv("DOCUMENT_ROOT");
|
||||
exec('sudo '.RASPI_CONFIG.'/system/debuglog.sh -i '.$root, $return);
|
||||
$root = getenv("DOCUMENT_ROOT");
|
||||
exec('sudo '.RASPI_CONFIG.'/system/debuglog.sh -i '.$root, $return);
|
||||
|
||||
$logOutput = implode(PHP_EOL, $return);
|
||||
$tempDir = sys_get_temp_dir();
|
||||
$filePath = $tempDir . DIRECTORY_SEPARATOR . RASPI_DEBUG_LOG;
|
||||
$handle = fopen($filePath, "w");
|
||||
fwrite($handle, $logOutput);
|
||||
fclose($handle);
|
||||
echo json_encode($filePath);
|
||||
|
||||
$logOutput = implode(PHP_EOL, $return);
|
||||
$tempDir = sys_get_temp_dir();
|
||||
$filePath = $tempDir . DIRECTORY_SEPARATOR . RASPI_DEBUG_LOG;
|
||||
$handle = fopen($filePath, "w");
|
||||
fwrite($handle, $logOutput);
|
||||
fclose($handle);
|
||||
echo json_encode($filePath);
|
||||
} else {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$tempDir = sys_get_temp_dir();
|
||||
|
@ -1,9 +1,8 @@
|
||||
<?php
|
||||
|
||||
require '../../includes/csrf.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/CSRF.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
if (isset($_POST['csrf_token'])) {
|
||||
|
@ -1,8 +1,8 @@
|
||||
<?php
|
||||
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../includes/autoload.php';
|
||||
require_once '../../includes/session.php';
|
||||
require_once '../../src/RaspAP/Auth/HTTPAuth.php';
|
||||
require_once '../../includes/config.php';
|
||||
require_once '../../includes/authenticate.php';
|
||||
|
||||
$logFile = '/tmp/raspap_install.log';
|
||||
|
66
includes/CSRF.php
Normal file
66
includes/CSRF.php
Normal file
@ -0,0 +1,66 @@
|
||||
<?php
|
||||
|
||||
namespace RaspAP\Tokens;
|
||||
|
||||
class CSRF
|
||||
{
|
||||
protected static ?CSRFTokenizer $instance = null;
|
||||
|
||||
/*
|
||||
* Get the CSRFTokenizer instance (singleton)
|
||||
*
|
||||
* @return CSRFTokenizer
|
||||
*/
|
||||
public static function instance(): CSRFTokenizer
|
||||
{
|
||||
if (self::$instance === null) {
|
||||
self::$instance = new CSRFTokenizer();
|
||||
}
|
||||
return self::$instance;
|
||||
}
|
||||
|
||||
public static function token(): string
|
||||
{
|
||||
return self::instance()->getToken();
|
||||
}
|
||||
|
||||
public static function verify(): bool
|
||||
{
|
||||
$token = $_POST['csrf_token'];
|
||||
return self::instance()->csrfValidateRequest() &&
|
||||
self::instance()->CSRFValidate($_POST['csrf_token'] ?? '');
|
||||
}
|
||||
|
||||
public static function metaTag(): string
|
||||
{
|
||||
return self::instance()->CSRFMetaTag();
|
||||
}
|
||||
|
||||
public static function hiddenField(): string
|
||||
{
|
||||
return self::instance()->CSRFTokenFieldTag();
|
||||
}
|
||||
|
||||
public static function handleInvalidToken(): void
|
||||
{
|
||||
self::instance()->handleInvalidCSRFToken();
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates a CSRF Request
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public static function validateRequest(): bool
|
||||
{
|
||||
return self::instance()->csrfValidateRequest();
|
||||
}
|
||||
}
|
||||
|
||||
if (\RaspAP\Tokens\CSRF::validateRequest()) {
|
||||
if (!\RaspAP\Tokens\CSRF::verify()) {
|
||||
error_log("CSRF verification failed. Token: " . ($_POST['csrf_token'] ?? 'not provided'));
|
||||
\RaspAP\Tokens\CSRF::handleInvalidToken();
|
||||
}
|
||||
}
|
||||
|
@ -9,31 +9,13 @@
|
||||
*/
|
||||
spl_autoload_register(function ($class) {
|
||||
|
||||
// project-specific namespace prefix
|
||||
$prefix = '';
|
||||
// base directory where all class files are stored
|
||||
$base_dir = __DIR__ . '/../src/';
|
||||
|
||||
// base directory for the namespace prefix
|
||||
$base_dir = 'src/';
|
||||
// convert the fully qualified class name into a file path
|
||||
$file = $base_dir . str_replace('\\', '/', $class) . '.php';
|
||||
|
||||
// normalize the base directory with a trailing separator
|
||||
$base_dir = rtrim($base_dir, DIRECTORY_SEPARATOR) . '/';
|
||||
|
||||
// does the class use the namespace prefix?
|
||||
$len = strlen($prefix);
|
||||
if (strncmp($prefix, $class, $len) !== 0) {
|
||||
// no, move to the next registered autoloader
|
||||
return;
|
||||
}
|
||||
|
||||
// get the relative class name
|
||||
$relative_class = substr($class, $len);
|
||||
|
||||
// replace the namespace prefix with the base directory, replace namespace
|
||||
// separators with directory separators in the relative class name, append
|
||||
// with .php
|
||||
$file = $base_dir . str_replace('\\', '/', $relative_class) . '.php';
|
||||
|
||||
// if the file exists, require it
|
||||
// require the file if it exists
|
||||
if (file_exists($file)) {
|
||||
require $file;
|
||||
}
|
||||
|
@ -1,7 +0,0 @@
|
||||
<?php
|
||||
|
||||
require_once 'functions.php';
|
||||
|
||||
if (csrfValidateRequest() && !CSRFValidate()) {
|
||||
handleInvalidCSRFToken();
|
||||
}
|
@ -74,9 +74,7 @@ function DisplayDashboard(&$extraFooterScripts): void
|
||||
$varName = "freq" . str_replace('.', '', $frequency) . "active";
|
||||
$$varName = "active";
|
||||
$vpnStatus = $vpn ? "active" : "inactive";
|
||||
if ($vpn) {
|
||||
$vpnManaged = $dashboard->getVpnManged($vpn);
|
||||
}
|
||||
$vpnManaged = $vpn ? $dashboard->getVpnManaged($vpn) : null;
|
||||
$firewallManaged = $firewallStatus = "";
|
||||
$firewallInstalled = array_filter($plugins, fn($p) => str_ends_with($p, 'Firewall')) ? true : false;
|
||||
if (!$firewallInstalled) {
|
||||
|
@ -1,6 +0,0 @@
|
||||
<?php
|
||||
require_once 'src/RaspAP/Exceptions/ExceptionHandler.php';
|
||||
|
||||
$handler = new RaspAP\Exceptions\ExceptionHandler;
|
||||
?>
|
||||
|
@ -306,82 +306,6 @@ function filter_comments($var)
|
||||
return $var[0] != '#';
|
||||
}
|
||||
|
||||
/**
|
||||
* Saves a CSRF token in the session
|
||||
*/
|
||||
function ensureCSRFSessionToken()
|
||||
{
|
||||
if (empty($_SESSION['csrf_token'])) {
|
||||
$_SESSION['csrf_token'] = bin2hex(random_bytes(32));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Add CSRF Token to form
|
||||
*/
|
||||
function CSRFTokenFieldTag()
|
||||
{
|
||||
$token = htmlspecialchars($_SESSION['csrf_token']);
|
||||
return '<input type="hidden" name="csrf_token" value="' . $token . '">';
|
||||
}
|
||||
|
||||
/**
|
||||
* Retuns a CSRF meta tag (for use with xhr, for example)
|
||||
*/
|
||||
function CSRFMetaTag()
|
||||
{
|
||||
$token = htmlspecialchars($_SESSION['csrf_token']);
|
||||
return '<meta name="csrf_token" content="' . $token . '">';
|
||||
}
|
||||
|
||||
/**
|
||||
* Validate CSRF Token
|
||||
*/
|
||||
function CSRFValidate()
|
||||
{
|
||||
if (empty($_SESSION['csrf_token']) || !is_string($_SESSION['csrf_token'])) {
|
||||
error_log('Session expired or CSRF token is missing.');
|
||||
header('Location: /login');
|
||||
exit;
|
||||
}
|
||||
|
||||
$post_token = $_POST['csrf_token'] ?? null;
|
||||
$header_token = $_SERVER['HTTP_X_CSRF_TOKEN'] ?? null;
|
||||
|
||||
if (empty($post_token) && is_null($header_token)) {
|
||||
error_log('CSRF token missing in the request');
|
||||
return false;
|
||||
}
|
||||
$request_token = $post_token ?: $header_token;
|
||||
|
||||
if (hash_equals($_SESSION['csrf_token'], $request_token)) {
|
||||
return true;
|
||||
} else {
|
||||
error_log('CSRF token mismatch');
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Should the request be CSRF-validated?
|
||||
*/
|
||||
function csrfValidateRequest()
|
||||
{
|
||||
$request_method = strtolower($_SERVER['REQUEST_METHOD']);
|
||||
return in_array($request_method, [ "post", "put", "patch", "delete" ]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle invalid CSRF
|
||||
*/
|
||||
function handleInvalidCSRFToken()
|
||||
{
|
||||
header('HTTP/1.1 500 Internal Server Error');
|
||||
header('Content-Type: text/plain');
|
||||
echo 'Invalid CSRF token';
|
||||
exit;
|
||||
}
|
||||
|
||||
/**
|
||||
* Test whether array is associative
|
||||
*/
|
||||
|
11
index.php
11
index.php
@ -23,13 +23,12 @@
|
||||
* as you leave these references intact in the header comments of your source files.
|
||||
*/
|
||||
|
||||
require 'includes/session.php';
|
||||
require 'includes/csrf.php';
|
||||
ensureCSRFSessionToken();
|
||||
|
||||
require_once 'includes/exceptions.php';
|
||||
require_once 'includes/config.php';
|
||||
require_once 'includes/autoload.php';
|
||||
$handler = new RaspAP\Exceptions\ExceptionHandler;
|
||||
|
||||
require_once 'includes/CSRF.php';
|
||||
require_once 'includes/session.php';
|
||||
require_once 'includes/defaults.php';
|
||||
require_once 'includes/locale.php';
|
||||
require_once 'includes/functions.php';
|
||||
@ -59,7 +58,7 @@ initializeApp();
|
||||
<html lang="en" <?php setTheme();?>>
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<?php echo CSRFMetaTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::metaTag(); ?>
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no" />
|
||||
<meta name="description" content="">
|
||||
|
@ -79,6 +79,7 @@ class HTTPAuth
|
||||
*/
|
||||
public function logout(): void
|
||||
{
|
||||
session_regenerate_id(true); // generate a new session id
|
||||
session_unset(); // unset all session variables
|
||||
session_destroy(); // destroy the session
|
||||
$redirectUrl = $_SERVER['REQUEST_URI'];
|
||||
|
136
src/RaspAP/Tokens/CSRFTokenizer.php
Normal file
136
src/RaspAP/Tokens/CSRFTokenizer.php
Normal file
@ -0,0 +1,136 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
* CSRF tokenizer class
|
||||
*
|
||||
* @description CSRF tokenizer class for RaspAP
|
||||
* @author Bill Zimmerman <billzimmerman@gmail.com>
|
||||
* @author Martin Glaß <mail@glasz.org>
|
||||
* @license https://github.com/raspap/raspap-webgui/blob/master/LICENSE
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace RaspAP\Tokens;
|
||||
|
||||
class CSRFTokenizer {
|
||||
|
||||
// Constructor
|
||||
public function __construct()
|
||||
{
|
||||
$this->ensureSession();
|
||||
|
||||
// ensure a CSRF token exists in the session
|
||||
if (empty($_SESSION['csrf_token'])) {
|
||||
$this->ensureCSRFSessionToken();
|
||||
header("Location: " .$_SERVER['REQUEST_URI']);
|
||||
exit;
|
||||
}
|
||||
|
||||
if ($this->csrfValidateRequest()) {
|
||||
$token = $_POST['csrf_token'] ?? $_SERVER['HTTP_X_CSRF_TOKEN'] ?? '';
|
||||
if (!$this->CSRFValidate($token)) {
|
||||
$this->handleInvalidCSRFToken();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Saves a CSRF token in the session
|
||||
*/
|
||||
public function ensureCSRFSessionToken(): void
|
||||
{
|
||||
if (empty($_SESSION['csrf_token'])) {
|
||||
$_SESSION['csrf_token'] = bin2hex(random_bytes(32));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a CSRF Token to form
|
||||
*/
|
||||
public function CSRFTokenFieldTag(): string
|
||||
{
|
||||
$token = htmlspecialchars($_SESSION['csrf_token']);
|
||||
return '<input type="hidden" name="csrf_token" value="' . $token . '">';
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a CSRF meta tag (for use with xhr, for example)
|
||||
*/
|
||||
public function CSRFMetaTag(): string
|
||||
{
|
||||
// if session has expired or user has logged out,
|
||||
// create a new session and token
|
||||
if (empty($_SESSION['csrf_token'])) {
|
||||
$this->ensureSession();
|
||||
$this->ensureCSRFSessionToken();
|
||||
return $_SESSION['csrf_token'];
|
||||
} else {
|
||||
$token = htmlspecialchars($_SESSION['csrf_token']);
|
||||
return '<meta name="csrf_token" content="' . $token . '">';
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates a CSRF Token
|
||||
*
|
||||
* @param string $token
|
||||
*/
|
||||
public function CSRFValidate(string $token): bool
|
||||
{
|
||||
if (empty($_SESSION['csrf_token']) || !is_string($_SESSION['csrf_token'])) {
|
||||
error_log('Session expired or CSRF token is missing.');
|
||||
header('Location: /login');
|
||||
exit;
|
||||
}
|
||||
|
||||
$post_token = $token ?? null;
|
||||
$header_token = $_SERVER['HTTP_X_CSRF_TOKEN'] ?? null;
|
||||
|
||||
if (empty($post_token) && is_null($header_token)) {
|
||||
error_log('CSRF token missing in the request');
|
||||
return false;
|
||||
}
|
||||
$request_token = $post_token ?: $header_token;
|
||||
|
||||
if (hash_equals($_SESSION['csrf_token'], $request_token)) {
|
||||
return true;
|
||||
} else {
|
||||
error_log('CSRF token mismatch');
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Should the request be CSRF-validated?
|
||||
*/
|
||||
public function csrfValidateRequest(): bool
|
||||
{
|
||||
$request_method = strtolower($_SERVER['REQUEST_METHOD']);
|
||||
return in_array($request_method, [ "post", "put", "patch", "delete" ]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle invalid CSRF
|
||||
*/
|
||||
public function handleInvalidCSRFToken(): string
|
||||
{
|
||||
if (function_exists('http_response_code')) {
|
||||
http_response_code(500);
|
||||
echo 'Invalid CSRF token';
|
||||
} else {
|
||||
header('HTTP/1.1 500 Internal Server Error');
|
||||
header('Content-Type: text/plain');
|
||||
echo 'Invalid CSRF token';
|
||||
}
|
||||
exit;
|
||||
}
|
||||
|
||||
protected function ensureSession()
|
||||
{
|
||||
if (session_status() == PHP_SESSION_NONE) {
|
||||
session_start();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -24,7 +24,7 @@ class Dashboard {
|
||||
* @param string $interface
|
||||
* @return string
|
||||
*/
|
||||
public function getVpnManged(?string $interface = null): ?string
|
||||
public function getVpnManaged(?string $interface = null): ?string
|
||||
{
|
||||
switch ($interface) {
|
||||
case 'wg0':
|
||||
|
@ -28,7 +28,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="adblock_conf" enctype="multipart/form-data" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField();?>
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item"><a class="nav-link active" id="blocklisttab" href="#adblocklistsettings" data-bs-toggle="tab"><?php echo _("Blocklist settings"); ?></a></li>
|
||||
|
@ -19,7 +19,7 @@
|
||||
<?php $status->showMessages(); ?>
|
||||
<h4><?php echo _("Authentication settings") ;?></h4>
|
||||
<form role="form" action="auth_conf" method="POST" class="needs-validation" novalidate>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<div class="row">
|
||||
<div class="mb-3 col-md-6">
|
||||
<label for="username"><?php echo _("Username"); ?></label>
|
||||
|
@ -27,7 +27,7 @@
|
||||
<div class="row" id="wpaConf">
|
||||
<div class="col">
|
||||
<form method="POST" action="wpa_conf" name="wpa_conf_form">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<input type="hidden" name="client_settings" ?>
|
||||
<div class="js-wifi-stations loading-spinner"></div>
|
||||
</form>
|
||||
|
@ -30,7 +30,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form action="wlan0_info" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
|
@ -30,7 +30,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form method="POST" action="dhcpd_conf" class="js-dhcp-settings-form needs-validation" novalidate>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs mb-3">
|
||||
|
@ -50,7 +50,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="hostapd_conf" method="POST" class="needs-validation" novalidate>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
|
@ -15,7 +15,7 @@
|
||||
</div>
|
||||
<div class="text-center mb-4">
|
||||
<form id="admin-login-form" action="login" method="POST" class="needs-validation" novalidate>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<div class="form-group">
|
||||
<input type="hidden" name="login-auth">
|
||||
<input type="hidden" id="redirect-url" name="redirect-url" value="<?php echo htmlspecialchars($redirectUrl, ENT_QUOTES, 'UTF-8'); ?>">
|
||||
|
@ -29,7 +29,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="openvpn_conf" enctype="multipart/form-data" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item"><a class="nav-link active" id="clienttab" href="#openvpnclient" data-bs-toggle="tab"><?php echo _("Client settings"); ?></a></li>
|
||||
|
@ -28,7 +28,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="provider_conf" enctype="multipart/form-data" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item"><a class="nav-link active" id="clienttab" href="#providerclient" data-bs-toggle="tab"><?php echo _("Settings"); ?></a></li>
|
||||
|
@ -28,7 +28,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="restapi_conf" method="POST" class="needs-validation" novalidate>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item"><a class="nav-link active" id="restapisettingstab" href="#restapisettings" data-bs-toggle="tab"><?php echo _("Settings"); ?></a></li>
|
||||
|
@ -11,7 +11,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="system_info" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<ul class="nav nav-tabs" role="tablist">
|
||||
<li role="presentation" class="nav-item"><a class="nav-link active" id="basictab" href="#basic" aria-controls="basic" role="tab" data-bs-toggle="tab"><?php echo _("Basic"); ?></a></li>
|
||||
<li role="presentation" class="nav-item"><a class="nav-link" id="languagetab" href="#language" aria-controls="language" role="tab" data-bs-toggle="tab"><?php echo _("Language"); ?></a></li>
|
||||
|
@ -3,7 +3,7 @@
|
||||
<h4 class="mt-3"><?php echo _("Advanced settings") ;?></h4>
|
||||
<?php if (!RASPI_MONITOR_ENABLED) : ?>
|
||||
<form action="system_info" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<div class="row">
|
||||
<div class="mb-3 col-md-6">
|
||||
<label for="code"><?php echo _("Web server port") ;?></label>
|
||||
|
@ -56,7 +56,7 @@ include('includes/sysstats.php');
|
||||
</div>
|
||||
|
||||
<form action="system_info" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<?php if (!RASPI_MONITOR_ENABLED) : ?>
|
||||
<input type="button" class="btn btn-warning" data-bs-toggle="modal" data-bs-target="#system-confirm-reboot" value="<?php echo _("Reboot"); ?>" />
|
||||
<input type="button" class="btn btn-warning" data-bs-toggle="modal" data-bs-target="#system-confirm-shutdown" value="<?php echo _("Shutdown"); ?>" />
|
||||
|
@ -1,7 +1,7 @@
|
||||
<!-- plugins tab -->
|
||||
<div role="tabpanel" class="tab-pane" id="plugins">
|
||||
<h4 class="mt-3"><?php echo _("Plugins") ;?></h4>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<div class="row">
|
||||
<div class="form-group col-lg-8 col-md-8">
|
||||
<label>
|
||||
|
@ -12,7 +12,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<form action="system_info" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<button type="button" onClick="window.location.reload();" class="btn btn-outline btn-primary"><i class="fas fa-sync-alt"></i> <?php echo _("Refresh") ?></a>
|
||||
</form>
|
||||
</div>
|
||||
|
@ -2,7 +2,7 @@
|
||||
<div role="tabpanel" class="tab-pane" id="tools">
|
||||
<h4 class="mt-3"><?php echo _("System tools") ;?></h4>
|
||||
<?php if (!RASPI_MONITOR_ENABLED) : ?>
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
|
||||
<div class="row">
|
||||
<div class="mb-3 col-lg-8 col-md-8">
|
||||
|
@ -28,7 +28,7 @@
|
||||
<div class="card-body">
|
||||
<?php $status->showMessages(); ?>
|
||||
<form role="form" action="wg_conf" enctype="multipart/form-data" method="POST">
|
||||
<?php echo CSRFTokenFieldTag() ?>
|
||||
<?php echo \RaspAP\Tokens\CSRF::hiddenField(); ?>
|
||||
<!-- Nav tabs -->
|
||||
<ul class="nav nav-tabs">
|
||||
<li class="nav-item"><a class="nav-link active" id="settingstab" href="#wgsettings" data-bs-toggle="tab"><?php echo _("Settings"); ?></a></li>
|
||||
|
Loading…
x
Reference in New Issue
Block a user