sAvAte inc. Serial Savate System <[( advisory )]>---------------------------------------<[( xxxxxxxxxxx2.adv.en Program: PHPSLASH Homepage: http://www.phpslash.org Author Contacted: 15/apr/2001 Answer: 16/apr/2001 (ajayrockrock) Patch : 16/apr/2001 Version tested: 0.6.1 Found by : tobozo - Problem description: ~~~~~~~~~~~~~~~~~~~~ Url block type can access the filesystem when a path is specified by the administrator. The method used in Block_render_url.class does not check if the $url variable contains a valid url scheme. No parsing is really done to check integrity of the url scheme, neither the content of the url and file name. - Impact: ~~~~~~~ If a path to a file is specified (ex : /etc/passwd), the file will be read and its content stored in the cache exactly as if it was a remote file on a given url. - Exploit: ~~~~~~~~ Login as admin with GOD permissions Access the BLOCKS admin section (blockAdmin.php3) and create a new block with the following information : Title : notTrusted Type : url Site Location : whatever Source URL : ./config.php3 Expire Length : 0 Owned by section : home Data : (empty) Order number : whatever It will display the content of the config.php3 as text in the block of the main page. It might become an issue if blockAdmin.php3 gives add/edit/remove permission to some users that are not supposed to access the filesystem. Fix : ~~~~~ Replace the function parse() in the Block_render_url.class tu use parse_url() and a regex before sending $url to the file() function. function parse($block_info) { $url = $block_info["source_url"]; /* check for url structure before opening it (you don't want /etc/passwd to be validated here -- tobozo -- */ $urlParts = parse_url($url); if( (empty($urlParts)) or (!$urlParts) ) { $this->output = "Block_render_url.class:: Parse error reading [$url]"; return; } $scheme = $urlParts[scheme]; $HostName = $urlParts[host]; if(empty($scheme)) { $this->output = "Block_render_url.class:: Missing protocol declaration [$url]"; return; } if(empty($HostName)){ $this->output = "Block_render_url.class:: No hostname in [$url]"; return; } if (!eregi("^(ht|f)tp",$scheme)) { $this->output = "Block_render_url.class:: No http:// or ftp:// in [$url]"; return; } /* have to silence 'implode' and 'file' because you don't want the errors showing up on the main page */ $ary = @file($url); $size = count($ary); $string = @implode("",$ary); if (strlen($string) < 1) { $this->output = "Block_render_url.class: $url contained no data."; return; }; for ($i = 0 ; $i < $size ; $i++) { $output .= $ary[$i]; }; $this->output = $output; } - Workaround : ~~~~~~~~~~~~ 1) check for all possible protocols 2) check for url content (host) - Code: ~~~~~ Tested on http://assassine.org (successfully) - Contact us: ~~~~~~~~~~~ http://madchat.sourceforge.net tobozo@users.sourceforge.net - Greetings: ~~~~~~~ The phpSlash Team, Gard, Jericho, madteam [EOF]