shell bypass 403
<?php /** * @package admintools * @copyright Copyright (c)2010-2024 Nicholas K. Dionysopoulos / Akeeba Ltd * @license GNU General Public License version 3, or later */ namespace Akeeba\Component\AdminTools\Administrator\Model; defined('_JEXEC') or die; use Akeeba\Component\AdminTools\Administrator\Helper\Storage; use Joomla\CMS\Application\CMSApplication; use Joomla\CMS\Factory; use Joomla\CMS\MVC\Model\BaseDatabaseModel; use Joomla\String\Inflector; #[\AllowDynamicProperties] class MainpasswordModel extends BaseDatabaseModel { public $views = [ 'adminpassword' => 'COM_ADMINTOOLS_TITLE_ADMINPASSWORD', 'badwords' => 'COM_ADMINTOOLS_TITLE_BADWORDS', 'cleantempdirectory' => 'COM_ADMINTOOLS_TITLE_CLEANTEMPDIRECTORY', 'databasetools' => 'COM_ADMINTOOLS_TITLE_DBTOOLS', 'emergencyoffline' => 'COM_ADMINTOOLS_TITLE_EMERGENCYOFFLINE', 'fixpermissions' => 'COM_ADMINTOOLS_TITLE_FIXPERMISSIONS', 'configurepermissions' => 'COM_ADMINTOOLS_TITLE_CONFIGUREPERMISSIONS', 'htaccessmaker' => 'COM_ADMINTOOLS_TITLE_HTACCESSMAKER', 'nginxconfmaker' => 'COM_ADMINTOOLS_TITLE_NGINXCONFMAKER', 'webconfigmaker' => 'COM_ADMINTOOLS_TITLE_WEBCONFIGMAKER', 'ipautobanhistories' => 'COM_ADMINTOOLS_TITLE_IPAUTOBANHISTORIES', 'autobannedaddresses' => 'COM_ADMINTOOLS_TITLE_AUTOBANNEDADDRESSES', 'disallowlists' => 'COM_ADMINTOOLS_TITLE_DISALLOWLISTS', 'adminallowlists' => 'COM_ADMINTOOLS_TITLE_ADMINALLOWLISTS', 'mainpassword' => 'COM_ADMINTOOLS_TITLE_MAINPASSWORD', 'quickstart' => 'COM_ADMINTOOLS_TITLE_QUICKSTART', 'urlredirections' => 'COM_ADMINTOOLS_TITLE_URLREDIRECTIONS', 'scanner' => 'COM_ADMINTOOLS_TITLE_SCANNER', 'scan' => 'COM_ADMINTOOLS_TITLE_SCANS', 'scanalerts' => 'COM_ADMINTOOLS_TITLE_SCANALERTS_MAINPASSWORD', 'seoandlinktools' => 'COM_ADMINTOOLS_TITLE_SEOANDLINKTOOLS', 'webapplicationfirewall' => 'COM_ADMINTOOLS_TITLE_WAF', 'wafdenylists' => 'COM_ADMINTOOLS_TITLE_WAFDENYLISTS', 'configurewaf' => 'COM_ADMINTOOLS_TITLE_CONFIGUREWAF', 'wafexceptions' => 'COM_ADMINTOOLS_TITLE_WAFEXCEPTIONS', 'checktempandlogdirectories' => 'COM_ADMINTOOLS_TITLE_CHECKTEMPANDLOGDIRECTORIES', 'schedulinginformation' => 'COM_ADMINTOOLS_TITLE_SCHEDULINGINFORMATION', 'exportimport' => 'COM_ADMINTOOLS_TITLE_EXPORTIMPORT', 'blockedrequestslog' => 'COM_ADMINTOOLS_TITLE_LOG', 'unblockip' => 'COM_ADMINTOOLS_TITLE_UNBLOCKIP', 'tempsuperusers' => 'COM_ADMINTOOLS_TITLE_TEMPSUPERUSERS', ]; /** * Checks if the user should be granted access to the current view, * based on his Main Password setting. * * @param string $view Optional. The string to check. Leave null to use the current view. * * @return bool */ public function accessAllowed(?string $view = null): bool { /** @var CMSApplication $app */ $app = Factory::getApplication(); $session = $app->getSession(); // Is this a view protected by the Main Password feature? if (empty($view)) { $view = $app->input->getCmd('view', 'Controlpanel'); } $inflector = new Inflector(); $altView = $inflector->isPlural($view) ? $inflector->toSingular($view) : $inflector->toPlural($view); // We're working on lowercase $view = strtolower($view); $altView = strtolower($altView); if (!isset($this->views[$view]) && !isset($this->views[$altView])) { return true; } // Do we have a Main Password? $params = Storage::getInstance(); $mainHash = $params->getValue('mainpassword', $params->getValue('masterpassword', '')); if (empty($mainHash)) { return true; } // Compare the main pw with the one the user entered $mainHash = md5($mainHash); $userHash = $session->get('admintools.userpwhash', ''); if ($userHash === $mainHash) { // The password matches, we are allowed to access everything return true; } // The login is invalid. If the view is locked I'll have to kick the user out. $lockedviews_raw = $params->getValue('lockedviews', ''); if (empty($lockedviews_raw)) { // There are no locked views. return true; } $lockedViews = explode(",", $lockedviews_raw); $lockedViews = array_map('strtolower', $lockedViews); if (empty($lockedViews)) { // This shouldn't happen. There are no locked views. return true; } // Special case: view=Blockedrequestslog, task=browse, format=json (graphs) is always allowed. $task = $app->input->get('task', ''); $format = $app->input->get('format', 'html'); if ( (($view == 'blockedrequestslog') || ($view == 'blockedrequestslogs')) && (($format == 'json') || $format == 'raw') && (empty($task) || ($task == 'main') || ($task == 'default')) ) { return true; } // Check if the view is locked. if (in_array($view, $lockedViews) || in_array($altView, $lockedViews)) { return false; } return true; } /** * Compares the user-supplied password against the main password * * @return bool True if the passwords match */ public function hasValidPassword() { $params = Storage::getInstance(); $mainHash = $params->getValue('mainpassword', $params->getValue('masterpassword', '')); if (empty($mainHash)) { return true; } $mainHash = md5($mainHash); $userHash = Factory::getApplication()->getSession()->get('admintools.userpwhash', ''); return hash_equals($mainHash, $userHash); } /** * Stores the hash of the user's password in the session * * @param $passwd string The password supplied by the user * * @return void */ public function setUserPassword($passwd) { $userHash = md5($passwd); Factory::getApplication()->getSession()->set('admintools.userpwhash', $userHash); } /** * Saves the Main Password and the protected views list * * @param string $mainPassword The new main password * @param array $protectedViews A list of the views to protect * * @return void */ public function saveSettings($mainPassword, array $protectedViews) { $params = Storage::getInstance(); // Add the new main password (also replaces the old "Master password") $params->setValue('masterpassword', null); $params->setValue('mainpassword', $mainPassword); // Add the protected views if (!empty($mainPassword) && !in_array('Mainpassword', $protectedViews)) { $protectedViews[] = 'Mainpassword'; } $params->setValue('lockedviews', implode(',', $protectedViews)); $params->save(); } /** * Get a list of the views which can be locked down and their lockdown status * * @return array */ public function &getItemList() { $lockedViews = []; $params = Storage::getInstance(); $lockedViewsRaw = $params->getValue('lockedviews', ''); if (!empty($lockedViewsRaw)) { $lockedViews = explode(",", $lockedViewsRaw); } $views = []; foreach ($this->views as $view => $langKey) { // I will only show a view if it actually exists as a View directory or Controller file. $viewDir = JPATH_ADMINISTRATOR . '/components/com_admintools/src/View/' . ucfirst($view); $controllerFile = JPATH_ADMINISTRATOR . '/components/com_admintools/src/Controller/' . ucfirst($view) . 'Controller.php'; if (!@is_dir($viewDir) && !@is_file($controllerFile)) { continue; } $views[$view] = [ in_array($view, $lockedViews), $langKey, ]; } return $views; } /** * Returns the stored main password * * @return string */ public function getMainpassword() { $params = Storage::getInstance(); return $params->getValue('mainpassword', $params->getValue('masterpassword', '')); } }