Files
server/usr/share/psa-pear/pear/php/Horde/ErrorHandler.php
2026-01-07 20:52:11 +01:00

215 lines
6.8 KiB
PHP

<?php
/**
* Provides methods used to handle error reporting.
*
* Copyright 2012-2017 Horde LLC (http://www.horde.org/)
*
* See the enclosed file COPYING for license information (LGPL). If you
* did not receive this file, see http://www.horde.org/licenses/lgpl21.
*
* @author Michael Slusarz <slusarz@horde.org>
* @category Horde
* @license http://www.horde.org/licenses/lgpl21 LGPL-2.1
* @package Core
*/
class Horde_ErrorHandler
{
/**
* Aborts with a fatal error, displaying debug information to the user.
*
* @param mixed $error Either a string or an object with a getMessage()
* method (e.g. PEAR_Error, Exception).
*/
public static function fatal($error)
{
global $registry;
if (is_object($error)) {
switch (get_class($error)) {
case 'Horde_Exception_AuthenticationFailure':
$auth_app = !$registry->clearAuthApp($error->application);
if ($auth_app &&
$registry->isAuthenticated(array('app' => $error->application, 'notransparent' => true))) {
break;
}
try {
Horde::log($error, 'NOTICE');
} catch (Exception $e) {}
if (Horde_Cli::runningFromCLI()) {
$cli = new Horde_Cli();
$cli->fatal($error);
}
$params = array();
if ($registry->getAuth()) {
$params['app'] = $error->application;
}
switch ($error->getCode()) {
case Horde_Auth::REASON_MESSAGE:
$params['msg'] = $error->getMessage();
$params['reason'] = $error->getCode();
break;
}
$logout_url = $registry->getLogoutUrl($params);
/* Clear authentication here. Otherwise, there might be
* issues on the login page since we would otherwise need
* to do session token checking (which might not be
* available, so logout won't happen, etc...) */
if ($auth_app && array_key_exists('app', $params)) {
$registry->clearAuth();
}
$logout_url->redirect();
}
}
try {
Horde::log($error, 'EMERG');
} catch (Exception $e) {}
try {
$cli = Horde_Cli::runningFromCLI();
} catch (Exception $e) {
die($e);
}
if ($cli) {
$cli = new Horde_Cli();
$cli->fatal($error);
}
if (!headers_sent()) {
header('Content-type: text/html; charset=UTF-8');
}
echo <<< HTML
<html>
<head><title>Horde :: Fatal Error</title></head>
<body style="background:#fff; color:#000">
HTML;
ob_start();
try {
$admin = (isset($registry) && $registry->isAdmin());
echo '<h1>' . Horde_Core_Translation::t("A fatal error has occurred") . '</h1>';
if (is_object($error) && method_exists($error, 'getMessage')) {
echo '<h3>' . htmlspecialchars($error->getMessage()) . '</h3>';
} elseif (is_string($error)) {
echo '<h3>' . htmlspecialchars($error) . '</h3>';
}
if ($admin) {
if ($error instanceof Throwable ||
$error instanceof Exception) {
$trace = $error;
$file = $error->getFile();
$line = $error->getLine();
} else {
$trace = debug_backtrace();
$calling = array_shift($trace);
$file = $calling['file'];
$line = $calling['line'];
}
printf(Horde_Core_Translation::t("in %s:%d"), $file, $line);
echo '<div id="backtrace"><pre>' .
strval(new Horde_Support_Backtrace($trace)) .
'</pre></div>';
if (is_object($error)) {
echo '<h3>' . Horde_Core_Translation::t("Details") . '</h3>';
echo '<h4>' . Horde_Core_Translation::t("The full error message is logged in Horde's log file, and is shown below only to administrators. Non-administrative users will not see error details.") . '</h4>';
ob_flush();
flush();
echo '<div id="details"><pre>' . htmlspecialchars(print_r($error, true)) . '</pre></div>';
}
} else {
echo '<h3>' . Horde_Core_Translation::t("Details have been logged for the administrator.") . '</h3>';
}
} catch (Exception $e) {
die($e);
}
ob_end_flush();
echo '</body></html>';
exit(1);
}
/**
* PHP legacy error handling (non-Exceptions).
*
* @param integer $errno See set_error_handler().
* @param string $errstr See set_error_handler().
* @param string $errfile See set_error_handler().
* @param integer $errline See set_error_handler().
* @param array $errcontext See set_error_handler().
*/
public static function errorHandler($errno, $errstr, $errfile, $errline,
$errcontext)
{
$er = error_reporting();
// Calls prefixed with '@'.
if ($er == 0) {
// Must return false to populate $php_errormsg (as of PHP 5.2).
return false;
}
if (!($er & $errno) || !class_exists('Horde_Log')) {
return;
}
$options = array();
try {
switch ($errno) {
case E_WARNING:
case E_USER_WARNING:
case E_RECOVERABLE_ERROR:
$priority = Horde_Log::WARN;
break;
case E_NOTICE:
case E_USER_NOTICE:
$priority = Horde_Log::NOTICE;
break;
case E_STRICT:
$options['notracelog'] = true;
$priority = Horde_Log::DEBUG;
break;
default:
$priority = Horde_Log::DEBUG;
break;
}
Horde::log(new ErrorException('PHP ERROR: ' . $errstr, 0, $errno, $errfile, $errline), $priority, $options);
} catch (Exception $e) {}
}
/**
* Catch fatal errors.
*/
public static function catchFatalError()
{
$error = error_get_last();
if ($error['type'] == E_ERROR) {
self::fatal(new ErrorException(
$error['message'],
0,
$error['type'],
$error['file'],
$error['line']
));
}
}
}