*/ // must be run within Dokuwiki $webroot = reset(split('lib',dirname(__FILE__))); if(!defined('DOKU_INC')) define('DOKU_INC', $webroot); if(!defined('DOKU_PLUGIN')) define('DOKU_PLUGIN',DOKU_INC.'lib/plugins'); if(!defined('DOKU_PAGES')) define('DOKU_PAGES',DOKU_INC.'data/pages'); if(!defined('DOKU_TMP')) define('DOKU_TMP',DOKU_INC.'data/tmp'); require_once (DOKU_INC.'inc/pageutils.php'); require_once (DOKU_INC.'inc/utf8.php'); class PrologTag { var $entryTagPattern = '//'; var $exitTagPattern = '/<\/prolog>/'; var $attributeEntryPattern = '\('; var $attributeExitPattern = '\)'; var $attributeValuePattern = '[^\)]*'; var $attributeName; var $attributePattern; /** * Constructor */ function PrologTag() { } /** * Gets all prolog entry tags from the text file * @param string $file file path * @return array $matchedTags found prolog entry tags */ function getEntryTags($file = null) { $fileContent = file_get_contents($file); $foundTags = preg_match_all($this->entryTagPattern, $fileContent, $matchedTags); return $matchedTags[0]; } /** * Sets attribute pattern * @param string $attributeName attribute name */ function setAttributePattern($attributeName) { $this->attributeName = $attributeName; $this->attributePattern = '/'; $this->attributePattern .= '([a-zA-Z0-9]+)'; $this->attributePattern .= $this->attributeEntryPattern; $this->attributePattern .= '('.$this->attributeValuePattern.')'; $this->attributePattern .= $this->attributeExitPattern; $this->attributePattern .= '/'; } /** * Gets the attribute value from the prolog entry tag * @param string $prologTag prolog entry tag * @return string $matched matched attribute value */ function getAttributeValue($prologTag = null) { $found = preg_match_all($this->attributePattern, $prologTag, $matched); $attrValue = ''; foreach($matched[1] as $i => $attrName) { if($attrName == $this->attributeName) { $attrValue = $matched[2][$i]; break; } } return $attrValue; } /** * Executes prolog code in the Prolog interpreter * @param string $prologCode the prolog source code * @param string $maxExecutionTime the limit for maximum interpretation time (in seconds) * @return array $executed array with output and errors from the interpreter */ function execute($prologCode = null, $maxExecutionTime = 5) { $executed = array('',''); if(!isset($prologCode)) return $executed; $maxExecutionTime = intval($maxExecutionTime); if($maxExecutionTime < 1 || $maxExecutionTime > 5) //1sec - 30sec $maxExecutionTime = 5; $tmpname = tempnam(DOKU_TMP, 'pl_'); $stdin = $tmpname.'.pl'; unlink($tmpname); $handleStdin = fopen($stdin, 'w'); fwrite($handleStdin, $prologCode); fclose($handleStdin); $descriptorspec = array( 0 => array('pipe', 'r'), // stdin 1 => array('pipe', 'w'), // stdout 2 => array('pipe', 'w') // stderr ); $process = proc_open('pl', $descriptorspec, $pipes); if(is_resource($process)) { fwrite($pipes[0], '[\''.substr($stdin, 0, -3).'\'].'); fclose($pipes[0]); $step = 10000; //0.01 second $maxExecutionTime = $maxExecutionTime * 1000000; $status = proc_get_status($process); while($status['running'] && $maxExecutionTime != 0) { $maxExecutionTime -= $step; usleep($step); $status = proc_get_status($process); } if($status['running'] == true) { fclose($pipes[1]); //stdout fclose($pipes[2]); //stderr proc_terminate($process); $executed[1] .= 'Process reached the maximum execution time and has been terminated! '; proc_close($process); } else { $executed[0] = stream_get_contents($pipes[1]); $executed[1] = stream_get_contents($pipes[2]); fclose($pipes[1]); //stdout fclose($pipes[2]); //stderr proc_close($process); } fclose($pipes[1]); //stdout fclose($pipes[2]); //stderr proc_close($process); } unlink($stdin); return $executed; } } ?>