Сама ошибка в инете обсуждалась неоднократно и в большинстве случаев у народа очень простое решение проблемы. Однако, иногда встречалось и что-то нестандартное, на что все равно не было получено ответа. Вобщем, у меня сообщение такое: Код (Text): Fatal error: Cannot redeclare restoresettings() (previously declared in D:\PROJECTS\WebMailPhp\inc_settings.php:5) in D:\PROJECTS\WebMailPhp\inc_settings.php on line 151 PHP Version 5.1.2, Microsoft-IIS/6.0 Приложение ajax-овое. Состоит из двух частей - логин (index.php) и все остальное (page.php). Каждая из этих частей имеет движок javascript, который в свою очередь делает асинхронный запрос на processing.php. Каждая из этих трех страниц подключает файл inc_settings.php, в котором описана функция restoresettings(). 1. Проверила, нет ли дублирующего подключения - не нашла. 2. Я заменила все require на require_once. Не помогло. 3. Поставила запись логов error_log перед каждым известным мне подключением файла inc_settings.php с указанием страницы, с которой происходит вызов, а также в сам этот файл с указанием, что он был подключен. Никаких повторов в полученном логе не обнаружила: Код (Text): index.php inc_settings.php processing.php inc_settings.php page.php inc_settings.php processing.php inc_settings.php ... 4. Переместила в другую директорию - ошибку не выводит. В прежней - выводит. Помогите! Может кто знает, в чем проблема?
Да, еще может возникнуть вопрос, что же находится в 5-й и 151-й строках в inc_settings: Код (Text): <?php function RestoreSettings() { global $strIniDir; global $Settings; //5-я строка $Settings = Array(); ... }//конец функции //151-я строка ... ?>
Функция парсит xml-файл, в котором хранятся настройки и исправляет их, если что-то где-то некорректно. Но эта функция прекрасно работает в не-ajax-овой версии системы. Код (Text): function RestoreSettings() { global $strIniDir; global $Settings; $Settings = Array(); $FileName = $strIniDir.'settings/config.xml'; $CurTeg = ''; function StartElement($Parser, $Name, $Attrs) { global $CurTeg; $CurTeg = $Name; } function EndElement($Parser, $Name) { global $CurTeg; $CurTeg = '\\'.$Name; } function CharacterElement($Parser, $Data) { global $CurTeg, $Settings, $strIniDir; switch (strtolower($CurTeg)) { case 'adminpassword': $Settings['txtAdminPassword'] = $Data; break; case 'allowadvancedlogin': $Settings['intAllowAdvancedLogin'] = (settype($Data, 'integer') == true) ? $Data : 0; break; case 'allowajax': $Settings['intAllowAjax'] = (settype($Data, 'integer') == true) ? $Data : 1; break; case 'attachmentsizelimit': $Settings['intAttachmentSizeLimit'] = (settype($Data, 'integer') == true) ? $Data : 1000200; break; case 'automaticcorrectloginsettings': $Settings['intAutomaticCorrectLoginSettings'] = (settype($Data, 'integer') == true) ? $Data : 0; break; case 'crlf': $Settings['txtCrlf'] = $Data; break; case 'defaultcharset': $Settings['txtDefaultCharset'] = $Data; break; case 'defaultdomainoptional': $Settings['txtDefaultDomainOptional'] = $Data; break; case 'defaultlogpath': $Path = $Data; if (strrpos($Path, '\\') > strrpos($Path, '/')) $Pos = strrpos($Path, '\\'); else $Pos = strrpos($Path, '/'); $Dir = substr($Path, 0, $Pos+1); $File = substr($Path, $Pos+1, strlen($Path)); if ($File == '') $File = 'log.txt'; if (strpos($File, '.') == false) $File = $File.'.txt'; $Parts = explode('.', $File); if ($Parts[0] == '') $Parts[0] = 'log'; if ($Parts[1] == '') $Parts[1] = 'txt'; $File = $Parts[0].'.'.$Parts[1]; if (is_dir($Dir)) $Settings['txtDefaultLogPath'] = $Dir.$File; elseif (is_dir($strIniDir.'logging/')) $Settings['txtDefaultLogPath'] = $strIniDir.'logging/'.$File; else $Settings['txtDefaultLogPath'] = $strIniDir.$File; break; case 'defaultskin': $Settings['txtDefaultSkin'] = $Data; break; case 'defaulttempdir': if (is_dir($Data)) $Settings['txtDefaultTempDir'] = $Data; elseif (is_dir($strIniDir.'attachments/')) $Settings['txtDefaultTempDir'] = $strIniDir.'attachments/'; else $Settings['txtDefaultTempDir'] = $strIniDir.'/'; break; case 'defaulttimeoffset': $Settings['txtDefaultTimeOffset'] = $Data; break; case 'disableerrorhandling': $Settings['intDisableErrorHandling'] = (settype($Data, 'integer') == true) ? $Data : 1; break; case 'enablelogging': $Settings['intEnableLogging'] = (settype($Data, 'integer') == true) ? $Data : 1; break; case 'hideloginmode': $Settings['intHideLoginMode'] = (settype($Data, 'integer') == true) ? $Data : 0; break; case 'imapflags': $Settings['txtImapFlags'] = $Data; break; case 'incomingmailserver': $Settings['txtIncomingMailServer'] = $Data; break; case 'incomingmailport': $Settings['intIncomingMailPort'] = (settype($Data, 'integer') == true) ? $Data : 110; break; case 'mailsperpage': $Settings['intMailsPerPage'] = (settype($Data, 'integer') == true) ? $Data : 10; break; case 'outgoingmailserver': $Settings['txtOutgoingMailServer'] = $Data; break; case 'outgoingmailport': $Settings['intOutgoingMailPort'] = (settype($Data, 'integer') == true) ? $Data : 25; break; case 'reqsmtpauth': $Settings['intReqSmtpAuth'] = (settype($Data, 'integer') == true) ? $Data : 0; break; case 'showtextlabels': $Settings['intShowTextLabels'] = (settype($Data, 'integer') == true) ? $Data : 1; break; case 'windowtitle': $Settings['txtWindowTitle'] = $Data; break; } } $Settings['txtAdminPassword'] = ''; $Settings['intAllowAdvancedLogin'] = 1; $Settings['intAllowAjax'] = 1; $Settings['intAttachmentSizeLimit'] = 1000200; $Settings['intAutomaticCorrectLoginSettings'] = 0; $Settings['txtCrlf'] = '\r\n'; $Settings['txtDefaultCharset'] = ''; $Settings['txtDefaultDomainOptional'] = ''; $Settings['txtDefaultLogPath'] = $strIniDir; $Settings['txtDefaultSkin'] = 'Default'; $Settings['txtDefaultTempDir'] = $strIniDir; $Settings['txtDefaultTimeOffset'] = ''; $Settings['intDisableErrorHandling'] = 0; $Settings['intEnableLogging'] = 1; $Settings['intHideLoginMode'] = 0; $Settings['txtImapFlags'] = 'no_flags'; $Settings['txtIncomingMailServer'] = 'localhost'; $Settings['intIncomingMailPort'] = 110; $Settings['intMailsPerPage'] = 10; $Settings['txtOutgoingMailServer'] = 'localhost'; $Settings['intOutgoingMailPort'] = 25; $Settings['intReqSmtpAuth'] = 0; $Settings['intShowTextLabels'] = 1; $Settings['txtWindowTitle'] = ''; $XmlParser = xml_parser_create(); xml_set_element_handler($XmlParser, 'StartElement', 'EndElement'); xml_set_character_data_handler ($XmlParser, 'CharacterElement'); if (!($FileHandler = fopen($FileName, "r"))) { $ErrorDesc = 'File '.$FileName.' not found'; return false; } while ($Data = fread($FileHandler, 4096)) { if (!xml_parse($XmlParser, $Data, feof($FileHandler))) { $ErrorDesc = 'XML error: '.xml_error_string(xml_get_error_code($XmlParser)).' at line '.xml_get_current_line_number($XmlParser); return false; } } xml_parser_free($XmlParser); return $Settings; }
гениально! спасибо за разъяснения! Впрочем, наверное, я забыла написать, что искала такую же функцию по всем скриптам и не нашла! (хотя искать было незачем - я знаю свои скрипты очень хорошо)
Ну вобщем пишу последние данные по указанной выше проблеме. Сегодня я с утра с нуля построила сайт, постепенно добавляя функциональность. Ошибки не было. Появилась та же самая ошибка, когда я добавила функцию, отлавливающую ошибки и записывающую их в файл. Приложение ajax не позволяет роскошь смотреть ошибки на экране. То есть необходимо либо просто отключить их вывод, либо записывать в файл для дебага. Итак, processing.php Код (Text): require './inc_functions.php'; set_error_handler('errr'); inc_functions.php Код (Text): function errr($errno, $errstr, $errfile, $errline) { switch($errno){ case E_ERROR: $er_lev = 'E_ERROR';break; case E_WARNING: $er_lev = 'E_WARNING';break; case E_PARSE: $er_lev = 'E_PARSE';break; case E_NOTICE: $er_lev = 'E_NOTICE';break; case E_CORE_ERROR: $er_lev = 'E_CORE_ERROR';break; case E_CORE_WARNING: $er_lev = 'E_CORE_WARNING';break; case E_COMPILE_ERROR: $er_lev = 'E_COMPILE_ERROR';break; case E_COMPILE_WARNING: $er_lev = 'E_COMPILE_WARNING';break; case E_USER_ERROR: $er_lev = 'E_USER_ERROR';break; case E_USER_WARNING: $er_lev = 'E_USER_WARNING';break; case E_USER_NOTICE: $er_lev = 'E_USER_NOTICE';break; case E_ALL: $er_lev = 'E_ALL';break; case E_STRICT: $er_lev = '';break; default: $er_lev = ''; } if ($er_lev != '') error_log(date('H:i:s ')." $er_lev: $errstr in $errfile on line $errline\r\n", 3, 'error.txt'); } Объясните глупенькой, в чем дело?
karrbon, прочитав Ваше сообщение, сразу подумала, что, конечно, эти функции должны быть вынесены, поскольку переопределяются каждый раз при вызове функции. Однако, во-первых, поскольку они определены внутри функции, по окончании работы этой функции они сразу уничтожаются; а во-вторых, если дело в них, то php должен жаловаться на переопределение этих функций, а не restoresettings. Все же я провела эксперимент и вынесла эти функции: Код (Text): Fatal error: Cannot redeclare startelement() (previously declared in D:\PROJECTS\WebMailPhp\inc_settings.php:2) in D:\PROJECTS\WebMailPhp\inc_settings.php on line 6
> поскольку они определены внутри функции, по окончании работы этой функции они сразу уничтожаются; неверно вообще, приведите минимальный неработающий код
мой минимальный неработающий код пока что очень большой. Я постараюсь свести его к минимуму и приведу попозже
karrbon, Извините, но пока не могу сделать минимальный работающий код. У меня создается впечатление, что это глюка связки php+iis 1. при перемещении в другую папку те же скрипты начинают работать 2. уже второй раз длительная генерация этой ошибки заканчивается ошибкой PHP has encountered an Access Violation at, от которой можно избавиться только рестартом iis 3. сегодня после возникновения этой ошибки и рестарта iis ошибка cannot redeclare перестала появляться, из-за чего я и не могу сделать минимальный неработающий код
Очень похоже, только версия php более позняя и случилось это не сразу после инсталяции, а через полгода Да, и ошибки вроде "Memory could not be read" не было. Хотя "PHP has encountered an Access Violation at" похоже чем-то. По ней я сразу нашла всю нужную инфу. Но я тогда еще не думала, что это может быть связано, потому что после рестарта iis "cannot redeclare" не исчезла.