<?xml version="1.0" encoding="UTF-8"?>
<commit>
  <added type="array">
    <added>
      <filename>application/controllers/json_test.php</filename>
    </added>
    <added>
      <filename>application/controllers/media.php</filename>
    </added>
    <added>
      <filename>application/controllers/scheduler/cluster.php</filename>
    </added>
    <added>
      <filename>application/libraries/Validation.php</filename>
    </added>
    <added>
      <filename>application/models/cluster.php</filename>
    </added>
    <added>
      <filename>application/views/main_test_js.php</filename>
    </added>
    <added>
      <filename>system/libraries/ORM_Versioned.php</filename>
    </added>
    <added>
      <filename>system/libraries/Tagcloud.php</filename>
    </added>
    <added>
      <filename>system/libraries/drivers/Image/GraphicsMagick.php</filename>
    </added>
  </added>
  <modified type="array">
    <modified>
      <diff>@@ -36,6 +36,11 @@ $config['salt_pattern'] = '3, 5, 6, 10, 24, 26, 35, 36, 37, 40';
 $config['lifetime'] = 1209600;
 
 /**
+ * Set the session key that will be used to store the current user.
+ */
+$config['session_key'] = 'auth_user';
+
+/**
  * Usernames (keys) and hashed passwords (values) used by the File driver.
  */
 $config['users'] = array</diff>
      <filename>application/config/auth.php</filename>
    </modified>
    <modified>
      <diff>@@ -5,3 +5,4 @@
  * Sets the default route to &quot;welcome&quot;
  */
 $config['_default'] = 'main';
+$config['feed/atom'] = 'feed/index/atom';
\ No newline at end of file</diff>
      <filename>application/config/routes.php</filename>
    </modified>
    <modified>
      <diff>@@ -55,7 +55,7 @@ class Users_Controller extends Admin_Controller
 	         //  Add some filters
 	        $post-&gt;pre_filter('trim', TRUE);
 			
-			if ($post-&gt;action = 'a') 				// Add/Edit Action
+			if ($post-&gt;action == 'a') 				// Add/Edit Action
 			{
 	        	// Add some rules, the input field, followed by a list of checks, carried out in order
 				$post-&gt;add_rules('username','required','length[3,16]', 'alpha');
@@ -74,20 +74,28 @@ class Users_Controller extends Admin_Controller
 					array($this,'email_exists_chk')) : '';
 					
 				// Validate for roles
-				if ($post-&gt;role != 'admin' &amp;&amp; $post-&gt;role != 'user') {
+				if ($post-&gt;role != 'admin' &amp;&amp; $post-&gt;role != 'login') {
 					$post-&gt;add_error('role', 'values');
 				}
 				
 				// Prevent modification of the admin users role to user role
-				if ($post-&gt;username == 'admin' &amp;&amp; $post-&gt;role == 'user') {
+				if ($post-&gt;username == 'admin' &amp;&amp; $post-&gt;role == 'login') {
 					$post-&gt;add_error('username', 'admin');
 				}
 			}
+			elseif ($post-&gt;action == 'd') 
+			{
+				// Prevent deletion of the admin account
+				if ($post-&gt;username == 'admin') {
+					$post-&gt;add_error('username', 'admin');
+				}
+			}
+			
 			
 			if ($post-&gt;validate())
 	        {
 				$user = ORM::factory('user',$post-&gt;user_id);
-				if ($post-&gt;action = 'a') 				// Add/Edit Action
+				if ($post-&gt;action == 'a') 				// Add/Edit Action
 				{
 					// Existing User??
 					if ($user-&gt;loaded==true)
@@ -101,10 +109,17 @@ class Users_Controller extends Admin_Controller
 						// Remove Old Roles
 						foreach($user-&gt;roles as $role){
 							$user-&gt;remove($role); 
-						} 
+						}
 						
 						// Add New Role
-						$user-&gt;add(ORM::factory('role', $post-&gt;role));
+						if ($post-&gt;role == 'admin') {
+							$user-&gt;add(ORM::factory('role', 'login'));
+							$user-&gt;add(ORM::factory('role', 'admin'));
+						}
+						else
+						{
+							$user-&gt;add(ORM::factory('role', 'login'));
+						}
 						
 						$form_saved = TRUE;
 						$form_action = &quot;EDITED&quot;;
@@ -119,23 +134,30 @@ class Users_Controller extends Admin_Controller
 						$user-&gt;save();
 						
 						// Add New Role
-						$user-&gt;add(ORM::factory('role', $post-&gt;role));
+						if ($post-&gt;role == 'admin') {
+							$user-&gt;add(ORM::factory('role', 'login'));
+							$user-&gt;add(ORM::factory('role', 'admin'));
+						}
+						else
+						{
+							$user-&gt;add(ORM::factory('role', 'login'));
+						}
 						
 						$form_saved = TRUE;
 						$form_action = &quot;ADDED&quot;;
 					}
 				}
-				elseif ($post-&gt;action = 'd')			// Delete Action 
+				elseif ($post-&gt;action == 'd')			// Delete Action 
 				{
 					if ($user-&gt;loaded==true)
 					{
-						// Remove Roles
-						foreach ($user-&gt;roles as $role) {
-							$user-&gt;remove_role($role);
+						// If the user does not exist, redirect
+						if ($user-&gt;loaded)
+						{
+							// Delete the user
+							$user-&gt;delete();
 						}
-						
-						// Delete User
-						$user-&gt;delete($post-&gt;user_id);
+
 						$form_saved = TRUE;
 						$form_action = &quot;DELETED&quot;;
 					}
@@ -172,7 +194,7 @@ class Users_Controller extends Admin_Controller
 		$this-&gt;template-&gt;content-&gt;pagination = $pagination;
 		$this-&gt;template-&gt;content-&gt;total_items = $pagination-&gt;total_items;
 		$this-&gt;template-&gt;content-&gt;users = $users;
-		$this-&gt;template-&gt;content-&gt;roles = array(&quot;admin&quot;=&gt;&quot;admin&quot;,&quot;user&quot;=&gt;&quot;user&quot;);
+		$this-&gt;template-&gt;content-&gt;roles = array(&quot;admin&quot;=&gt;&quot;admin&quot;,&quot;login&quot;=&gt;&quot;login&quot;);
 		
 		// Javascript Header
 		$this-&gt;template-&gt;colorpicker_enabled = TRUE;
@@ -183,8 +205,7 @@ class Users_Controller extends Admin_Controller
 	 * Checks if username already exists.
      * @param Validation $post $_POST variable with validation rules 
 	 */
-    //XXX: Should probably be marked private
-	public function username_exists_chk(Validation $post)
+	private function username_exists_chk(Validation $post)
 	{
 		$users = ORM::factory('user');
 		// If add-&gt;rules validation found any errors, get me out of here!
@@ -199,8 +220,7 @@ class Users_Controller extends Admin_Controller
 	 * Checks if email address is associated with an account.
 	 * @param Validation $post $_POST variable with validation rules 
 	 */
-    //XXX: Should probably be marked private
-	public function email_exists_chk( Validation $post )
+	private function email_exists_chk( Validation $post )
 	{
 		$users = ORM::factory('user');
 		if( array_key_exists('email',$post-&gt;errors()))</diff>
      <filename>application/controllers/admin/users.php</filename>
    </modified>
    <modified>
      <diff>@@ -31,6 +31,7 @@ class Login_Controller extends Template_Controller {
         parent::__construct();
 		
         $this-&gt;session = new Session();
+		// $profiler = new Profiler;
     }
 	
     public function index()</diff>
      <filename>application/controllers/login.php</filename>
    </modified>
    <modified>
      <diff>@@ -17,39 +17,51 @@ class Swatch_Controller extends Controller
 {
 	function index()
 	{
+		// Image Color
 	    if(!isset($_GET['c'])) {
-	        $main_color    = &quot;FFFFFF&quot;;
+	        $main_color    = &quot;990000&quot;;
 	    }
 		else
 		{
 			$main_color     = $_GET['c'];
 		}
 	
-	
-	    if(!isset($_GET['w'])) {
-	        $width = &quot;15&quot;;
+		
+		// Image Width
+	    if(!isset($_GET['w']) || !is_numeric($_GET['w'])) {
+	        $width = &quot;16&quot;;
 	    }
 		else
 		{
 			$width    = $_GET['w'];
 		}
 	
-	    if(!isset($_GET['h'])) {
-	        $height = &quot;15&quot;;
+		// Image Height
+	    if(!isset($_GET['h']) || !is_numeric($_GET['h'])) {
+	        $height = &quot;16&quot;;
 	    }
 		else
 		{
 			$height    = $_GET['h'];
 		}
 	
-	
+		// Image Border Color
 	    if(!isset($_GET['b'])) {
-	        $brdr_color = &quot;000000&quot;;
+	        $brdr_color = &quot;990000&quot;;
 	    }
 		else
 		{
 			$brdr_color    = $_GET['b'];
 		}
+		
+		// Image Type (Circle or Rectangle?)
+		if(!isset($_GET['t']) || ($_GET['t'] != &quot;rec&quot; &amp;&amp; $_GET['t'] != &quot;cir&quot;) ) {
+	        $image_type = &quot;rec&quot;;
+	    }
+		else
+		{
+			$image_type    = $_GET['t'];
+		}
 
 		$mc_red    =    hexdec(substr($main_color, 0, 2));
 		$mc_green    =    hexdec(substr($main_color, 2, 2));
@@ -58,16 +70,42 @@ class Swatch_Controller extends Controller
 		$bc_red    =    hexdec(substr($brdr_color, 0, 2));
 		$bc_green    =    hexdec(substr($brdr_color, 2, 2));
 		$bc_blue    =    hexdec(substr($brdr_color, 4, 2));
-
-		$image    = imagecreate( $width, $height );
-		$main_color    = imagecolorallocate( $image, $mc_red, $mc_green, $mc_blue );
-		$brdr_color    = imagecolorallocate( $image, $bc_red, $bc_green, $bc_blue );
-
-		imagefill( $image, 0, 0, $brdr_color);
-		imagefilledrectangle( $image, 1, 1, ($width-2), ($height-2), $main_color);
 		
+		
+		if ($image_type == 'rec')
+		{
+			$image    	   = imagecreate( $width, $height );
+			$main_color    = imagecolorallocate( $image, $mc_red, $mc_green, $mc_blue );
+			$brdr_color    = imagecolorallocate( $image, $bc_red, $bc_green, $bc_blue );
+			
+			imagefill( $image, 0, 0, $brdr_color);
+			imagefilledrectangle( $image, 1, 1, ($width-2), ($height-2), $main_color);
+		}
+		else
+		{ // Use imagecolorallocatealpha to set transparency level
+			
+			$a = $width;
+			$b = $a*4;
+			$c = $b/2;
+			$d = $b;
+			$e = $d-(2*8);
+			
+			$image    	   = imagecreate( $a, $a );
+			$image2    	   = imagecreate( ($b), ($b) );
+			$main_color    = imagecolorallocatealpha( $image2, $mc_red, $mc_green, $mc_blue, 20 );
+			$brdr_color    = imagecolorallocatealpha( $image2, $bc_red, $bc_green, $bc_blue, 0 );
+			$bkg_color	   = imagecolorallocatealpha($image2, 0, 0, 0, 127);
+			
+			imagefill( $image2, 0, 0, $bkg_color);
+			imagefilledellipse( $image2, $c, $c, $d, $d, $brdr_color);
+			imagefilledellipse( $image2, $c, $c, $e, $e, $main_color);
+			
+			imagecopyresampled($image,$image2,0,0,0,0,$a,$a,$b,$b);
+		}
+		
+		
+		header(&quot;Content-type: image/png&quot;);
 		imagepng($image);
 		imagedestroy($image);
-	
 	}
 }</diff>
      <filename>application/controllers/swatch.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Validation helper class.
  *
- * $Id: valid.php 3238 2008-07-30 15:42:28Z Shadowhand $
- *
- * $Id: valid.php 3238 2008-08-25 10:03:28CST David Kobia $
+ * $Id: valid.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -87,12 +85,15 @@ class valid_Core {
 	 *
 	 * @param   string   IP address
 	 * @param   boolean  allow IPv6 addresses
+	 * @param   boolean  allow private IP networks
 	 * @return  boolean
 	 */
-	public static function ip($ip, $ipv6 = FALSE)
+	public static function ip($ip, $ipv6 = FALSE, $allow_private = TRUE)
 	{
-		// Do not allow private and reserved range IPs
+		// By default do not allow private and reserved range IPs
 		$flags = FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE;
+		if ($allow_private === TRUE)
+			$flags =  FILTER_FLAG_NO_RES_RANGE;
 
 		if ($ipv6 === TRUE)
 			return (bool) filter_var($ip, FILTER_VALIDATE_IP, $flags);
@@ -197,6 +198,17 @@ class valid_Core {
 	}
 
 	/**
+	 * Tests if a string is a valid date string.
+	 * 
+	 * @param   string   date to check
+	 * @return  boolean
+	 */
+	public function date($str)
+	{
+		return (strtotime($str) !== FALSE);
+	}
+
+	/**
 	 * Checks whether a string consists of alphabetical characters only.
 	 *
 	 * @param   string   input string
@@ -255,41 +267,35 @@ class valid_Core {
 	/**
 	 * Checks whether a string is a valid number (negative and decimal numbers allowed).
 	 *
+	 * @see Uses locale conversion to allow decimal point to be locale specific.
+	 * @see http://www.php.net/manual/en/function.localeconv.php
+	 * 
 	 * @param   string   input string
 	 * @return  boolean
 	 */
 	public static function numeric($str)
 	{
-		return (is_numeric($str) AND preg_match('/^[-0-9.]++$/D', (string) $str));
-	}
-
-
-	/**
-	 * Checks whether a string is a valid number (negative and decimal numbers allowed) and between a specified range.
-	 *
-	 * @param   string   input string
-	 * @param   float (MIN/MAX)
-	 * @return  boolean
-	 */
-	public static function between($str, $min_max = array(0,0))
-	{
-		$set_min = $min_max[0];
-		$set_max = $min_max[1];
-		$str = (float) $str;
-		return (is_numeric($str) AND preg_match('/^[-0-9.]++$/D', (string) $str) AND ($str &lt;= $set_max AND $str &gt;= $set_min) );
+		// Use localeconv to set the decimal_point value: Usually a comma or period.
+		$locale = localeconv();
+		return (preg_match('/^[-0-9'.$locale['decimal_point'].']++$/D', (string) $str));
 	}
-	
 
 	/**
 	 * Checks whether a string is a valid text. Letters, numbers, whitespace,
 	 * dashes, periods, and underscores are allowed.
 	 *
-	 * @param   string   $str
+	 * @param   string   text to check
 	 * @return  boolean
 	 */
 	public static function standard_text($str)
 	{
-		return (bool) preg_match('/^[-\pL\pN\pZ_.]++$/uD', (string) $str);
+		// pL matches letters
+		// pN matches numbers
+		// pZ matches whitespace
+		// pPc matches underscores
+		// pPd matches dashes
+		// pPo matches normal puncuation
+		return (bool) preg_match('/^[\pL\pN\pZ\p{Pc}\p{Pd}\p{Po}]++$/uD', (string) $str);
 	}
 
 	/**
@@ -329,6 +335,20 @@ class valid_Core {
 		return (bool) preg_match($pattern, (string) $str);
 	}
 	
+	/**
+	 * Checks whether a string is a valid number (negative and decimal numbers allowed) and between a specified range.
+	 *
+	 * @param   string   input string
+	 * @param   float (MIN/MAX)
+	 * @return  boolean
+	 */
+	public static function between($str, $min_max = array(0,0))
+	{
+		$set_min = $min_max[0];
+		$set_max = $min_max[1];
+		$str = (float) $str;
+		return (is_numeric($str) AND preg_match('/^[-0-9.]++$/D', (string) $str) AND ($str &lt;= $set_max AND $str &gt;= $set_min) );
+	}
 	
 	/**
 	 * Checks whether a string is a valid date (mm/dd/yyyy).</diff>
      <filename>application/helpers/valid.php</filename>
    </modified>
    <modified>
      <diff>@@ -3,37 +3,37 @@
 &lt;head&gt;
 	&lt;meta http-equiv=&quot;Content-Type&quot; content=&quot;text/html; charset=utf-8&quot; /&gt;
 	&lt;title&gt;UshahidiEngine&lt;/title&gt;
-	&lt;style type=&quot;text/css&quot; media=&quot;all&quot; &gt;@import &quot;&lt;?php echo url::base() ?&gt;media/css/admin/all.css&quot;;&lt;/style&gt;
-	&lt;!--[if lt IE 7]&gt;&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;media/css/admin/ie6.css&quot; media=&quot;screen&quot;/&gt;&lt;![endif]--&gt;
-	&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;media/css/datepicker/ui.datepicker.css&quot; media=&quot;screen&quot;/&gt;
+	&lt;style type=&quot;text/css&quot; media=&quot;all&quot; &gt;@import &quot;&lt;?php echo url::base() ?&gt;index.php/media/css/admin/all.css&quot;;&lt;/style&gt;
+	&lt;!--[if lt IE 7]&gt;&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;index.php/media/css/admin/ie6.css&quot; media=&quot;screen&quot;/&gt;&lt;![endif]--&gt;
+	&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;index.php/media/css/datepicker/ui.datepicker.css&quot; media=&quot;screen&quot;/&gt;
 	&lt;?php
 	
 	// Load OpenLayers
 	if ($map_enabled)
 	{
-		echo html::script('media/js/OpenLayers/OpenLayers');
+		echo html::script('index.php/media/js/OpenLayers/OpenLayers');
 		echo $api_url . &quot;\n&quot;;
 	}
 	
 	// Load jQuery
-	echo html::script('media/js/jquery');
-	echo html::script('media/js/jquery.form');
-	echo html::script('media/js/jquery.validate.min');
-	echo html::script('media/js/jquery.ui.min');
+	echo html::script('index.php/media/js/jquery');
+	echo html::script('index.php/media/js/jquery.form');
+	echo html::script('index.php/media/js/jquery.validate.min');
+	echo html::script('index.php/media/js/jquery.ui.min');
 	
 	// Load Flot
 	if ($flot_enabled)
 	{
-		echo html::script('media/js/jquery.flot');
-		echo html::script('media/js/excanvas.pack');
-		echo html::script('media/js/timeline.js');
+		echo html::script('index.php/media/js/jquery.flot');
+		echo html::script('index.php/media/js/excanvas.pack');
+		echo html::script('index.php/media/js/timeline.js');
 	}
 	
 	// Load ColorPicker
 	if ($colorpicker_enabled)
 	{
-		echo html::stylesheet('media/css/colorpicker');
-		echo html::script('media/js/colorpicker');
+		echo html::stylesheet('index.php/media/css/colorpicker');
+		echo html::script('index.php/media/js/colorpicker');
 	}
 	?&gt;
 	&lt;script type=&quot;text/javascript&quot; charset=&quot;utf-8&quot;&gt;</diff>
      <filename>application/views/admin/layout.php</filename>
    </modified>
    <modified>
      <diff>@@ -26,7 +26,5 @@
 				// Submit Form
 				$(&quot;#userMain&quot;).submit();			
 
-			} else{
-				return false;
 			}
 		}
\ No newline at end of file</diff>
      <filename>application/views/admin/users_js.php</filename>
    </modified>
    <modified>
      <diff>@@ -3,52 +3,52 @@
 &lt;head&gt;
 	&lt;meta http-equiv=&quot;Content-Type&quot; content=&quot;text/html; charset=utf-8&quot; /&gt;
 	&lt;title&gt;&lt;?php echo $site_name; ?&gt;&lt;/title&gt;
-	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;media/css/all.css&quot;;&lt;/style&gt;
-	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;media/css/photoslider.css&quot;;&lt;/style&gt;
-	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;media/css/videoslider.css&quot;;&lt;/style&gt;
-	&lt;!--[if lt IE 7]&gt;&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;/media/css/ie6.css&quot; media=&quot;screen&quot;/&gt;&lt;![endif]--&gt;
+	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;index.php/media/css/all.css&quot;;&lt;/style&gt;
+	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;index.php/media/css/photoslider.css&quot;;&lt;/style&gt;
+	&lt;style media=&quot;all&quot; type=&quot;text/css&quot;&gt;@import &quot;&lt;?php echo url::base() ?&gt;index.php/media/css/videoslider.css&quot;;&lt;/style&gt;
+	&lt;!--[if lt IE 7]&gt;&lt;link rel=&quot;stylesheet&quot; type=&quot;text/css&quot; href=&quot;&lt;?php echo url::base() ?&gt;index.php/media/css/ie6.css&quot; media=&quot;screen&quot;/&gt;&lt;![endif]--&gt;
 	&lt;?php
 	// Load OpenLayers before jQuery!
 	if ($map_enabled)
 	{
-		echo html::script('media/js/OpenLayers/OpenLayers');
+		echo html::script('index.php/media/js/OpenLayers/OpenLayers');
 		// OpenLayers Theme
-		echo html::stylesheet('media/js/OpenLayers/theme/default/style');
+		echo html::stylesheet('index.php/media/js/OpenLayers/theme/default/style');
 	}	
 	
 	// Load jQuery
-	echo html::script('media/js/jquery');
-	echo html::script('media/js/jquery.ui.min');
+	echo html::script('index.php/media/js/jquery');
+	echo html::script('index.php/media/js/jquery.ui.min');
 	
 	// Other stuff to load only we have the map enabled
 	if ($map_enabled)
 	{
 		echo $api_url . &quot;\n&quot;;
 		if ($main_page) {
-			echo html::script('media/js/accessibleUISlider.jQuery');
-			echo html::script('media/js/jquery.flot');
-			echo html::script('media/js/timeline.js');
+			echo html::script('index.php/media/js/accessibleUISlider.jQuery');
+			echo html::script('index.php/media/js/jquery.flot');
+			echo html::script('index.php/media/js/timeline.js');
 			?&gt;
 			&lt;!--[if IE]&gt;&lt;script language=&quot;javascript&quot; type=&quot;text/javascript&quot; src=&quot;&lt;?php echo url::base() ?&gt;media/js/excanvas.pack.js&quot;&gt;&lt;/script&gt;&lt;![endif]--&gt;
 			&lt;?php
-			echo html::stylesheet('media/css/jquery-ui-themeroller');
+			echo html::stylesheet('index.php/media/css/jquery-ui-themeroller');
 		}
 	}
 	if ($validator_enabled) 
 	{
-		echo html::script('media/js/jquery.validate.min');
+		echo html::script('index.php/media/js/jquery.validate.min');
 	}
 	if ($datepicker_enabled)
 	{
-		echo html::stylesheet('media/css/datepicker/ui.datepicker');
+		echo html::stylesheet('index.php/media/css/datepicker/ui.datepicker');
 	}
 	if ($photoslider_enabled)
 	{
-		echo html::script('media/js/photoslider.js');
+		echo html::script('index.php/media/js/photoslider.js');
 	}
 	if( $videoslider_enabled )
 	{
-		echo html::script('media/js/coda-slider.pack.js');
+		echo html::script('index.php/media/js/coda-slider.pack.js');
 	}
 	if ($allow_feed == 1) {
 		echo &quot;&lt;link rel=\&quot;alternate\&quot; type=\&quot;application/rss+xml\&quot; href=\&quot;http://&quot; . $_SERVER['SERVER_NAME'] . &quot;/feed/\&quot; title=\&quot;RSS2\&quot; /&gt;&quot;;</diff>
      <filename>application/views/header.php</filename>
    </modified>
    <modified>
      <diff>@@ -48,7 +48,6 @@
 	
 			map.addControl(new OpenLayers.Control.Navigation());
 			map.addControl(new OpenLayers.Control.PanZoomBar());
-			map.addControl(new OpenLayers.Control.Attribution());
 			map.addControl(new OpenLayers.Control.MousePosition());
 			map.addControl(new OpenLayers.Control.LayerSwitcher());
 			</diff>
      <filename>application/views/reports_view_js.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Auth library configuration. By default, Auth will use the controller
  * database connection. If Database is not loaded, it will use use the default
@@ -9,7 +9,7 @@
  */
 
 /**
- * Driver to use for authentication. By default, file and ORM are available.
+ * Driver to use for authentication. By default, LDAP and ORM are available.
  */
 $config['driver'] = 'ORM';
 
@@ -17,7 +17,6 @@ $config['driver'] = 'ORM';
  * Type of hash to use for passwords. Any algorithm supported by the hash function
  * can be used here. Note that the length of your password is determined by the
  * hash type + the number of salt characters.
- * Note: This is unrelated to the hash settings in the Openid library.
  * @see http://php.net/hash
  * @see http://php.net/hash_algos
  */
@@ -26,9 +25,8 @@ $config['hash_method'] = 'sha1';
 /**
  * Defines the hash offsets to insert the salt at. The password hash length
  * will be increased by the total number of offsets.
- * *** YOU SHOULD PERSONALISE THIS ***
  */
-$config['salt_pattern'] = '3, 5, 6, 10, 24, 26, 35, 36, 37, 40';
+$config['salt_pattern'] = '1, 3, 5, 9, 14, 15, 20, 21, 28, 30';
 
 /**
  * Set the auto-login (remember me) cookie lifetime, in seconds. The default
@@ -37,9 +35,15 @@ $config['salt_pattern'] = '3, 5, 6, 10, 24, 26, 35, 36, 37, 40';
 $config['lifetime'] = 1209600;
 
 /**
+ * Set the session key that will be used to store the current user.
+ */
+$config['session_key'] = 'auth_user';
+
+/**
  * Usernames (keys) and hashed passwords (values) used by the File driver.
+ * Default admin password is &quot;admin&quot;. You are encouraged to change this.
  */
 $config['users'] = array
 (
-	// 'admin' =&gt; '4ccd0e25c2a7ffefd4b92ecbbd4781752920145f826a881073',
-);
+	// 'admin' =&gt; 'b3154acf3a344170077d11bdb5fff31532f679a1919e716a02',
+);
\ No newline at end of file</diff>
      <filename>modules/auth/config/auth.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,11 +1,11 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * User authorization library. Handles user login and logout, as well as secure
  * password hashing.
  *
  * @package    Auth
  * @author     Kohana Team
- * @copyright  (c) 2007-2008 Kohana Team
+ * @copyright  (c) 2007 Kohana Team
  * @license    http://kohanaphp.com/license.html
  */
 class Auth_Core {
@@ -49,10 +49,10 @@ class Auth_Core {
 	public function __construct($config = array())
 	{
 		// Append default auth configuration
-		$config += KOHANA::config('auth');
+		$config += Kohana::config('auth');
 
 		// Clean up the salt pattern and split it into an array
-		$config['salt_pattern'] = preg_split('/,\s*/', KOHANA::config('auth.salt_pattern'));
+		$config['salt_pattern'] = preg_split('/,\s*/', Kohana::config('auth.salt_pattern'));
 
 		// Save the config in the object
 		$this-&gt;config = $config;
@@ -88,6 +88,16 @@ class Auth_Core {
 	}
 
 	/**
+	 * Returns the currently logged in user, or FALSE.
+	 *
+	 * @return  mixed
+	 */
+	public function get_user()
+	{
+		return $this-&gt;driver-&gt;get_user();
+	}
+
+	/**
 	 * Attempt to log in a user by using an ORM object and plain-text password.
 	 *
 	 * @param   string   username to log in
@@ -136,7 +146,7 @@ class Auth_Core {
 	/**
 	 * Log out a user by removing the related session variables.
 	 *
-	 * @param   boolean   completely destroy the session
+	 * @param   boolean  completely destroy the session
 	 * @return  boolean
 	 */
 	public function logout($destroy = FALSE)
@@ -148,11 +158,8 @@ class Auth_Core {
 	 * Creates a hashed password from a plaintext password, inserting salt
 	 * based on the configured salt pattern.
 	 *
-	 * Parameters:
-	 *  password - plaintext password
-	 *
-	 * Returns:
-	 *  Hashed password string
+	 * @param   string  plaintext password
+	 * @return  string  hashed password string
 	 */
 	public function hash_password($password, $salt = FALSE)
 	{
@@ -196,10 +203,10 @@ class Auth_Core {
 	/**
 	 * Perform a hash, using the configured method.
 	 *
-	 * @param   string   string to hash
+	 * @param   string  string to hash
 	 * @return  string
 	 */
-	protected function hash($str)
+	public function hash($str)
 	{
 		return hash($this-&gt;config['hash_method'], $str);
 	}
@@ -210,13 +217,13 @@ class Auth_Core {
 	 * @param   string  hashed password
 	 * @return  string
 	 */
-	protected function find_salt($password)
+	public function find_salt($password)
 	{
 		$salt = '';
 
 		foreach ($this-&gt;config['salt_pattern'] as $i =&gt; $offset)
 		{
-			// Find salt characters... take a good long look..
+			// Find salt characters, take a good long look...
 			$salt .= substr($password, $offset + $i, 1);
 		}
 </diff>
      <filename>modules/auth/libraries/Auth.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,24 +1,63 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
- * Auth driver interface.
+ * Abstract Auth driver, must be extended by all drivers.
  *
- * $Id: Auth.php 2482 2008-04-12 16:48:50Z Shadowhand $
+ * $Id: Auth.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Auth
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
  * @license    http://kohanaphp.com/license.html
  */
-interface Auth_Driver {
+abstract class Auth_Driver {
 
-   /**
-	 * Checks if a user session is active. Optionally allows checking for a
-	 * specific role.
+	// Session instance
+	protected $session;
+
+	// Configuration
+	protected $config;
+
+	/**
+	 * Creates a new driver instance, loading the session and storing config.
 	 *
-	 * @param   string    role name
+	 * @param   array  configuration
+	 * @return  void
+	 */
+	public function __construct(array $config)
+	{
+		// Load Session
+		$this-&gt;session = Session::instance();
+
+		// Store config
+		$this-&gt;config = $config;
+	}
+
+	/**
+	 * Checks if a session is active.
+	 *
+	 * @param   string   role name (not supported)
 	 * @return  boolean
 	 */
-	public function logged_in($role);
+	public function logged_in($role)
+	{
+		return isset($_SESSION[$this-&gt;config['session_key']]);
+	}
+
+	/**
+	 * Gets the currently logged in user from the session.
+	 * Returns FALSE if no user is currently logged in.
+	 *
+	 * @return  mixed
+	 */
+	public function get_user()
+	{
+		if ($this-&gt;logged_in(NULL))
+		{
+			return $_SESSION[$this-&gt;config['session_key']];
+		}
+
+		return FALSE;
+	}
 
 	/**
 	 * Logs a user in.
@@ -28,37 +67,76 @@ interface Auth_Driver {
 	 * @param   boolean  enable auto-login
 	 * @return  boolean
 	 */
-	public function login($username, $password, $remember);
+	abstract public function login($username, $password, $remember);
 
 	/**
-	 * Logs a user in, based on stored credentials, typically cookies.
+	 * Forces a user to be logged in, without specifying a password.
 	 *
+	 * @param   mixed    username
 	 * @return  boolean
 	 */
-	public function auto_login();
+	abstract public function force_login($username);
 
 	/**
-	 * Forces a user login, without needing to specify a password.
+	 * Logs a user in, based on stored credentials, typically cookies.
+	 * Not supported by default.
 	 *
-	 * @param   mixed    username
 	 * @return  boolean
 	 */
-	public function force_login($username);
+	public function auto_login()
+	{
+		return FALSE;
+	}
 
 	/**
 	 * Log a user out.
 	 *
-	 * @param   boolean   completely destroy the session - also delete authautologin cookie
+	 * @param   boolean  completely destroy the session
 	 * @return  boolean
 	 */
-	public function logout($destroy);
+	public function logout($destroy)
+	{
+		if ($destroy === TRUE)
+		{
+			// Destroy the session completely
+			Session::instance()-&gt;destroy();
+		}
+		else
+		{
+			// Remove the user from the session
+			$this-&gt;session-&gt;delete($this-&gt;config['session_key']);
+
+			// Regenerate session_id
+			$this-&gt;session-&gt;regenerate();
+		}
+
+		// Double check
+		return ! $this-&gt;logged_in(NULL);
+	}
 
 	/**
 	 * Get the stored password for a username.
 	 *
-	 * @param   mixed   user object or username string
+	 * @param   mixed   username
 	 * @return  string
 	 */
-	public function password($username);
+	abstract public function password($username);
+
+	/**
+	 * Completes a login by assigning the user to the session key.
+	 *
+	 * @param   string   username
+	 * @return  TRUE
+	 */
+	protected function complete_login($user)
+	{
+		// Regenerate session_id
+		$this-&gt;session-&gt;regenerate();
+
+		// Store username in session
+		$_SESSION[$this-&gt;config['session_key']] = $user;
+
+		return TRUE;
+	}
 
-} // End Auth_Driver Interface
\ No newline at end of file
+} // End Auth_Driver
\ No newline at end of file</diff>
      <filename>modules/auth/libraries/drivers/Auth.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,33 +1,29 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * File Auth driver.
  * Note: this Auth driver does not support roles nor auto-login.
  *
- * $Id: File.php 3114 2008-07-15 21:11:44Z Geert $
+ * $Id: File.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Auth
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
  * @license    http://kohanaphp.com/license.html
  */
-class Auth_File_Driver implements Auth_Driver {
+class Auth_File_Driver extends Auth_Driver {
 
 	// User list
 	protected $users;
 
-	// Session instance
-	protected $session;
-
 	/**
 	 * Constructor loads the user list into the class.
 	 */
 	public function __construct(array $config)
 	{
+		parent::__construct($config);
+
 		// Load user list
 		$this-&gt;users = empty($config['users']) ? array() : $config['users'];
-
-		// Load Session
-		$this-&gt;session = Session::instance();
 	}
 
 	/**
@@ -40,16 +36,10 @@ class Auth_File_Driver implements Auth_Driver {
 	 */
 	public function login($username, $password, $remember)
 	{
-		// Validate username/password combination
 		if (isset($this-&gt;users[$username]) AND $this-&gt;users[$username] === $password)
 		{
-			// Regenerate session_id
-			$this-&gt;session-&gt;regenerate();
-
-			// Store username in session
-			$_SESSION['auth_user'] = $username;
-
-			return TRUE;
+			// Complete the login
+			return $this-&gt;complete_login($username);
 		}
 
 		// Login failed
@@ -64,60 +54,8 @@ class Auth_File_Driver implements Auth_Driver {
 	 */
 	public function force_login($username)
 	{
-		// Regenerate session_id
-		$this-&gt;session-&gt;regenerate();
-
-		// Store username in session
-		$_SESSION['auth_user'] = $username;
-
-		return TRUE;
-	}
-
-	/**
-	 * Logs a user in, based on stored credentials. (not supported)
-	 *
-	 * @return  boolean
-	 */
-	public function auto_login()
-	{
-		return FALSE;
-	}
-
-	/**
-	 * Log a user out.
-	 *
-	 * @param   boolean  completely destroy the session
-	 * @return  boolean
-	 */
-	public function logout($destroy)
-	{
-		if ($destroy === TRUE)
-		{
-			// Destroy the session completely
-			Session::instance()-&gt;destroy();
-		}
-		else
-		{
-			// Remove the user session
-			unset($_SESSION['auth_user']);
-
-			// Regenerate session_id
-			$this-&gt;session-&gt;regenerate();
-		}
-
-		// Double check
-		return ! $this-&gt;logged_in(NULL);
-	}
-
-	/**
-	 * Checks if a session is active.
-	 *
-	 * @param   string   role name (not supported)
-	 * @return  boolean
-	 */
-	public function logged_in($role)
-	{
-		return isset($_SESSION['auth_user']);
+		// Complete the login
+		return $this-&gt;complete_login($username);
 	}
 
 	/**
@@ -128,7 +66,7 @@ class Auth_File_Driver implements Auth_Driver {
 	 */
 	public function password($username)
 	{
-		return (isset($this-&gt;users[$username])) ? $this-&gt;users[$username] : FALSE;
+		return isset($this-&gt;users[$username]) ? $this-&gt;users[$username] : FALSE;
 	}
 
-} // End Auth_File_Driver Class
\ No newline at end of file
+} // End Auth_File_Driver
\ No newline at end of file</diff>
      <filename>modules/auth/libraries/drivers/Auth/File.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,71 +1,93 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * ORM Auth driver.
  *
- * $Id: ORM.php 3114 2008-07-15 21:11:44Z Geert $
- * $Id: ORM.php 3352 2008-08-18 09:43:56BST atomless $
+ * $Id: ORM.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Auth
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
  * @license    http://kohanaphp.com/license.html
  */
-class Auth_ORM_Driver implements Auth_Driver {
-
-	protected $config;
-
-	// Session library
-	protected $session;
+class Auth_ORM_Driver extends Auth_Driver {
 
 	/**
-	 * Constructor. Loads the Session instance.
+	 * Checks if a session is active.
 	 *
-	 * @return  void
+	 * @param   string   role name
+	 * @param   array    collection of role names
+	 * @return  boolean
 	 */
-	public function __construct(array $config)
-	{
-		// Load config
-		$this-&gt;config = $config;
-
-		// Load libraries
-		$this-&gt;session = Session::instance();
-	}
-
 	public function logged_in($role)
 	{
 		$status = FALSE;
 
-		$authuser = $this-&gt;session-&gt;get('auth_user', FALSE);
+		// Get the user from the session
+		$user = $this-&gt;session-&gt;get($this-&gt;config['session_key']);
 
-		// Checks if a user is logged in and valid
-		if ( ! empty($authuser)
-			 AND is_object($authuser)
-			 AND ($authuser instanceof User_Model)
-			 AND $authuser-&gt;loaded)
+		if (is_object($user) AND $user instanceof User_Model AND $user-&gt;loaded)
 		{
 			// Everything is okay so far
 			$status = TRUE;
 
 			if ( ! empty($role))
 			{
-				// Check that the user has the given role
-				$status = $authuser-&gt;has(new Role_Model($role));
+
+				// If role is an array
+				if (is_array($role))
+				{
+					// Check each role
+					foreach ($role as $role_iteration)
+					{
+						if ( ! is_object($role_iteration))
+						{
+							$role_iteration = ORM::factory('role', $role_iteration);
+						}
+						// If the user doesn't have the role
+						if( ! $user-&gt;has($role_iteration))
+						{
+							// Set the status false and get outta here
+							$status = FALSE;
+							break;
+						}
+					}
+				}
+				else
+				{
+				// Else just check the one supplied roles
+					if ( ! is_object($role))
+					{
+						// Load the role
+						$role = ORM::factory('role', $role);
+					}
+
+					// Check that the user has the given role
+					$status = $user-&gt;has($role);
+				}
 			}
 		}
 
 		return $status;
 	}
 
+	/**
+	 * Logs a user in.
+	 *
+	 * @param   string   username
+	 * @param   string   password
+	 * @param   boolean  enable auto-login
+	 * @return  boolean
+	 */
 	public function login($user, $password, $remember)
 	{
 		if ( ! is_object($user))
 		{
-			// Load the user if only username was passed
+			// Load the user
 			$user = ORM::factory('user', $user);
 		}
 
 		// If the passwords match, perform a login
-		if ($user-&gt;has(new Role_Model('login')) AND $user-&gt;password === $password)
+		if ($user-&gt;has(ORM::factory('role', 'login')) AND $user-&gt;password === $password)
 		{
 			if ($remember === TRUE)
 			{
@@ -77,7 +99,7 @@ class Auth_ORM_Driver implements Auth_Driver {
 				$token-&gt;expires = time() + $this-&gt;config['lifetime'];
 				$token-&gt;save();
 
-				// Set the autologin cookie - links to user_token in the db
+				// Set the autologin cookie
 				cookie::set('authautologin', $token-&gt;token, $this-&gt;config['lifetime']);
 			}
 
@@ -91,6 +113,32 @@ class Auth_ORM_Driver implements Auth_Driver {
 		return FALSE;
 	}
 
+	/**
+	 * Forces a user to be logged in, without specifying a password.
+	 *
+	 * @param   mixed    username
+	 * @return  boolean
+	 */
+	public function force_login($user)
+	{
+		if ( ! is_object($user))
+		{
+			// Load the user
+			$user = ORM::factory('user', $user);
+		}
+
+		// Mark the session as forced, to prevent users from changing account information
+		$_SESSION['auth_forced'] = TRUE;
+
+		// Run the standard completion
+		$this-&gt;complete_login($user);
+	}
+
+	/**
+	 * Logs a user in, based on the authautologin cookie.
+	 *
+	 * @return  boolean
+	 */
 	public function auto_login()
 	{
 		if ($token = cookie::get('authautologin'))
@@ -98,7 +146,7 @@ class Auth_ORM_Driver implements Auth_Driver {
 			// Load the token and user
 			$token = ORM::factory('user_token', $token);
 
-			if ($token-&gt;id &gt; 0 AND $token-&gt;user-&gt;id &gt; 0)
+			if ($token-&gt;loaded AND $token-&gt;user-&gt;loaded)
 			{
 				if ($token-&gt;user_agent === sha1(Kohana::$user_agent))
 				{
@@ -123,44 +171,29 @@ class Auth_ORM_Driver implements Auth_Driver {
 		return FALSE;
 	}
 
-	public function force_login($user)
-	{
-		if ( ! is_object($user))
-		{
-			// Load the user
-			$user = ORM::factory('user', $user);
-		}
-
-		// Mark the session as forced, to prevent users from changing account information
-		$this-&gt;session-&gt;set('auth_forced', TRUE);
-
-		// Run the standard completion
-		$this-&gt;complete_login($user);
-	}
-
+	/**
+	 * Log a user out and remove any auto-login cookies.
+	 *
+	 * @param   boolean  completely destroy the session
+	 * @return  boolean
+	 */
 	public function logout($destroy)
 	{
-		// Delete the autologin cookie if it exists
-		cookie::get('authautologin') and cookie::delete('authautologin');
-
-		if ($destroy === TRUE)
-		{
-			// Destroy the session completely
-			Session::instance()-&gt;destroy();
-		}
-		else
+		if (cookie::get('authautologin'))
 		{
-			// Remove the user object from the session
-			$this-&gt;session-&gt;delete('auth_user');
-
-			// Regenerate session_id
-			$this-&gt;session-&gt;regenerate();
+			// Delete the autologin cookie to prevent re-login
+			cookie::delete('authautologin');
 		}
 
-		// Double check
-		return ! $this-&gt;session-&gt;get('auth_user', FALSE);
+		return parent::logout($destroy);
 	}
 
+	/**
+	 * Get the stored password for a username.
+	 *
+	 * @param   mixed   username
+	 * @return  string
+	 */
 	public function password($user)
 	{
 		if ( ! is_object($user))
@@ -172,6 +205,13 @@ class Auth_ORM_Driver implements Auth_Driver {
 		return $user-&gt;password;
 	}
 
+	/**
+	 * Complete the login for a user by incrementing the logins and setting
+	 * session data: user_id, username, roles
+	 *
+	 * @param   object   user model object
+	 * @return  void
+	 */
 	protected function complete_login(User_Model $user)
 	{
 		// Update the number of logins
@@ -183,11 +223,7 @@ class Auth_ORM_Driver implements Auth_Driver {
 		// Save the user
 		$user-&gt;save();
 
-		// Regenerate session_id
-		$this-&gt;session-&gt;regenerate();
-
-		// Store session data
-		$this-&gt;session-&gt;set('auth_user', $user);
+		return parent::complete_login($user);
 	}
 
-} // End Auth_Orm_Driver Class
\ No newline at end of file
+} // End Auth_ORM_Driver
\ No newline at end of file</diff>
      <filename>modules/auth/libraries/drivers/Auth/ORM.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,14 +1,27 @@
-&lt;?php
-/**
- * Model for roles for the Auth Module
- *
- * $Id: auth_role.php 3352 2008-08-18 09:43:56BST atomless $
- */
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+
 class Auth_Role_Model extends ORM {
 
 	protected $has_and_belongs_to_many = array('users');
 
 	/**
+	 * Validates and optionally saves a role record from an array.
+	 *
+	 * @param  array    values to check
+	 * @param  boolean  save the record when validation succeeds
+	 * @return boolean
+	 */
+	public function validate(array &amp; $array, $save = FALSE)
+	{
+		$array = Validation::factory($array)
+			-&gt;pre_filter('trim')
+			-&gt;add_rules('name', 'required', 'length[4,32]')
+			-&gt;add_rules('description', 'length[0,255]');
+
+		return parent::validate($array, $save);
+	}
+
+	/**
 	 * Allows finding roles by name.
 	 */
 	public function unique_key($id)
@@ -21,4 +34,4 @@ class Auth_Role_Model extends ORM {
 		return parent::unique_key($id);
 	}
 
-} // End Role_Model
\ No newline at end of file
+} // End Auth Role Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/auth_role.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,110 +1,155 @@
-&lt;?php
-/**
- * Model for users for the Auth Module
- *
- * $Id: auth_user_model.php 3352 2008-08-18 09:43:56BST atomless $
- */
-class Auth_User_Model extends ORM {
-
-	// Relationships
-	protected $has_many = array('user_tokens');
-	protected $has_and_belongs_to_many = array('roles');
-
-	public function __set($key, $value)
-	{
-		if ($key === 'password')
-		{
-			// Use Auth to hash the password
-			$value = Auth::instance()-&gt;hash_password($value);
-		}
-
-		parent::__set($key, $value);
-	}
-
-	/**
-	 * Used instead of the __set method ($user-&gt;password=x) to avoid double hashing of password.
-	 * For example when confirming pending_user.
-	 *
-	 * @param String   pre-hashed password string
-	 * @return void
-	 */
-	public function set_prehashed_password($value)
-	{
-		parent::__set('password', $value);
-	}
-
-	/**
-	 * Tests if a user already exists in the database by checking
-	 * submitted data against any db fields with type set to unique.
-	 * NOTE: Only tested with the mysql db driver.
-	 *
-	 * @param   string   array of key value pairs to check
-	 * @param   Validation Object  *Optional - enables adding of relevant errors to the
-	 * 								validation object's errors array.
-	 * @return  bool
-	 *
-	 */
-	public function exists($user_data_array, $validation_object = FALSE)
-	{
-		$userexists = FALSE;
-
-		foreach($this-&gt;db-&gt;field_data($this-&gt;table_name) as $column)
-		{
-			if ($column-&gt;Key=='UNI')
-			{
-				if (array_key_exists($column-&gt;Field, $user_data_array))
-				{
-					if ($this-&gt;db-&gt;where($column-&gt;Field, $user_data_array[$column-&gt;Field])-&gt;count_records($this-&gt;table_name) &gt; 0)
-					{
-						if (get_Class($validation_object) == 'Validation')
-						{
-							// Add already exists errors to the referenced POST validation error array
-							$validation_object-&gt;add_error($column-&gt;Field, 'exists');
-						}
-
-						$userexists = TRUE;
-					}
-				}
-			}
-		}
-		return $userexists;
-	}
-
-	/**
-	 * Tests if a user email already exists in the database.
-	 *
-	 * @param   string   email to check
-	 * @return  bool
-	 */
-	public function email_exists($email)
-	{
-		return (bool) $this-&gt;db-&gt;where('email', $email)-&gt;count_records($this-&gt;table_name);
-	}
-
-	/**
-	 * Tests if a username already exists in the database.
-	 *
-	 * @param   string   username to check
-	 * @return  bool
-	 */
-	public function username_exists($name)
-	{
-		return (bool) $this-&gt;db-&gt;where('username', $name)-&gt;count_records($this-&gt;table_name);
-	}
-
-	/**
-	 * Allows a model to be loaded by username or email address.
-	 *
-	 * @param   string   database table field name
-	 * @return  string
-	 */
-	public function unique_key($id)
-	{
-		if ( ! empty($id) AND is_string($id) AND ! ctype_digit($id))
-		{
-			return valid::email($id) ? 'email' : 'username';
-		}
-
-		return parent::unique_key($id);
-	}
-}
\ No newline at end of file
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+
+class Auth_User_Model extends ORM {
+
+	// Relationships
+	protected $has_many = array('user_tokens');
+	protected $has_and_belongs_to_many = array('roles');
+
+	// Columns to ignore
+	protected $ignored_columns = array('password_confirm');
+
+	public function __set($key, $value)
+	{
+		if ($key === 'password')
+		{
+			// Use Auth to hash the password
+			$value = Auth::instance()-&gt;hash_password($value);
+		}
+
+		parent::__set($key, $value);
+	}
+
+	/**
+	 * Validates and optionally saves a new user record from an array.
+	 *
+	 * @param  array    values to check
+	 * @param  boolean  save the record when validation succeeds
+	 * @return boolean
+	 */
+	public function validate(array &amp; $array, $save = FALSE)
+	{
+		$array = Validation::factory($array)
+			-&gt;pre_filter('trim')
+			-&gt;add_rules('email', 'required', 'length[4,127]', 'valid::email')
+			-&gt;add_rules('username', 'required', 'length[4,32]', 'chars[a-zA-Z0-9_.]', array($this, 'username_exists'))
+			-&gt;add_rules('password', 'required', 'length[5,42]')
+			-&gt;add_rules('password_confirm', 'matches[password]');
+
+		return parent::validate($array, $save);
+	}
+
+	/**
+	 * Validates login information from an array, and optionally redirects
+	 * after a successful login.
+	 *
+	 * @param  array    values to check
+	 * @param  string   URI or URL to redirect to
+	 * @return boolean
+	 */
+	public function login(array &amp; $array, $redirect = FALSE)
+	{
+		$array = Validation::factory($array)
+			-&gt;pre_filter('trim')
+			-&gt;add_rules('username', 'required', 'length[4,127]')
+			-&gt;add_rules('password', 'required', 'length[5,42]');
+
+		// Login starts out invalid
+		$status = FALSE;
+
+		if ($array-&gt;validate())
+		{
+			// Attempt to load the user
+			$this-&gt;find($array['username']);
+
+			if ($this-&gt;loaded AND Auth::instance()-&gt;login($this, $array['password']))
+			{
+				if (is_string($redirect))
+				{
+					// Redirect after a successful login
+					url::redirect($redirect);
+				}
+
+				// Login is successful
+				$status = TRUE;
+			}
+			else
+			{
+				$array-&gt;add_error('username', 'invalid');
+			}
+		}
+
+		return $status;
+	}
+
+	/**
+	 * Validates an array for a matching password and password_confirm field.
+	 *
+	 * @param  array    values to check
+	 * @param  string   save the user if
+	 * @return boolean
+	 */
+	public function change_password(array &amp; $array, $save = FALSE)
+	{
+		$array = Validation::factory($array)
+			-&gt;pre_filter('trim')
+			-&gt;add_rules('password', 'required', 'length[5,127]')
+			-&gt;add_rules('password_confirm', 'matches[password]');
+
+		if ($status = $array-&gt;validate())
+		{
+			// Change the password
+			$this-&gt;password = $array['password'];
+
+			if ($save !== FALSE AND $status = $this-&gt;save())
+			{
+				if (is_string($save))
+				{
+					// Redirect to the success page
+					url::redirect($save);
+				}
+			}
+		}
+
+		return $status;
+	}
+
+	/**
+	 * Tests if a user email already exists in the database.
+	 *
+	 * @param   string   email to check
+	 * @return  bool
+	 */
+	public function email_exists($email)
+	{
+		return (bool) $this-&gt;db-&gt;where('email', $email)-&gt;count_records($this-&gt;table_name);
+	}
+
+	/**
+	 * Tests if a username exists in the database. This can be used as a
+	 * Validation rule.
+	 *
+	 * @param   mixed    id to check
+	 * @return  boolean
+	 */
+	public function username_exists($id)
+	{
+		return (bool) $this-&gt;db
+			-&gt;where($this-&gt;unique_key($id), $id)
+			-&gt;count_records($this-&gt;table_name);
+	}
+
+	/**
+	 * Allows a model to be loaded by username or email address.
+	 */
+	public function unique_key($id)
+	{
+		if ( ! empty($id) AND is_string($id) AND ! ctype_digit($id))
+		{
+			return valid::email($id) ? 'email' : 'username';
+		}
+
+		return parent::unique_key($id);
+	}
+
+} // End Auth User Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/auth_user.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,5 @@
-&lt;?php
-/**
- * Model for (auto login) user_tokens for the Auth Module
- *
- * $Id: auth_user_token.php 3352 3352 2008-08-18 09:43:56BST atomless $
- */
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+
 class Auth_User_Token_Model extends ORM {
 
 	// Relationships
@@ -70,7 +66,7 @@ class Auth_User_Token_Model extends ORM {
 	/**
 	 * Finds a new unique token, using a loop to make sure that the token does
 	 * not already exist in the database. This could potentially become an
-	 * infinite loop, but the chances of that happening are VERY unlikely.
+	 * infinite loop, but the chances of that happening are very unlikely.
 	 *
 	 * @return  string
 	 */
@@ -103,4 +99,4 @@ class Auth_User_Token_Model extends ORM {
 		return parent::unique_key($id);
 	}
 
-} // End User Token
\ No newline at end of file
+} // End Auth User Token Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/auth_user_token.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,11 +1,7 @@
-&lt;?php
-/**
- * Model for roles for the Auth Module
- *
- * $Id: role.php 3352 2008-08-18 09:43:56BST atomless $
- */
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+
 class Role_Model extends Auth_Role_Model {
 
-	// Use this actual model (rather than extending it) when needing to write a custom role model
+	// This class can be replaced or extended
 
-} // End Role_Model
\ No newline at end of file
+} // End Role Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/role.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,11 +1,7 @@
-&lt;?php
-/**
- * Model for users for the Auth Module
- *
- * $Id: user.php 3352 2008-08-18 09:43:56BST atomless $
- */
-class User_Model extends Auth_User_Model {
-
-	// Use this actual model (rather than extending it) when needing to write a custom user model
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
-} // End User_Model
\ No newline at end of file
+class User_Model extends Auth_User_Model {
+	
+	// This class can be replaced or extended
+	
+} // End User Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/user.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,11 +1,7 @@
-&lt;?php
-/**
- * Model for (auto login) user_tokens for the Auth Module
- *
- * $Id: user_token.php 3352 2008-08-18 09:43:56BST atomless $
- */
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+
 class User_Token_Model extends Auth_User_Token_Model {
 
-	// Use this actual model (rather than extending it) when needing to write a custom user token model
+	// This class can be replaced or extended
 
-} // End User_Token_Model
\ No newline at end of file
+} // End User Token Model
\ No newline at end of file</diff>
      <filename>modules/auth/models/user_token.php</filename>
    </modified>
    <modified>
      <diff>@@ -508,8 +508,8 @@ CREATE TABLE IF NOT EXISTS `location` (
   `id` bigint(20) unsigned NOT NULL auto_increment,
   `location_name` varchar(255) default NULL,
   `country_id` int(11) default NULL,
-  `latitude` varchar(50) default NULL,
-  `longitude` varchar(50) default NULL,
+  `latitude` DOUBLE NOT NULL default '0',
+  `longitude` DOUBLE NOT NULL default '0',
   `location_visible` tinyint(4) NOT NULL default '1',
   `location_date` datetime default NULL,
   PRIMARY KEY  (`id`)
@@ -737,7 +737,7 @@ CREATE TABLE IF NOT EXISTS `roles` (
 --
 
 INSERT INTO `roles` (`id`, `name`, `description`) VALUES
-(1, 'user', 'Login privileges, granted after account confirmation'),
+(1, 'login', 'Login privileges, granted after account confirmation'),
 (2, 'admin', 'Administrative user, has access to everything.');
 
 -- --------------------------------------------------------
@@ -757,7 +757,9 @@ CREATE TABLE IF NOT EXISTS `roles_users` (
 -- Dumping data for table `roles_users`
 --
 
-INSERT INTO `roles_users` (`user_id`, `role_id`) VALUES (1, 2);
+INSERT INTO `roles_users` (`user_id`, `role_id`) VALUES
+(1, 1),
+(1, 2);
 
 -- --------------------------------------------------------
 
@@ -1012,6 +1014,39 @@ CREATE TABLE `scheduler_log` (
 --
 
 
+-- --------------------------------------------------------
+
+--
+-- Table structure for table `cluster`
+--
+
+CREATE TABLE IF NOT EXISTS `cluster` (
+  `id` int(11) NOT NULL,
+  `location_id` bigint(20) NOT NULL default '0',	
+  `latitude` double NOT NULL,
+  `longitude` double NOT NULL,
+  `latitude_min` double NOT NULL,
+  `longitude_min` double NOT NULL,
+  `latitude_max` double NOT NULL,
+  `longitude_max` double NOT NULL,
+  `child_count` int(11) NOT NULL,
+  `parent_id` int(11) NOT NULL,
+  `left_side` int(11) NOT NULL,
+  `right_side` int(11) NOT NULL,
+  `level` int(11) NOT NULL,
+  `incident_id` bigint(20) NOT NULL default '0',
+  `incident_title` varchar(255) default NULL,
+  `incident_date` int(10) NOT NULL default 0,
+  `category_id` int(11) UNSIGNED NOT NULL default '0',
+  `category_color` varchar(20) NOT NULL default '990000',
+  PRIMARY KEY  (`id`)
+);
+
+--
+-- Dumping data for table `cluster`
+--
+
+
 --
 -- Constraints for dumped tables
 --</diff>
      <filename>sql/ushahidi.sql</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Cache
  *</diff>
      <filename>system/config/cache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Cache:Memcache
  *</diff>
      <filename>system/config/cache_memcache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Cache:SQLite
  */</diff>
      <filename>system/config/cache_sqlite.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Cache:Xcache
  *</diff>
      <filename>system/config/cache_xcache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/captcha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/cookie.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Credit card validation configuration.
  * </diff>
      <filename>system/config/credit_cards.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * SwiftMailer driver, used with the email helper.
  *</diff>
      <filename>system/config/email.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Encrypt
  *</diff>
      <filename>system/config/encryption.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 // HTTP-EQUIV type meta tags
 $config['meta_equiv'] = array</diff>
      <filename>system/config/http.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Image
  *</diff>
      <filename>system/config/image.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $config['uncountable'] = array
 (
@@ -32,6 +32,7 @@ $config['uncountable'] = array
 	'sheep',
 	'sms',
 	'species',
+	'staff',
 	'toothpaste',
 	'traffic',
 	'understanding',
@@ -52,4 +53,6 @@ $config['irregular'] = array
 	'goose' =&gt; 'geese',
 	'ox' =&gt; 'oxen',
 	'leaf' =&gt; 'leaves',
+	'course' =&gt; 'courses',
+	'size' =&gt; 'sizes',
 );</diff>
      <filename>system/config/inflector.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/locale.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *
@@ -36,7 +36,7 @@ $config = array
 	'cpt'   =&gt; array('application/mac-compactpro'),
 	'csh'   =&gt; array('text/x-csh'),
 	'css'   =&gt; array('text/css'),
-	'csv'   =&gt; array('text/x-comma-separated-values', 'application/vnd.ms-excel'),
+	'csv'   =&gt; array('text/x-comma-separated-values', 'application/vnd.ms-excel', 'text/comma-separated-values', 'text/csv'),
 	'dbk'   =&gt; array('application/docbook+xml'),
 	'dcr'   =&gt; array('application/x-director'),
 	'deb'   =&gt; array('application/x-debian-package'),</diff>
      <filename>system/config/mimes.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Pagination
  *</diff>
      <filename>system/config/pagination.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Profiler
  *</diff>
      <filename>system/config/profiler.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/routes.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package Session
  *</diff>
      <filename>system/config/session.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Database
  *
@@ -8,28 +8,29 @@
  */
 $config = array
 (
-	'tinyint'      =&gt; array('type' =&gt; 'int', 'max' =&gt; 127),
-	'smallint'     =&gt; array('type' =&gt; 'int', 'max' =&gt; 32767),
-	'mediumint'    =&gt; array('type' =&gt; 'int', 'max' =&gt; 8388607),
-	'int'          =&gt; array('type' =&gt; 'int', 'max' =&gt; 2147483647),
-	'integer'      =&gt; array('type' =&gt; 'int', 'max' =&gt; 2147483647),
-	'bigint'       =&gt; array('type' =&gt; 'int', 'max' =&gt; 9223372036854775807),
-	'float'        =&gt; array('type' =&gt; 'float'),
-	'boolean'      =&gt; array('type' =&gt; 'boolean'),
-	'time'         =&gt; array('type' =&gt; 'string', 'format' =&gt; '00:00:00'),
-	'date'         =&gt; array('type' =&gt; 'string', 'format' =&gt; '0000-00-00'),
-	'year'         =&gt; array('type' =&gt; 'string', 'format' =&gt; '0000'),
-	'datetime'     =&gt; array('type' =&gt; 'string', 'format' =&gt; '0000-00-00 00:00:00'),
-	'char'         =&gt; array('type' =&gt; 'string', 'exact' =&gt; TRUE),
-	'binary'       =&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE, 'exact' =&gt; TRUE),
-	'varchar'      =&gt; array('type' =&gt; 'string'),
-	'varbinary'    =&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE),
-	'blob'         =&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE),
-	'text'         =&gt; array('type' =&gt; 'string')
+	'tinyint'			=&gt; array('type' =&gt; 'int', 'max' =&gt; 127),
+	'smallint'			=&gt; array('type' =&gt; 'int', 'max' =&gt; 32767),
+	'mediumint'			=&gt; array('type' =&gt; 'int', 'max' =&gt; 8388607),
+	'int'				=&gt; array('type' =&gt; 'int', 'max' =&gt; 2147483647),
+	'integer'			=&gt; array('type' =&gt; 'int', 'max' =&gt; 2147483647),
+	'bigint'			=&gt; array('type' =&gt; 'int', 'max' =&gt; 9223372036854775807),
+	'float'				=&gt; array('type' =&gt; 'float'),
+	'float unsigned'	=&gt; array('type' =&gt; 'float', 'min' =&gt; 0),
+	'boolean'			=&gt; array('type' =&gt; 'boolean'),
+	'time'				=&gt; array('type' =&gt; 'string', 'format' =&gt; '00:00:00'),
+	'date'				=&gt; array('type' =&gt; 'string', 'format' =&gt; '0000-00-00'),
+	'year'				=&gt; array('type' =&gt; 'string', 'format' =&gt; '0000'),
+	'datetime'			=&gt; array('type' =&gt; 'string', 'format' =&gt; '0000-00-00 00:00:00'),
+	'char'				=&gt; array('type' =&gt; 'string', 'exact' =&gt; TRUE),
+	'binary'			=&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE, 'exact' =&gt; TRUE),
+	'varchar'			=&gt; array('type' =&gt; 'string'),
+	'varbinary'			=&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE),
+	'blob'				=&gt; array('type' =&gt; 'string', 'binary' =&gt; TRUE),
+	'text'				=&gt; array('type' =&gt; 'string')
 );
 
 // DOUBLE
-$config['double'] = $config['decimal'] = $config['real'] = $config['numeric'] = $config['float'];
+$config['double'] = $config['double unsigned'] = $config['decimal'] = $config['real'] = $config['numeric'] = $config['float'];
 
 // BIT
 $config['bit'] = $config['boolean'];</diff>
      <filename>system/config/sql_types.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/upload.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/user_agents.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * @package  Core
  *</diff>
      <filename>system/config/view.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,10 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Outputs the dynamic Captcha resource.
  * Usage: Call the Captcha controller from a view, e.g.
  *        &lt;img src=&quot;&lt;?php echo url::site('captcha') ?&gt;&quot; /&gt;
  *
- * $Id: captcha.php 3281 2008-08-06 16:13:58Z Shadowhand $
+ * $Id: captcha.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/controllers/captcha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Allows a template to be automatically loaded and displayed. Display can be
  * dynamically turned off in the controller methods, and the template file
@@ -7,7 +7,7 @@
  * To use it, declare your controller to extend this class:
  * `class Your_Controller extends Template_Controller`
  *
- * $Id: template.php 3201 2008-07-23 17:05:49Z Shadowhand $
+ * $Id: template.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/controllers/template.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Simple benchmarking.
  *
- * $Id: Benchmark.php 2897 2008-06-25 08:02:08Z armen $
+ * $Id: Benchmark.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/core/Benchmark.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Kohana process control file, loaded by the front controller.
  * 
- * $Id: Bootstrap.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Bootstrap.php 3918 2009-01-21 03:15:53Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -10,11 +10,11 @@
  * @license    http://kohanaphp.com/license.html
  */
 
-define('KOHANA_VERSION',  '2.2');
-define('KOHANA_CODENAME', 'ef&#237;mera');
+define('KOHANA_VERSION',  '2.3.1');
+define('KOHANA_CODENAME', 'accipiter');
 
 // Test of Kohana is running in Windows
-define('KOHANA_IS_WIN', PHP_SHLIB_SUFFIX === 'dll');
+define('KOHANA_IS_WIN', DIRECTORY_SEPARATOR === '\\');
 
 // Kohana benchmarks are prefixed to prevent collisions
 define('SYSTEM_BENCHMARK', 'system_benchmark');
@@ -55,4 +55,4 @@ Benchmark::stop(SYSTEM_BENCHMARK.'_system_initialization');
 Event::run('system.execute');
 
 // Clean up and exit
-Event::run('system.shutdown');
\ No newline at end of file
+Event::run('system.shutdown');</diff>
      <filename>system/core/Bootstrap.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,10 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Process queuing/execution class. Allows an unlimited number of callbacks
  * to be added to 'events'. Events can be run multiple times, and can also
  * process event-specific data. By default, Kohana has several system events.
  *
- * $Id: Event.php 3170 2008-07-21 02:16:01Z Shadowhand $
+ * $Id: Event.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/core/Event.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Provides Kohana-specific helper functions. This is where the magic happens!
  *
- * $Id: Kohana.php 3283 2008-08-06 20:56:56Z Geert $
+ * $Id: Kohana.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -109,7 +109,7 @@ final class Kohana {
 
 		if (function_exists('date_default_timezone_set'))
 		{
-			$timezone = Kohana::config('locale.timezone');
+			$timezone = self::config('locale.timezone');
 
 			// Set default timezone, due to increased validation of date settings
 			// which cause massive amounts of E_NOTICEs to be generated in PHP 5.2+
@@ -168,49 +168,15 @@ final class Kohana {
 		// Enable Kohana output handling
 		Event::add('system.shutdown', array('Kohana', 'shutdown'));
 
-		if ($config = Kohana::config('core.enable_hooks'))
+		if (self::config('core.enable_hooks') === TRUE)
 		{
-			$hooks = array();
+			// Find all the hook files
+			$hooks = self::list_files('hooks', TRUE);
 
-			if ( ! is_array($config))
+			foreach ($hooks as $file)
 			{
-				// All of the hooks are enabled, so we use list_files
-				$hooks = Kohana::list_files('hooks', TRUE);
-			}
-			else
-			{
-				// Individual hooks need to be found
-				foreach ($config as $name)
-				{
-					if ($hook = Kohana::find_file('hooks', $name, FALSE))
-					{
-						// Hook was found, add it to loaded hooks
-						$hooks[] = $hook;
-					}
-					else
-					{
-						// This should never happen
-						Kohana::log('error', 'Hook not found: '.$name);
-					}
-				}
-			}
-
-			// Length of extension, for offset
-			$ext = -(strlen(EXT));
-
-			foreach ($hooks as $hook)
-			{
-				// Validate the filename extension
-				if (substr($hook, $ext) === EXT)
-				{
-					// Hook was found, include it
-					include $hook;
-				}
-				else
-				{
-					// This should never happen
-					Kohana::log('error', 'Hook not found: '.$hook);
-				}
+				// Load the hook
+				include $file;
 			}
 		}
 
@@ -256,7 +222,7 @@ final class Kohana {
 				Event::run('system.404');
 			}
 
-			if (IN_PRODUCTION AND $class-&gt;getConstant('ALLOW_PRODUCTION') == FALSE)
+			if ($class-&gt;isAbstract() OR (IN_PRODUCTION AND $class-&gt;getConstant('ALLOW_PRODUCTION') == FALSE))
 			{
 				// Controller is not allowed to run in production
 				Event::run('system.404');
@@ -513,7 +479,12 @@ final class Kohana {
 	{
 		if (self::$log_levels[$type] &lt;= self::$configuration['core']['log_threshold'])
 		{
-			self::$log[] = array(date('Y-m-d H:i:s P'), $type, $message);
+			$message = array(date('Y-m-d H:i:s P'), $type, $message);
+
+			// Run the system.log event
+			Event::run('system.log', $message);
+
+			self::$log[] = $message;
 		}
 	}
 
@@ -524,7 +495,7 @@ final class Kohana {
 	 */
 	public static function log_save()
 	{
-		if (empty(self::$log))
+		if (empty(self::$log) OR self::$configuration['core']['log_threshold'] &lt; 1)
 			return;
 
 		// Filename of the log
@@ -729,7 +700,7 @@ final class Kohana {
 		// Fetch benchmark for page execution time
 		$benchmark = Benchmark::get(SYSTEM_BENCHMARK.'_total_execution');
 
-		if (Kohana::config('core.render_stats') === TRUE)
+		if (self::config('core.render_stats') === TRUE)
 		{
 			// Replace the global template variables
 			$output = str_replace(
@@ -753,7 +724,7 @@ final class Kohana {
 			);
 		}
 
-		if ($level = Kohana::config('core.output_compression') AND ini_get('output_handler') !== 'ob_gzhandler' AND (int) ini_get('zlib.output_compression') === 0)
+		if ($level = self::config('core.output_compression') AND ini_get('output_handler') !== 'ob_gzhandler' AND (int) ini_get('zlib.output_compression') === 0)
 		{
 			if ($level &lt; 1 OR $level &gt; 9)
 			{
@@ -882,7 +853,7 @@ final class Kohana {
 		$file = str_replace('\\', '/', realpath($file));
 		$file = preg_replace('|^'.preg_quote(DOCROOT).'|', '', $file);
 
-		if ($level &gt;= self::$configuration['core']['log_threshold'])
+		if ($level &lt;= self::$configuration['core']['log_threshold'])
 		{
 			// Log the error
 			self::log('error', self::lang('core.uncaught_exception', $type, $message, $file, $line));
@@ -1004,37 +975,39 @@ final class Kohana {
 			$file = $class;
 		}
 
-		if (($filepath = self::find_file($type, $file)) === FALSE)
+		if ($filename = self::find_file($type, $file))
+		{
+			// Load the class
+			require $filename;
+		}
+		else
+		{
+			// The class could not be found
 			return FALSE;
+		}
 
-		// Load the file
-		require $filepath;
-
-		if ($type === 'libraries' OR $type === 'helpers')
+		if ($filename = self::find_file($type, self::$configuration['core']['extension_prefix'].$class))
 		{
-			if ($extension = self::find_file($type, self::$configuration['core']['extension_prefix'].$class))
-			{
-				// Load the extension
-				require $extension;
-			}
-			elseif ($suffix !== 'Core' AND class_exists($class.'_Core', FALSE))
-			{
-				// Class extension to be evaluated
-				$extension = 'class '.$class.' extends '.$class.'_Core { }';
+			// Load the class extension
+			require $filename;
+		}
+		elseif ($suffix !== 'Core' AND class_exists($class.'_Core', FALSE))
+		{
+			// Class extension to be evaluated
+			$extension = 'class '.$class.' extends '.$class.'_Core { }';
 
-				// Start class analysis
-				$core = new ReflectionClass($class.'_Core');
+			// Start class analysis
+			$core = new ReflectionClass($class.'_Core');
 
-				if ($core-&gt;isAbstract())
-				{
-					// Make the extension abstract
-					$extension = 'abstract '.$extension;
-				}
-
-				// Transparent class extensions are handled using eval. This is
-				// a disgusting hack, but it gets the job done.
-				eval($extension);
+			if ($core-&gt;isAbstract())
+			{
+				// Make the extension abstract
+				$extension = 'abstract '.$extension;
 			}
+
+			// Transparent class extensions are handled using eval. This is
+			// a disgusting hack, but it gets the job done.
+			eval($extension);
 		}
 
 		return TRUE;
@@ -1150,7 +1123,7 @@ final class Kohana {
 
 		if ($path === FALSE)
 		{
-			$paths = array_reverse(Kohana::include_paths());
+			$paths = array_reverse(self::include_paths());
 
 			foreach ($paths as $path)
 			{
@@ -1200,7 +1173,7 @@ final class Kohana {
 		$group = $group[0];
 
 		// Get locale name
-		$locale = Kohana::config('locale.language.0');
+		$locale = self::config('locale.language.0');
 
 		if ( ! isset(self::$internal_cache['language'][$locale][$group]))
 		{
@@ -1238,7 +1211,7 @@ final class Kohana {
 
 		if ($line === NULL)
 		{
-			Kohana::log('error', 'Missing i18n entry '.$key.' for language '.$locale);
+			self::log('error', 'Missing i18n entry '.$key.' for language '.$locale);
 
 			// Return the key string as fallback
 			return $key;
@@ -1391,20 +1364,20 @@ final class Kohana {
 
 		// Return the raw string
 		if ($key === 'agent')
-			return Kohana::$user_agent;
+			return self::$user_agent;
 
 		if ($info === NULL)
 		{
 			// Parse the user agent and extract basic information
-			$agents = Kohana::config('user_agents');
+			$agents = self::config('user_agents');
 
 			foreach ($agents as $type =&gt; $data)
 			{
 				foreach ($data as $agent =&gt; $name)
 				{
-					if (stripos(Kohana::$user_agent, $agent) !== FALSE)
+					if (stripos(self::$user_agent, $agent) !== FALSE)
 					{
-						if ($type === 'browser' AND preg_match('|'.preg_quote($agent).'[^0-9.]*+([0-9.][0-9.a-z]*)|i', Kohana::$user_agent, $match))
+						if ($type === 'browser' AND preg_match('|'.preg_quote($agent).'[^0-9.]*+([0-9.][0-9.a-z]*)|i', self::$user_agent, $match))
 						{
 							// Set the browser version
 							$info['version'] = $match[1];
@@ -1472,11 +1445,11 @@ final class Kohana {
 			{
 				case 'accept_lang':
 					// Check if the lange is accepted
-					return in_array($compare, Kohana::user_agent('languages'));
+					return in_array($compare, self::user_agent('languages'));
 				break;
 				case 'accept_charset':
 					// Check if the charset is accepted
-					return in_array($compare, Kohana::user_agent('charsets'));
+					return in_array($compare, self::user_agent('charsets'));
 				break;
 				default:
 					// Invalid comparison
@@ -1532,7 +1505,7 @@ final class Kohana {
 
 			if (isset($entry['file']))
 			{
-				$temp .= Kohana::lang('core.error_file_line', preg_replace('!^'.preg_quote(DOCROOT).'!', '', $entry['file']), $entry['line']);
+				$temp .= self::lang('core.error_file_line', preg_replace('!^'.preg_quote(DOCROOT).'!', '', $entry['file']), $entry['line']);
 			}
 
 			$temp .= '&lt;pre&gt;';</diff>
      <filename>system/core/Kohana.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * A port of phputf8 to a unified file/class. Checks PHP status to ensure that
  * UTF-8 support is available and normalize global variables to UTF-8. It also
@@ -18,7 +18,7 @@
  * string functions.
  * @see http://php.net/mbstring
  *
- * $Id: utf8.php 2712 2008-05-29 17:05:06Z Geert $
+ * $Id: utf8.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/core/utf8.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::from_unicode
  *</diff>
      <filename>system/core/utf8/from_unicode.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::ltrim
  *</diff>
      <filename>system/core/utf8/ltrim.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::ord
  *</diff>
      <filename>system/core/utf8/ord.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::rtrim
  *</diff>
      <filename>system/core/utf8/rtrim.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::str_ireplace
  *</diff>
      <filename>system/core/utf8/str_ireplace.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::str_pad
  *</diff>
      <filename>system/core/utf8/str_pad.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::str_split
  *</diff>
      <filename>system/core/utf8/str_split.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strcasecmp
  *</diff>
      <filename>system/core/utf8/strcasecmp.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strcspn
  *</diff>
      <filename>system/core/utf8/strcspn.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::stristr
  *</diff>
      <filename>system/core/utf8/stristr.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strlen
  *</diff>
      <filename>system/core/utf8/strlen.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strpos
  *</diff>
      <filename>system/core/utf8/strpos.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strrev
  *</diff>
      <filename>system/core/utf8/strrev.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strrpos
  *</diff>
      <filename>system/core/utf8/strrpos.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strspn
  *</diff>
      <filename>system/core/utf8/strspn.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strtolower
  *</diff>
      <filename>system/core/utf8/strtolower.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::strtoupper
  *</diff>
      <filename>system/core/utf8/strtoupper.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::substr
  *</diff>
      <filename>system/core/utf8/substr.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::substr_replace
  *</diff>
      <filename>system/core/utf8/substr_replace.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::to_unicode
  *</diff>
      <filename>system/core/utf8/to_unicode.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::transliterate_to_ascii
  *</diff>
      <filename>system/core/utf8/transliterate_to_ascii.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::trim
  *</diff>
      <filename>system/core/utf8/trim.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::ucfirst
  *</diff>
      <filename>system/core/utf8/ucfirst.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * utf8::ucwords
  *</diff>
      <filename>system/core/utf8/ucwords.php</filename>
    </modified>
    <modified>
      <filename>system/fonts/DejaVuSerif.ttf</filename>
    </modified>
    <modified>
      <filename>system/fonts/LICENSE</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Array helper class.
  *
- * $Id: arr.php 2924 2008-06-27 14:46:20Z Shadowhand $
+ * $Id: arr.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -288,4 +288,29 @@ class arr_Core {
 		return $array;
 	}
 
+	/**
+	 * Recursively convert an array to an object.
+	 *
+	 * @param   array   array to convert
+	 * @return  object
+	 */
+	public static function to_object(array $array, $class = 'stdClass')
+	{
+		$object = new $class;
+
+		foreach ($array as $key =&gt; $value)
+		{
+			if (is_array($value))
+			{
+				// Convert the array to an object
+				$value = arr::to_object($value, $class);
+			}
+
+			// Add the value to the object
+			$object-&gt;{$key} = $value;
+		}
+
+		return $object;
+	}
+
 } // End arr
\ No newline at end of file</diff>
      <filename>system/helpers/arr.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Cookie helper class.
  *
- * $Id: cookie.php 3221 2008-07-28 13:14:40Z Geert $
+ * $Id: cookie.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/cookie.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Date helper class.
  *
- * $Id: date.php 2663 2008-05-07 19:58:02Z Shadowhand $
+ * $Id: date.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/date.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Download helper class.
  *
- * $Id: download.php 3238 2008-07-30 15:42:28Z Shadowhand $
+ * $Id: download.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/download.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Email helper class.
  *
- * $Id: email.php 3213 2008-07-27 14:28:37Z Geert $
+ * $Id: email.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -95,7 +95,7 @@ class email_Core {
 			break;
 			default:
 				// Use the native connection
-				$connection = new Swift_Connection_NativeMail;
+				$connection = new Swift_Connection_NativeMail($config['options']);
 			break;
 		}
 </diff>
      <filename>system/helpers/email.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Controls headers that effect client caching of pages
  *
- * $Id: expires.php 3229 2008-07-28 22:16:20Z Geert $
+ * $Id: expires.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/expires.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Feed helper class.
  *
- * $Id: feed.php 2985 2008-07-07 19:13:27Z Shadowhand $
+ * $Id: feed.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/feed.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * File helper class.
  *
- * $Id: file.php 3237 2008-07-30 12:10:20Z Geert $
+ * $Id: file.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -62,6 +62,15 @@ class file_Core {
 			return mime_content_type($filename);
 		}
 
+		if ( ! KOHANA_IS_WIN)
+		{
+			// Attempt to locate use the file command, checking the return value
+			if ($command = trim(exec('which file', $output, $return)) AND $return === 0)
+			{
+				return trim(exec($command.' -bi '.escapeshellarg($filename)));
+			}
+		}
+
 		if ( ! empty($extension) AND is_array($mime = Kohana::config('mimes.'.$extension)))
 		{
 			// Return the mime-type guess, based on the extension</diff>
      <filename>system/helpers/file.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Form helper class.
  *
- * $Id: form.php 2914 2008-06-25 22:45:11Z Shadowhand $
+ * $Id: form.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -144,9 +144,10 @@ class form_Core {
 	 * @param   string|array  input name or an array of HTML attributes
 	 * @param   string        input value, when using a name
 	 * @param   string        a string to be attached to the end of the attributes
+	 * @param   boolean       encode existing entities
 	 * @return  string
 	 */
-	public static function input($data, $value = '', $extra = '')
+	public static function input($data, $value = '', $extra = '', $double_encode = TRUE )
 	{
 		if ( ! is_array($data))
 		{
@@ -161,7 +162,7 @@ class form_Core {
 		);
 
 		// For safe form data
-		$data['value'] = html::specialchars($data['value']);
+		$data['value'] = html::specialchars($data['value'], $double_encode);
 
 		return '&lt;input'.form::attributes($data).' '.$extra.' /&gt;';
 	}
@@ -212,9 +213,10 @@ class form_Core {
 	 * @param   string|array  input name or an array of HTML attributes
 	 * @param   string        input value, when using a name
 	 * @param   string        a string to be attached to the end of the attributes
+	 * @param   boolean       encode existing entities
 	 * @return  string
 	 */
-	public static function textarea($data, $value = '', $extra = '')
+	public static function textarea($data, $value = '', $extra = '', $double_encode = TRUE )
 	{
 		if ( ! is_array($data))
 		{
@@ -227,7 +229,7 @@ class form_Core {
 		// Value is not part of the attributes
 		unset($data['value']);
 
-		return '&lt;textarea'.form::attributes($data, 'textarea').' '.$extra.'&gt;'.html::specialchars($value).'&lt;/textarea&gt;';
+		return '&lt;textarea'.form::attributes($data, 'textarea').' '.$extra.'&gt;'.html::specialchars($value, $double_encode).'&lt;/textarea&gt;';
 	}
 
 	/**
@@ -241,6 +243,7 @@ class form_Core {
 	 */
 	public static function dropdown($data, $options = NULL, $selected = NULL, $extra = '')
 	{
+
 		if ( ! is_array($data))
 		{
 			$data = array('name' =&gt; $data);
@@ -260,15 +263,15 @@ class form_Core {
 			}
 		}
 
-		// Selected value should always be a string
-		$selected = (string) $selected;
-
 		$input = '&lt;select'.form::attributes($data, 'select').' '.$extra.'&gt;'.&quot;\n&quot;;
 		foreach ((array) $options as $key =&gt; $val)
 		{
 			// Key should always be a string
 			$key = (string) $key;
 
+			// Selected must always be a string
+			$selected = (string) $selected;
+
 			if (is_array($val))
 			{
 				$input .= '&lt;optgroup label=&quot;'.$key.'&quot;&gt;'.&quot;\n&quot;;
@@ -277,7 +280,16 @@ class form_Core {
 					// Inner key should always be a string
 					$inner_key = (string) $inner_key;
 
-					$sel = ($selected === $inner_key) ? ' selected=&quot;selected&quot;' : '';
+					if (is_array($selected))
+					{
+						$sel = in_array($inner_key, $selected, TRUE);
+					}
+					else
+					{
+						$sel = ($selected === $inner_key);
+					}
+
+					$sel = ($sel === TRUE) ? ' selected=&quot;selected&quot;' : '';
 					$input .= '&lt;option value=&quot;'.$inner_key.'&quot;'.$sel.'&gt;'.$inner_val.'&lt;/option&gt;'.&quot;\n&quot;;
 				}
 				$input .= '&lt;/optgroup&gt;'.&quot;\n&quot;;
@@ -427,16 +439,26 @@ class form_Core {
 	 * @param   string        a string to be attached to the end of the attributes
 	 * @return  string
 	 */
-	public static function label($data = '', $text = '', $extra = '')
+	public static function label($data = '', $text = NULL, $extra = '')
 	{
 		if ( ! is_array($data))
 		{
-			if (strpos($data, '[') !== FALSE)
+			if (is_string($data))
 			{
-				$data = preg_replace('/\[.*\]/', '', $data);
+				// Specify the input this label is for
+				$data = array('for' =&gt; $data);
 			}
+			else
+			{
+				// No input specified
+				$data = array();
+			}
+		}
 
-			$data = empty($data) ? array() : array('for' =&gt; $data);
+		if ($text === NULL AND isset($data['for']))
+		{
+			// Make the text the human-readable input name
+			$text = ucwords(inflector::humanize($data['for']));
 		}
 
 		return '&lt;label'.form::attributes($data).' '.$extra.'&gt;'.$text.'&lt;/label&gt;';</diff>
      <filename>system/helpers/form.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Format helper class.
  *
- * $Id: format.php 2451 2008-04-08 15:04:00Z PugFish $
+ * $Id: format.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/format.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * HTML helper class.
  *
- * $Id: html.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: html.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -299,10 +299,34 @@ class html_Core {
 		}
 		else
 		{
-			// Add the suffix only when it's not already present
-			$suffix   = ( ! empty($suffix) AND strpos($href, $suffix) === FALSE) ? $suffix : '';
-			$media    = empty($media) ? '' : ' media=&quot;'.$media.'&quot;';
-			$compiled = '&lt;link rel=&quot;'.$rel.'&quot; type=&quot;'.$type.'&quot; href=&quot;'.url::base((bool) $index).$href.$suffix.'&quot;'.$media.' /&gt;';
+			if (strpos($href, '://') === FALSE)
+			{
+				// Make the URL absolute
+				$href = url::base($index).$href;
+			}
+
+			$length = strlen($suffix);
+
+			if ( $length &gt; 0 AND substr_compare($href, $suffix, -$length, $length, FALSE) !== 0)
+			{
+				// Add the defined suffix
+				$href .= $suffix;
+			}
+
+			$attr = array
+			(
+				'rel' =&gt; $rel,
+				'type' =&gt; $type,
+				'href' =&gt; $href,
+			);
+
+			if ( ! empty($media))
+			{
+				// Add the media type to the attributes
+				$attr['media'] = $media;
+			}
+
+			$compiled = '&lt;link'.html::attributes($attr).' /&gt;';
 		}
 
 		return $compiled.&quot;\n&quot;;
@@ -328,12 +352,16 @@ class html_Core {
 		}
 		else
 		{
-			// Do not touch full URLs
 			if (strpos($script, '://') === FALSE)
 			{
 				// Add the suffix only when it's not already present
-				$suffix = (substr($script, -3) !== '.js') ? '.js' : '';
-				$script = url::base((bool) $index).$script.$suffix;
+				$script = url::base((bool) $index).$script;
+			}
+
+			if (substr_compare($script, '.js', -3, 3, FALSE) !== 0)
+			{
+				// Add the javascript suffix
+				$script .= '.js';
 			}
 
 			$compiled = '&lt;script type=&quot;text/javascript&quot; src=&quot;'.$script.'&quot;&gt;&lt;/script&gt;';
@@ -391,7 +419,7 @@ class html_Core {
 		$compiled = '';
 		foreach ($attrs as $key =&gt; $val)
 		{
-			$compiled .= ' '.$key.'=&quot;'.$val.'&quot;';
+			$compiled .= ' '.$key.'=&quot;'.html::specialchars($val).'&quot;';
 		}
 
 		return $compiled;</diff>
      <filename>system/helpers/html.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Inflector helper class.
  *
- * $Id: inflector.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: inflector.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/inflector.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Number helper class.
  *
- * $Id: num.php 2373 2008-03-28 20:01:58Z Shadowhand $
+ * $Id: num.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/num.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Remote url/file helper.
  *
- * $Id: remote.php 3149 2008-07-18 13:48:25Z Shadowhand $
+ * $Id: remote.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/remote.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Request helper class.
  *
- * $Id: request.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: request.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -41,6 +41,28 @@ class request_Core {
 	}
 
 	/**
+	 * Returns the current request protocol, based on $_SERVER['https']. In CLI
+	 * mode, NULL will be returned.
+	 *
+	 * @return  string
+	 */
+	public static function protocol()
+	{
+		if (PHP_SAPI === 'cli')
+		{
+			return NULL;
+		}
+		elseif ( ! empty($_SERVER['HTTPS']) AND $_SERVER['HTTPS'] === 'on')
+		{
+			return 'https';
+		}
+		else
+		{
+			return 'http';
+		}
+	}
+
+	/**
 	 * Tests if the current request is an AJAX request by checking the X-Requested-With HTTP
 	 * request header that most popular JS frameworks now set for AJAX calls.
 	 *</diff>
      <filename>system/helpers/request.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Security helper class.
  *
- * $Id: security.php 2239 2008-03-08 09:57:44Z Geert $
+ * $Id: security.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/security.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Text helper class.
  *
- * $Id: text.php 3228 2008-07-28 20:47:04Z dlib $
+ * $Id: text.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -95,11 +95,12 @@ class text_Core {
 	 * @param   integer  length of string to return
 	 * @return  string
 	 *
-	 * @tutorial  alnum    - alpha-numeric characters
-	 * @tutorial  alpha    - alphabetical characters
-	 * @tutorial  numeric  - digit characters, 0-9
-	 * @tutorial  nozero   - digit characters, 1-9
-	 * @tutorial  distinct - clearly distinct alpha-numeric characters
+	 * @tutorial  alnum     alpha-numeric characters
+	 * @tutorial  alpha     alphabetical characters
+	 * @tutorial  hexdec    hexadecimal characters, 0-9 plus a-f
+	 * @tutorial  numeric   digit characters, 0-9
+	 * @tutorial  nozero    digit characters, 1-9
+	 * @tutorial  distinct  clearly distinct alpha-numeric characters
 	 */
 	public static function random($type = 'alnum', $length = 8)
 	{
@@ -113,6 +114,9 @@ class text_Core {
 			case 'alpha':
 				$pool = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
 			break;
+			case 'hexdec':
+				$pool = '0123456789abcdef';
+			break;
 			case 'numeric':
 				$pool = '0123456789';
 			break;
@@ -128,15 +132,32 @@ class text_Core {
 			break;
 		}
 
-		$str = '';
+		// Split the pool into an array of characters
+		$pool = ($utf8 === TRUE) ? utf8::str_split($pool, 1) : str_split($pool, 1);
 
-		$pool_size = ($utf8 === TRUE) ? utf8::strlen($pool) : strlen($pool);
+		// Largest pool key
+		$max = count($pool) - 1;
 
+		$str = '';
 		for ($i = 0; $i &lt; $length; $i++)
 		{
-			$str .= ($utf8 === TRUE)
-				? utf8::substr($pool, mt_rand(0, $pool_size - 1), 1)
-				:       substr($pool, mt_rand(0, $pool_size - 1), 1);
+			// Select a random character from the pool and add it to the string
+			$str .= $pool[mt_rand(0, $max)];
+		}
+
+		// Make sure alnum strings contain at least one letter and one digit
+		if ($type === 'alnum' AND $length &gt; 1)
+		{
+			if (ctype_alpha($str))
+			{
+				// Add a random digit
+				$str[mt_rand(0, $length - 1)] = chr(mt_rand(48, 57));
+			}
+			elseif (ctype_digit($str))
+			{
+				// Add a random letter
+				$str[mt_rand(0, $length - 1)] = chr(mt_rand(65, 90));
+			}
 		}
 
 		return $str;
@@ -182,7 +203,7 @@ class text_Core {
 		if (utf8::strlen($replacement) == 1)
 		{
 			$regex .= 'e';
-			return preg_replace($regex, 'str_repeat($replacement, utf8::strlen(\'$1\')', $str);
+			return preg_replace($regex, 'str_repeat($replacement, utf8::strlen(\'$1\'))', $str);
 		}
 
 		return preg_replace($regex, $replacement, $str);</diff>
      <filename>system/helpers/text.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,9 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Upload helper class for working with the global $_FILES
  * array and Validation library.
  *
- * $Id: upload.php 3264 2008-08-05 19:03:14Z Geert $
+ * $Id: upload.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/helpers/upload.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * URL helper class.
  *
- * $Id: url.php 3238 2008-07-30 15:42:28Z Shadowhand $
+ * $Id: url.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -177,7 +177,7 @@ class url_Core {
 	}
 
 	/**
-	 * Sends a page redirect header.
+	 * Sends a page redirect header and runs the system.redirect Event.
 	 *
 	 * @param  mixed   string site URI or URL to redirect to, or array of strings if method is 300
 	 * @param  string  HTTP method of redirect
@@ -186,62 +186,64 @@ class url_Core {
 	public static function redirect($uri = '', $method = '302')
 	{
 		if (Event::has_run('system.send_headers'))
-			return;
-
-		$uri = (array) $uri;
-
-		for ($i = 0, $count_uri = count($uri); $i &lt; $count_uri; $i++)
 		{
-			if (strpos($uri[$i], '://') === FALSE)
-			{
-				$uri[$i] = url::site($uri[$i]);
-			}
+			return FALSE;
 		}
 
-		if ($method == '300')
+		$codes = array
+		(
+			'refresh' =&gt; 'Refresh',
+			'300' =&gt; 'Multiple Choices',
+			'301' =&gt; 'Moved Permanently',
+			'302' =&gt; 'Found',
+			'303' =&gt; 'See Other',
+			'304' =&gt; 'Not Modified',
+			'305' =&gt; 'Use Proxy',
+			'307' =&gt; 'Temporary Redirect'
+		);
+
+		// Validate the method and default to 302
+		$method = isset($codes[$method]) ? (string) $method : '302';
+
+		if ($method === '300')
 		{
-			if ($count_uri &gt; 0)
-			{
-				header('HTTP/1.1 300 Multiple Choices');
-				header('Location: '.$uri[0]);
-
-				$choices = '';
-				foreach ($uri as $href)
-				{
-					$choices .= '&lt;li&gt;&lt;a href=&quot;'.$href.'&quot;&gt;'.$href.'&lt;/a&gt;&lt;/li&gt;';
-				}
+			$uri = (array) $uri;
 
-				exit('&lt;h1&gt;301 - Multiple Choices:&lt;/h1&gt;&lt;ul&gt;'.$choices.'&lt;/ul&gt;');
+			$output = '&lt;ul&gt;';
+			foreach ($uri as $link)
+			{
+				$output .= '&lt;li&gt;'.html::anchor($link).'&lt;/li&gt;';
 			}
+			$output .= '&lt;/ul&gt;';
+
+			// The first URI will be used for the Location header
+			$uri = $uri[0];
 		}
 		else
 		{
-			$uri = $uri[0];
+			$output = '&lt;p&gt;'.html::anchor($uri).'&lt;/p&gt;';
+		}
 
-			if ($method == 'refresh')
-			{
-				header('Refresh: 0; url='.$uri);
-			}
-			else
-			{
-				$codes = array
-				(
-					'301' =&gt; 'Moved Permanently',
-					'302' =&gt; 'Found',
-					'303' =&gt; 'See Other',
-					'304' =&gt; 'Not Modified',
-					'305' =&gt; 'Use Proxy',
-					'307' =&gt; 'Temporary Redirect'
-				);
-
-				$method = isset($codes[$method]) ? $method : '302';
-
-				header('HTTP/1.1 '.$method.' '.$codes[$method]);
-				header('Location: '.$uri);
-			}
+		// Run the redirect event
+		Event::run('system.redirect', $uri);
+
+		if (strpos($uri, '://') === FALSE)
+		{
+			// HTTP headers expect absolute URLs
+			$uri = url::site($uri, request::protocol());
+		}
 
-			exit('&lt;h1&gt;'.$method.' - '.$codes[$method].'&lt;/h1&gt;&lt;p&gt;&lt;a href=&quot;'.$uri.'&quot;&gt;'.$uri.'&lt;/a&gt;&lt;/p&gt;');
+		if ($method === 'refresh')
+		{
+			header('Refresh: 0; url='.$uri);
+		}
+		else
+		{
+			header('HTTP/1.1 '.$method.' '.$codes[$method]);
+			header('Location: '.$uri);
 		}
+
+		exit('&lt;h1&gt;'.$method.' - '.$codes[$method].'&lt;/h1&gt;'.$output);
 	}
 
 } // End url
\ No newline at end of file</diff>
      <filename>system/helpers/url.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Validation helper class.
  *
- * $Id: valid.php 3238 2008-07-30 15:42:28Z Shadowhand $
+ * $Id: valid.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -85,12 +85,15 @@ class valid_Core {
 	 *
 	 * @param   string   IP address
 	 * @param   boolean  allow IPv6 addresses
+	 * @param   boolean  allow private IP networks
 	 * @return  boolean
 	 */
-	public static function ip($ip, $ipv6 = FALSE)
+	public static function ip($ip, $ipv6 = FALSE, $allow_private = TRUE)
 	{
-		// Do not allow private and reserved range IPs
+		// By default do not allow private and reserved range IPs
 		$flags = FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE;
+		if ($allow_private === TRUE)
+			$flags =  FILTER_FLAG_NO_RES_RANGE;
 
 		if ($ipv6 === TRUE)
 			return (bool) filter_var($ip, FILTER_VALIDATE_IP, $flags);
@@ -195,6 +198,17 @@ class valid_Core {
 	}
 
 	/**
+	 * Tests if a string is a valid date string.
+	 * 
+	 * @param   string   date to check
+	 * @return  boolean
+	 */
+	public function date($str)
+	{
+		return (strtotime($str) !== FALSE);
+	}
+
+	/**
 	 * Checks whether a string consists of alphabetical characters only.
 	 *
 	 * @param   string   input string
@@ -253,24 +267,35 @@ class valid_Core {
 	/**
 	 * Checks whether a string is a valid number (negative and decimal numbers allowed).
 	 *
+	 * @see Uses locale conversion to allow decimal point to be locale specific.
+	 * @see http://www.php.net/manual/en/function.localeconv.php
+	 * 
 	 * @param   string   input string
 	 * @return  boolean
 	 */
 	public static function numeric($str)
 	{
-		return (is_numeric($str) AND preg_match('/^[-0-9.]++$/D', (string) $str));
+		// Use localeconv to set the decimal_point value: Usually a comma or period.
+		$locale = localeconv();
+		return (preg_match('/^[-0-9'.$locale['decimal_point'].']++$/D', (string) $str));
 	}
 
 	/**
 	 * Checks whether a string is a valid text. Letters, numbers, whitespace,
 	 * dashes, periods, and underscores are allowed.
 	 *
-	 * @param   string   $str
+	 * @param   string   text to check
 	 * @return  boolean
 	 */
 	public static function standard_text($str)
 	{
-		return (bool) preg_match('/^[-\pL\pN\pZ_.]++$/uD', (string) $str);
+		// pL matches letters
+		// pN matches numbers
+		// pZ matches whitespace
+		// pPc matches underscores
+		// pPd matches dashes
+		// pPo matches normal puncuation
+		return (bool) preg_match('/^[\pL\pN\pZ\p{Pc}\p{Pd}\p{Po}]++$/uD', (string) $str);
 	}
 
 	/**
@@ -309,5 +334,44 @@ class valid_Core {
 
 		return (bool) preg_match($pattern, (string) $str);
 	}
+	
+	/**
+	 * Checks whether a string is a valid number (negative and decimal numbers allowed) and between a specified range.
+	 *
+	 * @param   string   input string
+	 * @param   float (MIN/MAX)
+	 * @return  boolean
+	 */
+	public static function between($str, $min_max = array(0,0))
+	{
+		$set_min = $min_max[0];
+		$set_max = $min_max[1];
+		$str = (float) $str;
+		return (is_numeric($str) AND preg_match('/^[-0-9.]++$/D', (string) $str) AND ($str &lt;= $set_max AND $str &gt;= $set_min) );
+	}
+	
+	/**
+	 * Checks whether a string is a valid date (mm/dd/yyyy).
+	 *
+	 * @param   string   input string
+	 * @return  boolean
+	 */
+	public static function date_mmddyyyy($str)
+	{
+		return (strptime($str, '%m/%d/%G'));
+	
+	}
+
+	/**
+	 * Checks whether a string is a valid date (dd/mm/yyyy).
+	 *
+	 * @param   string   input string
+	 * @return  boolean
+	 */
+	public static function date_ddmmyyyy($str)
+	{
+		return (strptime($str, '%d/%m/%G'));
+	
+	}
 
 } // End valid
\ No newline at end of file</diff>
      <filename>system/helpers/valid.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/cache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/calendar.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/captcha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/core.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/encrypt.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/errors.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/event.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (
@@ -18,7 +18,13 @@ $lang = array
 	(
 		'not_found' =&gt; 'The ImageMagick directory specified does not contain a required program, %s.',
 	),
-
+	
+	// GraphicsMagick specific messages
+	'graphicsmagick' =&gt; array
+	(
+		'not_found' =&gt; 'The GraphicsMagick directory specified does not contain a required program, %s.',
+	),
+	
 	// GD specific messages
 	'gd' =&gt; array
 	(</diff>
      <filename>system/i18n/en_US/image.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,3 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang['query_methods_not_allowed'] = 'Query methods cannot be used through ORM';
\ No newline at end of file</diff>
      <filename>system/i18n/en_US/orm.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/pagination.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/profiler.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/session.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/swift.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (</diff>
      <filename>system/i18n/en_US/upload.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,11 @@
-&lt;?php defined('SYSPATH') or die('No direct access allowed.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 $lang = array
 (
 	// Class errors
 	'invalid_rule'  =&gt; 'Invalid validation rule used: %s',
+	'i18n_array'    =&gt; 'The %s i18n key must be an array to be used with the in_lang rule',
+	'not_callable'  =&gt; 'Callback %s used for Validation is not callable',
 
 	// General errors
 	'unknown_error' =&gt; 'Unknown validation error while validating the %s field.',</diff>
      <filename>system/i18n/en_US/validation.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,10 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Provides a driver-based interface for finding, creating, and deleting cached
  * resources. Caches are identified by a unique string. Tagging of caches is
  * also supported, and caches can be found and deleted by id or tag.
  *
- * $Id: Cache.php 3263 2008-08-05 17:57:50Z PugFish $
+ * $Id: Cache.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/Cache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Calendar creation library.
  *
- * $Id: Calendar.php 3279 2008-08-06 14:41:49Z Shadowhand $
+ * $Id: Calendar.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Calendar
  * @author     Kohana Team
@@ -27,13 +27,13 @@ class Calendar_Core extends Event_Subject {
 	/**
 	 * Returns an array of the names of the days, using the current locale.
 	 *
-	 * @param   boolean  return short names
+	 * @param   integer  left of day names
 	 * @return  array
 	 */
-	public static function days($short = FALSE)
+	public static function days($length = TRUE)
 	{
 		// strftime day format
-		$format = ($short == TRUE) ? '%a' : '%A';
+		$format = ($length &gt; 3) ? '%A' : '%a';
 
 		// Days of the week
 		$days = array('Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday');
@@ -53,12 +53,13 @@ class Calendar_Core extends Event_Subject {
 				$days[$i] = strftime($format, strtotime($day));
 			}
 		}
-		elseif ($short == TRUE)
+
+		if (is_int($length) OR ctype_digit($length))
 		{
 			foreach ($days as $i =&gt; $day)
 			{
-				// Shorten the day names to 3 letters
-				$days[$i] = substr($day, 0, 3);
+				// Shorten the days to the expected length
+				$days[$i] = utf8::substr($day, 0, $length);
 			}
 		}
 </diff>
      <filename>system/libraries/Calendar.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Calendar event observer class.
  *
- * $Id: Calendar_Event.php 2899 2008-06-25 08:04:09Z armen $
+ * $Id: Calendar_Event.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Calendar
  * @author     Kohana Team</diff>
      <filename>system/libraries/Calendar_Event.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha library.
  *
- * $Id: Captcha.php 3168 2008-07-21 01:34:36Z Shadowhand $
+ * $Id: Captcha.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team
@@ -49,7 +49,7 @@ class Captcha_Core {
 	 * @param   string  config group name
 	 * @return  object
 	 */
-	public function factory($group = NULL)
+	public static function factory($group = NULL)
 	{
 		return new Captcha($group);
 	}</diff>
      <filename>system/libraries/Captcha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,9 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Kohana Controller class. The controller class must be extended to work
  * properly, so this class is defined as abstract.
  *
- * $Id: Controller.php 3281 2008-08-06 16:13:58Z Shadowhand $
+ * $Id: Controller.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -66,10 +66,18 @@ abstract class Controller_Core {
 		// Import the view variables to local namespace
 		extract($kohana_input_data, EXTR_SKIP);
 
-		// Views are straight HTML pages with embedded PHP, so importing them
-		// this way insures that $this can be accessed as if the user was in
-		// the controller, which gives the easiest access to libraries in views
-		include $kohana_view_filename;
+		try
+		{
+			// Views are straight HTML pages with embedded PHP, so importing them
+			// this way insures that $this can be accessed as if the user was in
+			// the controller, which gives the easiest access to libraries in views
+			include $kohana_view_filename;
+		}
+		catch (Exception $e)
+		{
+			// Display the exception using its internal __toString method
+			echo $e;
+		}
 
 		// Fetch the output and close the buffer
 		return ob_get_clean();</diff>
      <filename>system/libraries/Controller.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Provides database access in a platform agnostic way, using simple query building blocks.
  *
- * $Id: Database.php 3295 2008-08-07 19:30:03Z zombor $
+ * $Id: Database.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -49,6 +49,9 @@ class Database_Core {
 	protected $offset     = FALSE;
 	protected $last_query = '';
 
+	// Stack of queries for push/pop
+	protected $query_history = array();
+
 	/**
 	 * Returns a singleton instance of Database.
 	 *
@@ -355,7 +358,9 @@ class Database_Core {
 	 */
 	public function join($table, $key, $value = NULL, $type = '')
 	{
-		if ($type != '')
+		$join = array();
+
+		if ( ! empty($type))
 		{
 			$type = strtoupper(trim($type));
 
@@ -377,23 +382,22 @@ class Database_Core {
 			$cond[] = $this-&gt;driver-&gt;where($key, $this-&gt;driver-&gt;escape_column($this-&gt;config['table_prefix'].$value), 'AND ', count($cond), FALSE);
 		}
 
-		if( ! isset($this-&gt;join['tables']) OR ! isset($this-&gt;join['conditions']))
-		{
-			$this-&gt;join['tables'] = array();
-			$this-&gt;join['conditions'] = array();
-		}
+		if( ! is_array($this-&gt;join)) { $this-&gt;join = array(); }
 
 		foreach ((array) $table as $t)
 		{
-			$this-&gt;join['tables'][] = $this-&gt;driver-&gt;escape_column($this-&gt;config['table_prefix'].$t);
+			$join['tables'][] = $this-&gt;driver-&gt;escape_column($this-&gt;config['table_prefix'].$t);
 		}
 
-		$this-&gt;join['conditions'][] = '('.trim(implode(' ', $cond)).')';
-		$this-&gt;join['type'] = $type;
+		$join['conditions'] = '('.trim(implode(' ', $cond)).')';
+		$join['type'] = $type;
+
+		$this-&gt;join[] = $join;
 
 		return $this;
 	}
 
+
 	/**
 	 * Selects the where(s) for a database query.
 	 *
@@ -620,6 +624,12 @@ class Database_Core {
 
 			if ($val != '')
 			{
+				// Add the table prefix if we are using table.column names
+				if(strpos($val, '.'))
+				{
+					$val = $this-&gt;config['table_prefix'].$val;
+				}
+
 				$this-&gt;groupby[] = $this-&gt;driver-&gt;escape_column($val);
 			}
 		}
@@ -673,11 +683,18 @@ class Database_Core {
 		{
 			$direction = strtoupper(trim($direction));
 
+			// Add a direction if the provided one isn't valid
 			if ( ! in_array($direction, array('ASC', 'DESC', 'RAND()', 'RANDOM()', 'NULL')))
 			{
 				$direction = 'ASC';
 			}
 
+			// Add the table prefix if a table.column was passed
+			if (strpos($column, '.'))
+			{
+				$column = $this-&gt;config['table_prefix'].$column;
+			}
+
 			$this-&gt;orderby[] = $this-&gt;driver-&gt;escape_column($column).' '.$direction;
 		}
 
@@ -896,7 +913,9 @@ class Database_Core {
 			}
 			$values = implode(&quot;,&quot;, $escaped_values);
 		}
-		$this-&gt;where($this-&gt;driver-&gt;escape_column($field).' '.($not === TRUE ? 'NOT ' : '').'IN ('.$values.')');
+
+		$where = $this-&gt;driver-&gt;escape_column(((strpos($field,'.') !== FALSE) ? $this-&gt;config['table_prefix'] : ''). $field).' '.($not === TRUE ? 'NOT ' : '').'IN ('.$values.')';
+		$this-&gt;where[] = $this-&gt;driver-&gt;where($where, '', 'AND ', count($this-&gt;where), -1);
 
 		return $this;
 	}
@@ -1093,9 +1112,7 @@ class Database_Core {
 	{
 		$this-&gt;link or $this-&gt;connect();
 
-		$this-&gt;reset_select();
-
-		return $this-&gt;driver-&gt;list_tables();
+		return $this-&gt;driver-&gt;list_tables($this);
 	}
 
 	/**
@@ -1253,6 +1270,65 @@ class Database_Core {
 		return $this-&gt;driver-&gt;stmt_prepare($sql, $this-&gt;config);
 	}
 
+	/**
+	 * Pushes existing query space onto the query stack.  Use push
+	 * and pop to prevent queries from clashing before they are
+	 * executed
+	 *
+	 * @return Database_Core This Databaes object
+	 */
+	public function push()
+	{	
+		array_push($this-&gt;query_history, array(
+			$this-&gt;select,
+			$this-&gt;from,
+			$this-&gt;join,
+			$this-&gt;where,
+			$this-&gt;orderby,
+			$this-&gt;order,
+			$this-&gt;groupby,
+			$this-&gt;having,
+			$this-&gt;distinct,
+			$this-&gt;limit,
+			$this-&gt;offset
+		));
+
+		$this-&gt;reset_select();
+
+		return $this;
+	}
+
+	/**
+	 * Pops from query stack into the current query space.
+	 *
+	 * @return Database_Core This Databaes object
+	 */
+	public function pop()
+	{
+		if (count($this-&gt;query_history) == 0)
+		{
+			// No history
+			return $this;
+		}
+	
+		list(
+			$this-&gt;select,
+			$this-&gt;from,
+			$this-&gt;join,
+			$this-&gt;where,
+			$this-&gt;orderby,
+			$this-&gt;order,
+			$this-&gt;groupby,
+			$this-&gt;having,
+			$this-&gt;distinct,
+			$this-&gt;limit,
+			$this-&gt;offset
+		) = array_pop($this-&gt;query_history);
+
+		return $this;
+	}
+
+
 } // End Database Class
 
 </diff>
      <filename>system/libraries/Database.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,10 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * The Encrypt library provides two-way encryption of text and binary strings
  * using the MCrypt extension.
  * @see http://php.net/mcrypt
  *
- * $Id: Encrypt.php 3263 2008-08-05 17:57:50Z PugFish $
+ * $Id: Encrypt.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/Encrypt.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Kohana event observer. Uses the SPL observer pattern.
  *
- * $Id: Event_Observer.php 2337 2008-03-24 19:17:38Z Shadowhand $
+ * $Id: Event_Observer.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/Event_Observer.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Kohana event subject. Uses the SPL observer pattern.
  *
- * $Id: Event_Subject.php 2337 2008-03-24 19:17:38Z Shadowhand $
+ * $Id: Event_Subject.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/Event_Subject.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,9 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Manipulate images using standard methods such as resize, crop, rotate, etc.
  * This class must be re-initialized for every image you wish to manipulate.
  *
- * $Id: Image.php 3246 2008-08-01 13:42:09Z OscarB $
+ * $Id: Image.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Image
  * @author     Kohana Team
@@ -303,9 +303,10 @@ class Image_Core {
 	 * @throws  Kohana_Exception
 	 * @param   string   new image filename
 	 * @param   integer  permissions for new image
+	 * @param   boolean  keep or discard image process actions
 	 * @return  object
 	 */
-	public function save($new_image = FALSE, $chmod = 0644)
+	public function save($new_image = FALSE, $chmod = 0644, $keep_actions = FALSE)
 	{
 		// If no new image is defined, use the current image
 		empty($new_image) and $new_image = $this-&gt;image['file'];
@@ -328,37 +329,40 @@ class Image_Core {
 				chmod($new_image, $chmod);
 			}
 		}
-
-		// Reset the actions
-		$this-&gt;actions = array();
-
+		
+		// Reset actions. Subsequent save() or render() will not apply previous actions.
+		if ($keep_actions === FALSE)
+			$this-&gt;actions = array();
+		
 		return $status;
 	}
 	
- 	/** 
- 	 * Output the image to the browser. 
- 	 * 
- 	 * @return	object 
- 	 */ 
- 	public function render() 
- 	{ 
- 		$new_image = $this-&gt;image['file']; 
-  
- 		// Separate the directory and filename 
- 		$dir  = pathinfo($new_image, PATHINFO_DIRNAME); 
- 		$file = pathinfo($new_image, PATHINFO_BASENAME); 
-  
- 		// Normalize the path 
- 		$dir = str_replace('\\', '/', realpath($dir)).'/'; 
-  
- 		// Process the image with the driver 
- 		$status = $this-&gt;driver-&gt;process($this-&gt;image, $this-&gt;actions, $dir, $file, $render = TRUE); 
-  
- 		// Reset the actions 
- 		$this-&gt;actions = array(); 
-  
- 		return $status; 
- 	}
+	/** 
+	 * Output the image to the browser. 
+	 * 
+	 * @param   boolean  keep or discard image process actions
+	 * @return	object 
+	 */ 
+	public function render($keep_actions = FALSE) 
+	{ 
+		$new_image = $this-&gt;image['file']; 
+	
+		// Separate the directory and filename 
+		$dir  = pathinfo($new_image, PATHINFO_DIRNAME); 
+		$file = pathinfo($new_image, PATHINFO_BASENAME); 
+	
+		// Normalize the path 
+		$dir = str_replace('\\', '/', realpath($dir)).'/'; 
+	
+		// Process the image with the driver 
+		$status = $this-&gt;driver-&gt;process($this-&gt;image, $this-&gt;actions, $dir, $file, $render = TRUE); 
+		
+		// Reset actions. Subsequent save() or render() will not apply previous actions.
+		if ($keep_actions === FALSE)
+			$this-&gt;actions = array();
+		
+		return $status; 
+	}
 
 	/**
 	 * Sanitize a given value type.</diff>
      <filename>system/libraries/Image.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Input library.
  *
- * $Id: Input.php 3250 2008-08-02 11:58:29Z armen $
+ * $Id: Input.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -83,16 +83,13 @@ class Input_Core {
 				$preserve = array('GLOBALS', '_REQUEST', '_GET', '_POST', '_FILES', '_COOKIE', '_SERVER', '_ENV', '_SESSION');
 
 				// This loop has the same effect as disabling register_globals
-				foreach ($GLOBALS as $key =&gt; $val)
+				foreach (array_diff(array_keys($GLOBALS), $preserve) as $key)
 				{
-					if ( ! in_array($key, $preserve))
-					{
-						global $$key;
-						$$key = NULL;
-
-						// Unset the global variable
-						unset($GLOBALS[$key], $$key);
-					}
+					global $$key;
+					$$key = NULL;
+
+					// Unset the global variable
+					unset($GLOBALS[$key], $$key);
 				}
 
 				// Warn the developer about register globals
@@ -129,6 +126,10 @@ class Input_Core {
 			{
 				foreach ($_COOKIE as $key =&gt; $val)
 				{
+					// Ignore special attributes in RFC2109 compliant cookies
+					if ($key == '$Version' OR $key == '$Path' OR $key == '$Domain')
+						continue;
+
 					// Sanitize $_COOKIE
 					$_COOKIE[$this-&gt;clean_input_keys($key)] = $this-&gt;clean_input_data($val);
 				}</diff>
      <filename>system/libraries/Input.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,16 +1,17 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Model base class.
  *
- * $Id: Model.php 3002 2008-07-08 14:19:12Z Shadowhand $
+ * $Id: Model.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
- * @copyright  (c) 2007-2008 Kohana Team
+ * @copyright  (c) 2007-2009 Kohana Team
  * @license    http://kohanaphp.com/license.html
  */
 class Model_Core {
 
+	// Database object
 	protected $db;
 
 	/**</diff>
      <filename>system/libraries/Model.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,14 +1,16 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
- * Object Relational Mapping (ORM) is a method of abstracting database
- * access to standard PHP calls. All table rows are represented as a model.
+ * [Object Relational Mapping][ref-orm] (ORM) is a method of abstracting database
+ * access to standard PHP calls. All table rows are represented as model objects,
+ * with object properties representing row data. ORM in Kohana generally follows
+ * the [Active Record][ref-act] pattern.
  *
- * @see http://en.wikipedia.org/wiki/Active_record
- * @see http://en.wikipedia.org/wiki/Object-relational_mapping
+ * [ref-orm]: http://wikipedia.org/wiki/Object-relational_mapping
+ * [ref-act]: http://wikipedia.org/wiki/Active_record
  *
- * $Id: ORM.php 3304 2008-08-08 18:45:30Z Shadowhand $
+ * $Id: ORM.php 3917 2009-01-21 03:06:22Z zombor $
  *
- * @package    Core
+ * @package    ORM
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
  * @license    http://kohanaphp.com/license.html
@@ -21,18 +23,24 @@ class ORM_Core {
 	protected $has_many                = array();
 	protected $has_and_belongs_to_many = array();
 
+	// Relationships that should always be joined
+	protected $load_with = array();
+
 	// Current object
 	protected $object  = array();
 	protected $changed = array();
+	protected $related = array();
 	protected $loaded  = FALSE;
 	protected $saved   = FALSE;
-	protected $sorting = array('id' =&gt; 'asc');
+	protected $sorting;
 
 	// Related objects
-	protected $related = array();
+	protected $object_relations = array();
+	protected $changed_relations = array();
 
 	// Model table information
 	protected $object_name;
+	protected $object_plural;
 	protected $table_name;
 	protected $table_columns;
 	protected $ignored_columns;
@@ -41,6 +49,9 @@ class ORM_Core {
 	protected $primary_key = 'id';
 	protected $primary_val = 'name';
 
+	// Array of foreign key name overloads
+	protected $foreign_key = array();
+
 	// Model configuration
 	protected $table_names_plural = TRUE;
 	protected $reload_on_wakeup   = TRUE;
@@ -49,6 +60,12 @@ class ORM_Core {
 	protected $db = 'default';
 	protected $db_applied = array();
 
+	// With calls already applied
+	protected $with_applied = array();
+
+	// Stores column information for ORM models
+	protected static $column_cache = array();
+
 	/**
 	 * Creates and returns a new model.
 	 *
@@ -73,26 +90,28 @@ class ORM_Core {
 	 */
 	public function __construct($id = NULL)
 	{
-		// Set the object name
-		$this-&gt;object_name = strtolower(substr(get_class($this), 0, -6));
+		// Set the object name and plural name
+		$this-&gt;object_name   = strtolower(substr(get_class($this), 0, -6));
+		$this-&gt;object_plural = inflector::plural($this-&gt;object_name);
+
+		if (!isset($this-&gt;sorting))
+		{
+			// Default sorting
+			$this-&gt;sorting = array($this-&gt;primary_key =&gt; 'asc');
+		}
 
 		// Initialize database
 		$this-&gt;__initialize();
 
-		if ($id === NULL OR $id === '')
-		{
-			// Clear the object
-			$this-&gt;clear();
-		}
-		elseif (is_object($id))
-		{
-			// Object is loaded and saved
-			$this-&gt;loaded = $this-&gt;saved = TRUE;
+		// Clear the object
+		$this-&gt;clear();
 
+		if (is_object($id))
+		{
 			// Load an object
 			$this-&gt;load_values((array) $id);
 		}
-		else
+		elseif (!empty($id))
 		{
 			// Find an object
 			$this-&gt;find($id);
@@ -195,7 +214,7 @@ class ORM_Core {
 			{
 				// We use switch here to manually call the database methods. This is
 				// done for speed: call_user_func_array can take over 300% longer to
-				// make calls. Mose database methods are 4 arguments or less, so this
+				// make calls. Most database methods are 4 arguments or less, so this
 				// avoids almost any calls to call_user_func_array.
 
 				switch ($num_args)
@@ -243,7 +262,7 @@ class ORM_Core {
 		{
 			return NULL;
 		}
-		elseif (isset($this-&gt;object[$column]) OR array_key_exists($column, $this-&gt;object))
+		elseif (array_key_exists($column, $this-&gt;object))
 		{
 			return $this-&gt;object[$column];
 		}
@@ -255,18 +274,14 @@ class ORM_Core {
 		{
 			return $this-&gt;object[$this-&gt;primary_key];
 		}
-		elseif (($owner = isset($this-&gt;has_one[$column])) OR isset($this-&gt;belongs_to[$column]))
+		elseif ($model = $this-&gt;related_object($column))
 		{
-			// Determine the model name
-			$model = ($owner === TRUE) ? $this-&gt;has_one[$column] : $this-&gt;belongs_to[$column];
-
-			// Load model
-			$model = ORM::factory($model);
+			// This handles the has_one and belongs_to relationships
 
-			if (isset($this-&gt;object[$column.'_'.$model-&gt;primary_key]))
+			if (array_key_exists($column.'_'.$model-&gt;primary_key, $this-&gt;object))
 			{
 				// Use the FK that exists in this model as the PK
-				$where = array($model-&gt;primary_key =&gt; $this-&gt;object[$column.'_'.$model-&gt;primary_key]);
+				$where = array($model-&gt;table_name.'.'.$model-&gt;primary_key =&gt; $this-&gt;object[$column.'_'.$model-&gt;primary_key]);
 			}
 			else
 			{
@@ -277,24 +292,6 @@ class ORM_Core {
 			// one&lt;&gt;alias:one relationship
 			return $this-&gt;related[$column] = $model-&gt;find($where);
 		}
-		elseif (in_array($column, $this-&gt;has_one) OR in_array($column, $this-&gt;belongs_to))
-		{
-			$model = ORM::factory($column);
-
-			if (isset($this-&gt;object[$column.'_'.$model-&gt;primary_key]))
-			{
-				// Use the FK that exists in this model as the PK
-				$where = array($model-&gt;primary_key =&gt; $this-&gt;object[$column.'_'.$model-&gt;primary_key]);
-			}
-			else
-			{
-				// Use this model PK as the FK
-				$where = array($this-&gt;foreign_key() =&gt; $this-&gt;object[$this-&gt;primary_key]);
-			}
-
-			// one&lt;&gt;one relationship
-			return $this-&gt;related[$column] = ORM::factory($column, $where);
-		}
 		elseif (isset($this-&gt;has_many[$column]))
 		{
 			// Load the &quot;middle&quot; model
@@ -326,23 +323,27 @@ class ORM_Core {
 			// Load the remote model, always singular
 			$model = ORM::factory(inflector::singular($column));
 
-			// Load JOIN info
-			$join_table = $model-&gt;join_table($this-&gt;table_name);
-			$join_col1  = $model-&gt;foreign_key(NULL, $join_table);
-			$join_col2  = $model-&gt;foreign_key(TRUE);
-
-			// many&lt;&gt;many relationship
-			return $this-&gt;related[$column] = $model
-				-&gt;join($join_table, $join_col1, $join_col2)
-				-&gt;where($this-&gt;foreign_key(NULL, $join_table), $this-&gt;object[$this-&gt;primary_key])
-				-&gt;find_all();
+			if ($this-&gt;has($model, TRUE))
+			{
+				// many&lt;&gt;many relationship
+				return $this-&gt;related[$column] = $model
+					-&gt;in($model-&gt;table_name.'.'.$model-&gt;primary_key, $this-&gt;changed_relations[$column])
+					-&gt;find_all();
+			}
+			else
+			{
+				// empty many&lt;&gt;many relationship
+				return $this-&gt;related[$column] = $model
+					-&gt;where($model-&gt;table_name.'.'.$model-&gt;primary_key, NULL)
+					-&gt;find_all();
+			}
 		}
 		elseif (in_array($column, array
 			(
-				'object_name', // Object
+				'object_name', 'object_plural', // Object
 				'primary_key', 'primary_val', 'table_name', 'table_columns', // Table
 				'loaded', 'saved', // Status
-				'has_one', 'belongs_to', 'has_many', 'has_and_belongs_to_many', // Relationships
+				'has_one', 'belongs_to', 'has_many', 'has_and_belongs_to_many', 'load_with' // Relationships
 			)))
 		{
 			// Model meta information
@@ -380,6 +381,26 @@ class ORM_Core {
 
 			$this-&gt;object[$column] = $this-&gt;load_type($column, $value);
 		}
+		elseif (in_array($column, $this-&gt;has_and_belongs_to_many) AND is_array($value))
+		{
+			// Load relations
+			$model = ORM::factory(inflector::singular($column));
+
+			if ( ! isset($this-&gt;object_relations[$column]))
+			{
+				// Load relations
+				$this-&gt;has($model);
+			}
+
+			// Change the relationships
+			$this-&gt;changed_relations[$column] = $value;
+
+			if (isset($this-&gt;related[$column]))
+			{
+				// Force a reload of the relationships
+				unset($this-&gt;related[$column]);
+			}
+		}
 		else
 		{
 			throw new Kohana_Exception('core.invalid_property', $column, get_class($this));
@@ -425,7 +446,108 @@ class ORM_Core {
 	 */
 	public function as_array()
 	{
-		return $this-&gt;object;
+		$object = array();
+
+		foreach ($this-&gt;object as $key =&gt; $val)
+		{
+			// Reconstruct the array (calls __get)
+			$object[$key] = $this-&gt;$key;
+		}
+
+		return $object;
+	}
+
+	/**
+	 * Binds another one-to-one object to this model.  One-to-one objects
+	 * can be nested using 'object1:object2' syntax
+	 *
+	 * @param string $object
+	 * @return void
+	 */
+	public function with($object)
+	{
+		if (isset($this-&gt;with_applied[$object]))
+		{
+			// Don't join anything already joined
+			return $this;
+		}
+
+		$prefix = $table = $object;
+
+		// Split object parts
+		$objects = explode(':', $object);
+		$object	 = $this;
+		foreach ($objects as $object_part)
+		{
+			// Go down the line of objects to find the given target
+			$parent = $object;
+			$object = $parent-&gt;related_object($object_part);
+
+			if ( ! $object)
+			{
+				// Can't find related object
+				return $this;
+			}
+		}
+
+		$table = $object_part;
+
+		if ($this-&gt;table_names_plural)
+		{
+			$table = inflector::plural($table);
+		}
+
+		// Pop-off top object to get the parent object (user:photo:tag's parent is user:photo)
+		array_pop($objects);
+		$parent_prefix = implode(':', $objects);
+
+		if (empty($parent_prefix))
+		{
+			// Use this table name itself for the parent prefix
+			$parent_prefix = $this-&gt;table_name;
+		}
+		else
+		{
+			if( ! isset($this-&gt;with_applied[$parent_prefix]))
+			{
+				// If the parent object hasn't been joined yet, do it first (otherwise LEFT JOINs fail)
+				$this-&gt;with($parent_prefix);
+			}
+		}
+
+		// Add to with_applied to prevent duplicate joins
+		$this-&gt;with_applied[$prefix] = TRUE;
+
+		// Use the keys of the empty object to determine the columns
+		$select = array_keys($object-&gt;as_array());
+		foreach ($select as $i =&gt; $column)
+		{
+			// Add the prefix so that load_result can determine the relationship
+			$select[$i] = $prefix.'.'.$column.' AS '.$prefix.':'.$column;
+		}
+
+		// Select all of the prefixed keys in the object
+		$this-&gt;db-&gt;select($select);
+
+		// Use last object part to generate foreign key
+		$foreign_key = $object_part.'_'.$object-&gt;primary_key;
+
+		if (array_key_exists($foreign_key, $parent-&gt;object))
+		{
+			// Foreign key exists in the joined object's parent
+			$join_col1 = $object-&gt;foreign_key(TRUE, $prefix);
+			$join_col2 = $parent_prefix.'.'.$foreign_key;
+		}
+		else
+		{
+			$join_col1 = $parent-&gt;foreign_key(NULL, $prefix);
+			$join_col2 = $parent_prefix.'.'.$parent-&gt;primary_key;
+		}
+
+		// Join the related object into the result
+		$this-&gt;db-&gt;join($object-&gt;table_name.' AS '.$this-&gt;db-&gt;table_prefix().$prefix, $join_col1, $join_col2, 'LEFT');
+
+		return $this;
 	}
 
 	/**
@@ -447,7 +569,7 @@ class ORM_Core {
 			else
 			{
 				// Search for a specific column
-				$this-&gt;db-&gt;where($this-&gt;unique_key($id), $id);
+				$this-&gt;db-&gt;where($this-&gt;table_name.'.'.$this-&gt;unique_key($id), $id);
 			}
 		}
 
@@ -462,24 +584,18 @@ class ORM_Core {
 	 * @param   integer  SQL offset
 	 * @return  ORM_Iterator
 	 */
-	public function find_all($limit = NULL, $offset = 0)
+	public function find_all($limit = NULL, $offset = NULL)
 	{
-		if ($limit !== NULL)
+		if ($limit !== NULL AND ! isset($this-&gt;db_applied['limit']))
 		{
 			// Set limit
-			$this-&gt;db-&gt;limit($limit);
+			$this-&gt;limit($limit);
 		}
 
-		if ($offset !== NULL)
+		if ($offset !== NULL AND ! isset($this-&gt;db_applied['offset']))
 		{
 			// Set offset
-			$this-&gt;db-&gt;offset($offset);
-		}
-
-		if ( ! isset($this-&gt;db_applied['orderby']))
-		{
-			// Apply sorting
-			$this-&gt;db-&gt;orderby($this-&gt;sorting);
+			$this-&gt;offset($offset);
 		}
 
 		return $this-&gt;load_result(TRUE);
@@ -493,8 +609,18 @@ class ORM_Core {
 	 * @param   string  value column
 	 * @return  array
 	 */
-	public function select_list($key, $val)
+	public function select_list($key = NULL, $val = NULL)
 	{
+		if ($key === NULL)
+		{
+			$key = $this-&gt;primary_key;
+		}
+
+		if ($val === NULL)
+		{
+			$val = $this-&gt;primary_val;
+		}
+
 		// Return a select list from the results
 		return $this-&gt;select($key, $val)-&gt;find_all()-&gt;select_list($key, $val);
 	}
@@ -512,10 +638,19 @@ class ORM_Core {
 		{
 			$safe_array = $array-&gt;safe_array();
 
-			foreach ($safe_array as $key =&gt; $val)
+			foreach ($safe_array as $key =&gt; $value)
 			{
+				// Get the value from this object
+				$value = $this-&gt;$key;
+
+				if (is_object($value) AND $value instanceof ORM_Iterator)
+				{
+					// Convert the value to an array of primary keys
+					$value = $value-&gt;primary_key_array();
+				}
+
 				// Pre-fill data
-				$array[$key] = $this-&gt;$key;
+				$array[$key] = $value;
 			}
 		}
 
@@ -524,10 +659,10 @@ class ORM_Core {
 		{
 			$safe_array = $array-&gt;safe_array();
 
-			foreach ($safe_array as $key =&gt; $val)
+			foreach ($safe_array as $key =&gt; $value)
 			{
 				// Set new data
-				$this-&gt;$key = $val;
+				$this-&gt;$key = $value;
 			}
 
 			if ($save === TRUE OR is_string($save))
@@ -548,51 +683,114 @@ class ORM_Core {
 	}
 
 	/**
-	 * Saves the current object. If the object is new, it will be reloaded
-	 * after being saved.
+	 * Saves the current object.
 	 *
 	 * @chainable
 	 * @return  ORM
 	 */
 	public function save()
 	{
-		if (empty($this-&gt;changed))
-			return $this;
-
-		$data = array();
-		foreach ($this-&gt;changed as $column)
+		if ( ! empty($this-&gt;changed))
 		{
-			// Compile changed data
-			$data[$column] = $this-&gt;object[$column];
-		}
+			$data = array();
+			foreach ($this-&gt;changed as $column)
+			{
+				// Compile changed data
+				$data[$column] = $this-&gt;object[$column];
+			}
 
-		if ($this-&gt;loaded === TRUE)
-		{
-			$query = $this-&gt;db
-				-&gt;where($this-&gt;primary_key, $this-&gt;object[$this-&gt;primary_key])
-				-&gt;update($this-&gt;table_name, $data);
+			if ($this-&gt;loaded === TRUE)
+			{
+				$query = $this-&gt;db
+					-&gt;where($this-&gt;primary_key, $this-&gt;object[$this-&gt;primary_key])
+					-&gt;update($this-&gt;table_name, $data);
+
+				// Object has been saved
+				$this-&gt;saved = TRUE;
+			}
+			else
+			{
+				$query = $this-&gt;db
+					-&gt;insert($this-&gt;table_name, $data);
 
-			// Object has been saved
-			$this-&gt;saved = TRUE;
+				if ($query-&gt;count() &gt; 0)
+				{
+					if (empty($this-&gt;object[$this-&gt;primary_key]))
+					{
+						// Load the insert id as the primary key
+						$this-&gt;object[$this-&gt;primary_key] = $query-&gt;insert_id();
+					}
+
+					// Object is now loaded and saved
+					$this-&gt;loaded = $this-&gt;saved = TRUE;
+				}
+			}
 
-			// Nothing has been changed
-			$this-&gt;changed = array();
+			if ($this-&gt;saved === TRUE)
+			{
+				// All changes have been saved
+				$this-&gt;changed = array();
+			}
 		}
-		else
-		{
-			$query = $this-&gt;db
-				-&gt;insert($this-&gt;table_name, $data);
 
-			if ($query-&gt;count() &gt; 0)
+		if ($this-&gt;saved === TRUE AND ! empty($this-&gt;changed_relations))
+		{
+			foreach ($this-&gt;changed_relations as $column =&gt; $values)
 			{
-				if (empty($this-&gt;object[$this-&gt;primary_key]))
+				// All values that were added
+				$added = array_diff($values, $this-&gt;object_relations[$column]);
+
+				// All values that were saved
+				$removed = array_diff($this-&gt;object_relations[$column], $values);
+
+				if (empty($added) AND empty($removed))
 				{
-					// Load the insert id as the primary key
-					$this-&gt;object[$this-&gt;primary_key] = $query-&gt;insert_id();
+					// No need to bother
+					continue;
 				}
 
-				// Reload the object
-				$this-&gt;reload();
+				// Clear related columns
+				unset($this-&gt;related[$column]);
+
+				// Load the model
+				$model = ORM::factory(inflector::singular($column));
+
+				if (($join_table = array_search($column, $this-&gt;has_and_belongs_to_many)) === FALSE)
+					continue;
+
+				if (is_int($join_table))
+				{
+					// No &quot;through&quot; table, load the default JOIN table
+					$join_table = $model-&gt;join_table($this-&gt;table_name);
+				}
+
+				// Foreign keys for the join table
+				$object_fk  = $this-&gt;foreign_key(NULL);
+				$related_fk = $model-&gt;foreign_key(NULL);
+
+				if ( ! empty($added))
+				{
+					foreach ($added as $id)
+					{
+						// Insert the new relationship
+						$this-&gt;db-&gt;insert($join_table, array
+						(
+							$object_fk  =&gt; $this-&gt;object[$this-&gt;primary_key],
+							$related_fk =&gt; $id,
+						));
+					}
+				}
+
+				if ( ! empty($removed))
+				{
+					$this-&gt;db
+						-&gt;where($object_fk, $this-&gt;object[$this-&gt;primary_key])
+						-&gt;in($related_fk, $removed)
+						-&gt;delete($join_table);
+				}
+
+				// Clear all relations for this column
+				unset($this-&gt;object_relations[$column], $this-&gt;changed_relations[$column]);
 			}
 		}
 
@@ -635,11 +833,16 @@ class ORM_Core {
 			// Delete only given ids
 			$this-&gt;db-&gt;in($this-&gt;primary_key, $ids);
 		}
-		else
+		elseif (is_null($ids))
 		{
 			// Delete all records
 			$this-&gt;db-&gt;where(TRUE);
 		}
+		else
+		{
+			// Do nothing - safeguard
+			return $this;
+		}
 
 		// Delete all objects
 		$this-&gt;db-&gt;delete($this-&gt;table_name);
@@ -655,14 +858,12 @@ class ORM_Core {
 	 */
 	public function clear()
 	{
-		// Object is no longer loaded or saved
-		$this-&gt;loaded = $this-&gt;saved = FALSE;
-
-		// Nothing has been changed
-		$this-&gt;changed = array();
+		// Create an array with all the columns set to NULL
+		$columns = array_keys($this-&gt;table_columns);
+		$values  = array_combine($columns, array_fill(0, count($columns), NULL));
 
 		// Replace the current object with an empty one
-		$this-&gt;load_values(array());
+		$this-&gt;load_values($values);
 
 		return $this;
 	}
@@ -689,11 +890,16 @@ class ORM_Core {
 	{
 		if ($force === TRUE OR empty($this-&gt;table_columns))
 		{
-			// Load table columns
-			$this-&gt;table_columns = $this-&gt;db-&gt;list_fields($this-&gt;table_name);
-
-			if (empty($this-&gt;table_columns))
-				throw new Kohana_Exception('database.table_not_found', $this-&gt;table);
+			if (isset(self::$column_cache[$this-&gt;object_name]))
+			{
+				// Use cached column information
+				$this-&gt;table_columns = self::$column_cache[$this-&gt;object_name];
+			}
+			else
+			{
+				// Load table columns
+				self::$column_cache[$this-&gt;object_name] = $this-&gt;table_columns = $this-&gt;db-&gt;list_fields($this-&gt;table_name, TRUE);
+			}
 		}
 
 		return $this;
@@ -703,14 +909,14 @@ class ORM_Core {
 	 * Tests if this object has a relationship to a different model.
 	 *
 	 * @param   object   related ORM model
+	 * @param   boolean  check for any relations to given model
 	 * @return  boolean
 	 */
-	public function has(ORM $model)
+	public function has(ORM $model, $any = FALSE)
 	{
-		if ( ! $this-&gt;loaded)
-			return FALSE;
+		$related = $model-&gt;object_plural;
 
-		if (($join_table = array_search(inflector::plural($model-&gt;object_name), $this-&gt;has_and_belongs_to_many)) === FALSE)
+		if (($join_table = array_search($related, $this-&gt;has_and_belongs_to_many)) === FALSE)
 			return FALSE;
 
 		if (is_int($join_table))
@@ -719,16 +925,26 @@ class ORM_Core {
 			$join_table = $model-&gt;join_table($this-&gt;table_name);
 		}
 
-		if ($model-&gt;loaded)
+		if ( ! isset($this-&gt;object_relations[$related]))
 		{
-			// Select only objects of a specific id
-			$this-&gt;db-&gt;where($model-&gt;foreign_key(NULL, $join_table), $model-&gt;primary_key_value);
+			// Load the object relationships
+			$this-&gt;changed_relations[$related] = $this-&gt;object_relations[$related] = $this-&gt;load_relations($join_table, $model);
 		}
 
-		// Return the number of rows that exist
-		return $this-&gt;db
-			-&gt;where($this-&gt;foreign_key(NULL, $join_table), $this-&gt;object[$this-&gt;primary_key])
-			-&gt;count_records($join_table);
+		if ( ! $model-&gt;empty_primary_key())
+		{
+			// Check if a specific object exists
+			return in_array($model-&gt;primary_key_value, $this-&gt;changed_relations[$related]);
+		}
+		elseif ($any)
+		{
+			// Check if any relations to given model exist
+			return ! empty($this-&gt;changed_relations[$related]);
+		}
+		else
+		{
+			return FALSE;
+		}
 	}
 
 	/**
@@ -739,28 +955,21 @@ class ORM_Core {
 	 */
 	public function add(ORM $model)
 	{
-		if ( ! $this-&gt;loaded)
-			return FALSE;
-
 		if ($this-&gt;has($model))
 			return TRUE;
 
-		if (($join_table = array_search(inflector::plural($model-&gt;object_name), $this-&gt;has_and_belongs_to_many)) === FALSE)
-			return FALSE;
+		// Get the faked column name
+		$column = $model-&gt;object_plural;
 
-		if (is_int($join_table))
+		// Add the new relation to the update
+		$this-&gt;changed_relations[$column][] = $model-&gt;primary_key_value;
+
+		if (isset($this-&gt;related[$column]))
 		{
-			// No &quot;through&quot; table, load the default JOIN table
-			$join_table = $model-&gt;join_table($this-&gt;table_name);
+			// Force a reload of the relationships
+			unset($this-&gt;related[$column]);
 		}
 
-		// Insert the new relationship
-		$this-&gt;db-&gt;insert($join_table, array
-		(
-			$this-&gt;foreign_key(NULL, $join_table)  =&gt; $this-&gt;object[$this-&gt;primary_key],
-			$model-&gt;foreign_key(NULL, $join_table) =&gt; $model-&gt;primary_key_value,
-		));
-
 		return TRUE;
 	}
 
@@ -775,26 +984,22 @@ class ORM_Core {
 		if ( ! $this-&gt;has($model))
 			return FALSE;
 
-		if (($join_table = array_search(inflector::plural($model-&gt;object_name), $this-&gt;has_and_belongs_to_many)) === FALSE)
+		// Get the faked column name
+		$column = $model-&gt;object_plural;
+
+		if (($key = array_search($model-&gt;primary_key_value, $this-&gt;changed_relations[$column])) === FALSE)
 			return FALSE;
 
-		if (is_int($join_table))
-		{
-			// No &quot;through&quot; table, load the default JOIN table
-			$join_table = $model-&gt;join_table($this-&gt;table_name);
-		}
+		// Remove the relationship
+		unset($this-&gt;changed_relations[$column][$key]);
 
-		if ($model-&gt;loaded)
+		if (isset($this-&gt;related[$column]))
 		{
-			// Delete only a specific object
-			$this-&gt;db-&gt;where($model-&gt;foreign_key(NULL, $join_table), $model-&gt;primary_key_value);
+			// Force a reload of the relationships
+			unset($this-&gt;related[$column]);
 		}
 
-		// Return the number of rows deleted
-		return $this-&gt;db
-			-&gt;where($this-&gt;foreign_key(NULL, $join_table), $this-&gt;object[$this-&gt;primary_key])
-			-&gt;delete($join_table)
-			-&gt;count();
+		return TRUE;
 	}
 
 	/**
@@ -820,13 +1025,13 @@ class ORM_Core {
 			if (stripos($sql, 'LIMIT') !== FALSE)
 			{
 				// Remove LIMIT from the SQL
-				$sql = preg_replace('/\bLIMIT\s+[^a-z]+/i', '', $sql);
+				$sql = preg_replace('/\sLIMIT\s+[^a-z]+/i', ' ', $sql);
 			}
 
 			if (stripos($sql, 'OFFSET') !== FALSE)
 			{
 				// Remove OFFSET from the SQL
-				$sql = preg_replace('/\bOFFSET\s+\d+/i', '', $sql);
+				$sql = preg_replace('/\sOFFSET\s+\d+/i', '', $sql);
 			}
 
 			// Get the total rows from the last query executed
@@ -836,11 +1041,8 @@ class ORM_Core {
 				'FROM ('.trim($sql).') AS '.$this-&gt;db-&gt;escape_table('counted_results')
 			);
 
-			if ($result-&gt;count())
-			{
-				// Return the total number of rows from the query
-				return (int) $result-&gt;current()-&gt;total_rows;
-			}
+			// Return the total number of rows from the query
+			return (int) $result-&gt;current()-&gt;total_rows;
 		}
 
 		return FALSE;
@@ -919,8 +1121,16 @@ class ORM_Core {
 	{
 		if ($table === TRUE)
 		{
-			// Return the name of this tables PK
-			return $this-&gt;table_name.'.'.$this-&gt;primary_key;
+			if (is_string($prefix_table))
+			{
+				// Use prefix table name and this table's PK
+				return $prefix_table.'.'.$this-&gt;primary_key;
+			}
+			else
+			{
+				// Return the name of this table's PK
+				return $this-&gt;table_name.'.'.$this-&gt;primary_key;
+			}
 		}
 
 		if (is_string($prefix_table))
@@ -929,19 +1139,35 @@ class ORM_Core {
 			$prefix_table .= '.';
 		}
 
-		if ( ! is_string($table) OR ! isset($this-&gt;object[$table.'_'.$this-&gt;primary_key]))
+		if (isset($this-&gt;foreign_key[$table]))
 		{
-			// Use this table
-			$table = $this-&gt;table_name;
-
-			if ($this-&gt;table_names_plural === TRUE)
+			// Use the defined foreign key name, no magic here!
+			$foreign_key = $this-&gt;foreign_key[$table];
+		}
+		else
+		{
+			if ( ! is_string($table) OR ! isset($this-&gt;object[$table.'_'.$this-&gt;primary_key]))
 			{
-				// Make the key name singular
-				$table = inflector::singular($table);
+				// Use this table
+				$table = $this-&gt;table_name;
+
+				if (strpos($table, '.') !== FALSE)
+				{
+					// Hack around support for PostgreSQL schemas
+					list ($schema, $table) = explode('.', $table, 2);
+				}
+
+				if ($this-&gt;table_names_plural === TRUE)
+				{
+					// Make the key name singular
+					$table = inflector::singular($table);
+				}
 			}
+
+			$foreign_key = $table.'_'.$this-&gt;primary_key;
 		}
 
-		return $prefix_table.$table.'_'.$this-&gt;primary_key;
+		return $prefix_table.$foreign_key;
 	}
 
 	/**
@@ -949,7 +1175,7 @@ class ORM_Core {
 	 *
 	 * Example: The joining table of users and roles would be roles_users,
 	 * because &quot;r&quot; comes before &quot;u&quot;. Joining products and categories would
-	 * result in categories_prouducts, because &quot;c&quot; comes before &quot;p&quot;.
+	 * result in categories_products, because &quot;c&quot; comes before &quot;p&quot;.
 	 *
 	 * Example: zoo &gt; zebra &gt; robber &gt; ocean &gt; angel &gt; aardvark
 	 *
@@ -971,6 +1197,87 @@ class ORM_Core {
 	}
 
 	/**
+	 * Returns an ORM model for the given object name;
+	 *
+	 * @param   string  object name
+	 * @return  ORM
+	 */
+	protected function related_object($object)
+	{
+		if (isset($this-&gt;has_one[$object]))
+		{
+			$object = ORM::factory($this-&gt;has_one[$object]);
+		}
+		elseif (isset($this-&gt;belongs_to[$object]))
+		{
+			$object = ORM::factory($this-&gt;belongs_to[$object]);
+		}
+		elseif (in_array($object, $this-&gt;has_one) OR in_array($object, $this-&gt;belongs_to))
+		{
+			$object = ORM::factory($object);
+		}
+		else
+		{
+			return FALSE;
+		}
+
+		return $object;
+	}
+
+	/**
+	 * Loads an array of values into into the current object.
+	 *
+	 * @chainable
+	 * @param   array  values to load
+	 * @return  ORM
+	 */
+	public function load_values(array $values)
+	{
+		if (array_key_exists($this-&gt;primary_key, $values))
+		{
+			// Replace the object and reset the object status
+			$this-&gt;object = $this-&gt;changed = $this-&gt;related = array();
+
+			// Set the loaded and saved object status based on the primary key
+			$this-&gt;loaded = $this-&gt;saved = ($values[$this-&gt;primary_key] !== NULL);
+		}
+
+		// Related objects
+		$related = array();
+
+		foreach ($values as $column =&gt; $value)
+		{
+			if (strpos($column, ':') === FALSE)
+			{
+				if (isset($this-&gt;table_columns[$column]))
+				{
+					// The type of the value can be determined, convert the value
+					$value = $this-&gt;load_type($column, $value);
+				}
+
+				$this-&gt;object[$column] = $value;
+			}
+			else
+			{
+				list ($prefix, $column) = explode(':', $column, 2);
+
+				$related[$prefix][$column] = $value;
+			}
+		}
+
+		if ( ! empty($related))
+		{
+			foreach ($related as $object =&gt; $values)
+			{
+				// Load the related objects with the values in the result
+				$this-&gt;related[$object] = $this-&gt;related_object($object)-&gt;load_values($values);
+			}
+		}
+
+		return $this;
+	}
+
+	/**
 	 * Loads a value according to the types defined by the column metadata.
 	 *
 	 * @param   string  column name
@@ -997,7 +1304,20 @@ class ORM_Core {
 		switch ($column['type'])
 		{
 			case 'int':
-				$value = ($value === '' AND ! empty($data['null'])) ? NULL : (int) $value;
+				if ($value === '' AND ! empty($column['null']))
+				{
+					// Forms will only submit strings, so empty integer values must be null
+					$value = NULL;
+				}
+				elseif ((float) $value &gt; PHP_INT_MAX)
+				{
+					// This number cannot be represented by a PHP integer, so we convert it to a string
+					$value = (string) $value;
+				}
+				else
+				{
+					$value = (int) $value;
+				}
 			break;
 			case 'float':
 				$value = (float) $value;
@@ -1014,33 +1334,6 @@ class ORM_Core {
 	}
 
 	/**
-	 * Loads an array of values into into the current object.
-	 *
-	 * @chainable
-	 * @param   array  values to load
-	 * @return  ORM
-	 */
-	protected function load_values(array $values)
-	{
-		// Get the table columns
-		$columns = array_keys($this-&gt;table_columns);
-
-		// Make sure all the columns are defined
-		$this-&gt;object += array_combine($columns, array_fill(0, count($columns), NULL));
-
-		foreach ($columns as $column)
-		{
-			// Value for this column
-			$value = isset($values[$column]) ? $values[$column] : NULL;
-
-			// Set value manually, to avoid triggering changes
-			$this-&gt;object[$column] = $this-&gt;load_type($column, $value);
-		}
-
-		return $this;
-	}
-
-	/**
 	 * Loads a database result, either as a new object for this model, or as
 	 * an iterator for multiple rows.
 	 *
@@ -1059,10 +1352,38 @@ class ORM_Core {
 
 		if ( ! isset($this-&gt;db_applied['select']))
 		{
-			// Selete all columns by default
+			// Select all columns by default
 			$this-&gt;db-&gt;select($this-&gt;table_name.'.*');
 		}
 
+		if ( ! empty($this-&gt;load_with))
+		{
+			foreach ($this-&gt;load_with as $object)
+			{
+				// Join each object into the results
+				$this-&gt;with($object);
+			}
+		}
+
+		if ( ! isset($this-&gt;db_applied['orderby']) AND ! empty($this-&gt;sorting))
+		{
+			$sorting = array();
+			foreach ($this-&gt;sorting as $column =&gt; $direction)
+			{
+				if (strpos($column, '.') === FALSE)
+				{
+					// Keeps sorting working properly when using JOINs on
+					// tables with columns of the same name
+					$column = $this-&gt;table_name.'.'.$column;
+				}
+
+				$sorting[$column] = $direction;
+			}
+
+			// Apply the user-defined sorting
+			$this-&gt;db-&gt;orderby($sorting);
+		}
+
 		// Load the result
 		$result = $this-&gt;db-&gt;get($this-&gt;table_name);
 
@@ -1074,12 +1395,6 @@ class ORM_Core {
 
 		if ($result-&gt;count() === 1)
 		{
-			// Model is loaded and saved
-			$this-&gt;loaded = $this-&gt;saved = TRUE;
-
-			// Clear relationships and changed values
-			$this-&gt;related = $this-&gt;changed = array();
-
 			// Load object values
 			$this-&gt;load_values($result-&gt;result(FALSE)-&gt;current());
 		}
@@ -1092,4 +1407,44 @@ class ORM_Core {
 		return $this;
 	}
 
-} // End ORM
\ No newline at end of file
+	/**
+	 * Return an array of all the primary keys of the related table.
+	 *
+	 * @param   string  table name
+	 * @param   object  ORM model to find relations of
+	 * @return  array
+	 */
+	protected function load_relations($table, ORM $model)
+	{
+		// Save the current query chain (otherwise the next call will clash)
+		$this-&gt;db-&gt;push();
+
+		$query = $this-&gt;db
+			-&gt;select($model-&gt;foreign_key(NULL).' AS id')
+			-&gt;from($table)
+			-&gt;where($this-&gt;foreign_key(NULL, $table), $this-&gt;object[$this-&gt;primary_key])
+			-&gt;get()
+			-&gt;result(TRUE);
+
+		$this-&gt;db-&gt;pop();
+
+		$relations = array();
+		foreach ($query as $row)
+		{
+			$relations[] = $row-&gt;id;
+		}
+
+		return $relations;
+	}
+
+	/**
+	 * Returns whether or not primary key is empty
+	 *
+	 * @return bool
+	 */
+	protected function empty_primary_key()
+	{
+		return (empty($this-&gt;object[$this-&gt;primary_key]) AND $this-&gt;object[$this-&gt;primary_key] !== '0');
+	}
+
+} // End ORM</diff>
      <filename>system/libraries/ORM.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,10 +1,10 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
 * Object Relational Mapping (ORM) result iterator.
 *
-* $Id: ORM_Iterator.php 3106 2008-07-13 22:27:01Z Shadowhand $
+* $Id: ORM_Iterator.php 3917 2009-01-21 03:06:22Z zombor $
 *
-* @package    Core
+* @package    ORM
 * @author     Kohana Team
 * @copyright  (c) 2007-2008 Kohana Team
 * @license    http://kohanaphp.com/license.html
@@ -19,7 +19,7 @@ class ORM_Iterator_Core implements Iterator, ArrayAccess, Countable {
 	// Database result object
 	protected $result;
 
-	public function __construct(ORM $model, $result)
+	public function __construct(ORM $model, Database_Result $result)
 	{
 		// Class attributes
 		$this-&gt;class_name  = get_class($model);
@@ -54,6 +54,21 @@ class ORM_Iterator_Core implements Iterator, ArrayAccess, Countable {
 	}
 
 	/**
+	 * Return an array of all of the primary keys for this object.
+	 *
+	 * @return  array
+	 */
+	public function primary_key_array()
+	{
+		$ids = array();
+		foreach ($this-&gt;result as $row)
+		{
+			$ids[] = $row-&gt;{$this-&gt;primary_key};
+		}
+		return $ids;
+	}
+
+	/**
 	 * Create a key/value array from the results.
 	 *
 	 * @param   string  key column</diff>
      <filename>system/libraries/ORM_Iterator.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,11 +1,11 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Object Relational Mapping (ORM) &quot;tree&quot; extension. Allows ORM objects to act
  * as trees, with parents and children.
  *
- * $Id: ORM_Tree.php 3122 2008-07-16 14:19:34Z Shadowhand $
+ * $Id: ORM_Tree.php 3917 2009-01-21 03:06:22Z zombor $
  *
- * @package    Core
+ * @package    ORM
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
  * @license    http://kohanaphp.com/license.html
@@ -33,10 +33,10 @@ class ORM_Tree_Core extends ORM {
 				// Load child model
 				$model = ORM::factory(inflector::singular($this-&gt;children));
 
-				if (isset($this-&gt;object[$this-&gt;parent_key]))
+				if (array_key_exists($this-&gt;parent_key, $this-&gt;object))
 				{
 					// Find children of this parent
-					$model-&gt;where($this-&gt;parent_key, $this-&gt;object[$this-&gt;parent_key])-&gt;find();
+					$model-&gt;where($model-&gt;primary_key, $this-&gt;object[$this-&gt;parent_key])-&gt;find();
 				}
 
 				$this-&gt;related[$column] = $model;</diff>
      <filename>system/libraries/ORM_Tree.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Pagination library.
  *
- * $Id: Pagination.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Pagination.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -118,7 +118,8 @@ class Pagination_Core {
 			$_GET[$this-&gt;query_string] = '{page}';
 
 			// Create full URL
-			$this-&gt;url = url::site(Router::$current_uri).'?'.str_replace('%7Bpage%7D', '{page}', http_build_query($_GET));
+			$base_url = ($this-&gt;base_url === '') ? Router::$current_uri : $this-&gt;base_url;
+			$this-&gt;url = url::site($base_url).'?'.str_replace('%7Bpage%7D', '{page}', http_build_query($_GET));
 
 			// Reset page number
 			$_GET[$this-&gt;query_string] = $this-&gt;current_page;</diff>
      <filename>system/libraries/Pagination.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Adds useful information to the bottom of the current page for debugging and optimization purposes.
  *
@@ -8,7 +8,7 @@
  * POST Data    - The name and values of any POST data submitted to the current page.
  * Cookie Data  - All cookies sent for the current request.
  *
- * $Id: Profiler.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Profiler.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Profiler
  * @author     Kohana Team</diff>
      <filename>system/libraries/Profiler.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,69 +1,69 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
-/**
- * Provides a table layout for sections in the Profiler library.
- *
- * $Id$
- *
- * @package    Profiler
- * @author     Kohana Team
- * @copyright  (c) 2007-2008 Kohana Team
- * @license    http://kohanaphp.com/license.html
- */
-class Profiler_Table_Core {
-
-	protected $columns = array();
-	protected $rows = array();
-
-	/**
-	 * Get styles for table.
-	 *
-	 * @return  string
-	 */
-	public function styles()
-	{
-		static $styles_output;
-
-		if ( ! $styles_output)
-		{
-			$styles_output = TRUE;
-			return file_get_contents(Kohana::find_file('views', 'kohana_profiler_table', FALSE, 'css'));
-		}
-
-		return '';
-	}
-
-	/**
-	 * Add column to table.
-	 *
-	 * @param  string  CSS class
-	 * @param  string  CSS style
-	 */
-	public function add_column($class = '', $style = '')
-	{
-		$this-&gt;columns[] = array('class' =&gt; $class, 'style' =&gt; $style);
-	}
-
-	/**
-	 * Add row to table.
-	 *
-	 * @param  array   data to go in table cells
-	 * @param  string  CSS class
-	 * @param  string  CSS style
-	 */
-	public function add_row($data, $class = '', $style = '')
-	{
-		$this-&gt;rows[] = array('data' =&gt; $data, 'class' =&gt; $class, 'style' =&gt; $style);
-	}
-
-	/**
-	 * Render table.
-	 *
-	 * @return  string
-	 */
-	public function render()
-	{
-		$data['rows'] = $this-&gt;rows;
-		$data['columns'] = $this-&gt;columns;
-		return View::factory('kohana_profiler_table', $data)-&gt;render();
-	}
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
+/**
+ * Provides a table layout for sections in the Profiler library.
+ *
+ * $Id$
+ *
+ * @package    Profiler
+ * @author     Kohana Team
+ * @copyright  (c) 2007-2008 Kohana Team
+ * @license    http://kohanaphp.com/license.html
+ */
+class Profiler_Table_Core {
+
+	protected $columns = array();
+	protected $rows = array();
+
+	/**
+	 * Get styles for table.
+	 *
+	 * @return  string
+	 */
+	public function styles()
+	{
+		static $styles_output;
+
+		if ( ! $styles_output)
+		{
+			$styles_output = TRUE;
+			return file_get_contents(Kohana::find_file('views', 'kohana_profiler_table', FALSE, 'css'));
+		}
+
+		return '';
+	}
+
+	/**
+	 * Add column to table.
+	 *
+	 * @param  string  CSS class
+	 * @param  string  CSS style
+	 */
+	public function add_column($class = '', $style = '')
+	{
+		$this-&gt;columns[] = array('class' =&gt; $class, 'style' =&gt; $style);
+	}
+
+	/**
+	 * Add row to table.
+	 *
+	 * @param  array   data to go in table cells
+	 * @param  string  CSS class
+	 * @param  string  CSS style
+	 */
+	public function add_row($data, $class = '', $style = '')
+	{
+		$this-&gt;rows[] = array('data' =&gt; $data, 'class' =&gt; $class, 'style' =&gt; $style);
+	}
+
+	/**
+	 * Render table.
+	 *
+	 * @return  string
+	 */
+	public function render()
+	{
+		$data['rows'] = $this-&gt;rows;
+		$data['columns'] = $this-&gt;columns;
+		return View::factory('kohana_profiler_table', $data)-&gt;render();
+	}
 }
\ No newline at end of file</diff>
      <filename>system/libraries/Profiler_Table.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Router
  *
- * $Id: Router.php 3256 2008-08-05 01:34:16Z Shadowhand $
+ * $Id: Router.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -191,22 +191,16 @@ class Router_Core {
 				}
 			}
 		}
-		elseif (current($_GET) === '' AND substr($_SERVER['QUERY_STRING'], -1) !== '=')
+		elseif (isset($_GET['kohana_uri']))
 		{
-			// The URI is the array key, eg: ?this/is/the/uri
-			self::$current_uri = key($_GET);
+			// Use the URI defined in the query string
+			self::$current_uri = $_GET['kohana_uri'];
 
 			// Remove the URI from $_GET
-			unset($_GET[self::$current_uri]);
+			unset($_GET['kohana_uri']);
 
 			// Remove the URI from $_SERVER['QUERY_STRING']
-			$_SERVER['QUERY_STRING'] = ltrim(substr($_SERVER['QUERY_STRING'], strlen(self::$current_uri)), '/&amp;');
-
-			// Fixes really strange handling of a suffix in a GET string
-			if ($suffix = Kohana::config('core.url_suffix') AND substr(self::$current_uri, -(strlen($suffix))) === '_'.substr($suffix, 1))
-			{
-				self::$current_uri = substr(self::$current_uri, 0, -(strlen($suffix)));
-			}
+			$_SERVER['QUERY_STRING'] = preg_replace('~\bkohana_uri\b[^&amp;]*+&amp;?~', '', $_SERVER['QUERY_STRING']);
 		}
 		elseif (isset($_SERVER['PATH_INFO']) AND $_SERVER['PATH_INFO'])
 		{</diff>
      <filename>system/libraries/Router.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Session library.
  *
- * $Id: Session.php 3231 2008-07-29 07:30:50Z Geert $
+ * $Id: Session.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -109,8 +109,7 @@ class Session_Core {
 	public function create($vars = NULL)
 	{
 		// Destroy any current sessions
-		// NOTE: This is being commented out for Ticket #24
-		//$this-&gt;destroy();
+		$this-&gt;destroy();
 
 		if (self::$config['driver'] !== 'native')
 		{
@@ -158,8 +157,7 @@ class Session_Core {
 		);
 
 		// Start the session!
-		// NOTE: Suppressing warnings for Ticket #24 since session not destroyed
-		@session_start();
+		session_start();
 
 		// Put session_id in the session variable
 		$_SESSION['session_id'] = session_id();
@@ -207,11 +205,11 @@ class Session_Core {
 					break;
 				}
 			}
-
-			// Expire flash keys
-			$this-&gt;expire_flash();
 		}
 
+		// Expire flash keys
+		$this-&gt;expire_flash();
+
 		// Update last activity
 		$_SESSION['last_activity'] = time();
 </diff>
      <filename>system/libraries/Session.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * URI library.
  *
- * $Id: URI.php 3171 2008-07-21 02:27:11Z Shadowhand $
+ * $Id: URI.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/URI.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Validation library.
  *
- * $Id: Validation.php 3127 2008-07-16 14:43:52Z Shadowhand $
+ * $Id: Validation.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Validation
  * @author     Kohana Team
@@ -11,12 +11,6 @@
  */
 class Validation_Core extends ArrayObject {
 
-	// Unique &quot;any field&quot; key
-	protected $any_field;
-
-	// Array fields
-	protected $array_fields = array();
-
 	// Filters
 	protected $pre_filters = array();
 	protected $post_filters = array();
@@ -32,6 +26,9 @@ class Validation_Core extends ArrayObject {
 	protected $errors = array();
 	protected $messages = array();
 
+	// Fields that are expected to be arrays
+	protected $array_fields = array();
+
 	// Checks if there is data to validate.
 	protected $submitted;
 
@@ -41,9 +38,9 @@ class Validation_Core extends ArrayObject {
 	 * @param   array   array to use for validation
 	 * @return  object
 	 */
-	public static function factory($array = NULL)
+	public static function factory(array $array)
 	{
-		return new Validation( ! is_array($array) ? $_POST : $array);
+		return new Validation($array);
 	}
 
 	/**
@@ -55,16 +52,40 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function __construct(array $array)
 	{
-		// Set a dynamic, unique &quot;any field&quot; key
-		$this-&gt;any_field = uniqid(NULL, TRUE);
-
-		// Test if there is any actual data
-		$this-&gt;submitted = (count($array) &gt; 0);
+		// The array is submitted if the array is not empty
+		$this-&gt;submitted = ! empty($array);
 
 		parent::__construct($array, ArrayObject::ARRAY_AS_PROPS | ArrayObject::STD_PROP_LIST);
 	}
 
 	/**
+	 * Magic clone method, clears errors and messages.
+	 *
+	 * @return  void
+	 */
+	public function __clone()
+	{
+		$this-&gt;errors = array();
+		$this-&gt;messages = array();
+	}
+
+	/**
+	 * Create a copy of the current validation rules and change the array.
+	 *
+	 * @chainable
+	 * @param   array  new array to validate
+	 * @return  Validation
+	 */
+	public function copy(array $array)
+	{
+		$copy = clone $this;
+
+		$copy-&gt;exchangeArray($array);
+
+		return $copy;
+	}
+
+	/**
 	 * Test if the data has been submitted.
 	 *
 	 * @return  boolean
@@ -80,7 +101,29 @@ class Validation_Core extends ArrayObject {
 	}
 
 	/**
-	 * Returns the ArrayObject values.
+	 * Returns an array of all the field names that have filters, rules, or callbacks.
+	 *
+	 * @return  array
+	 */
+	public function field_names()
+	{
+		// All the fields that are being validated
+		$fields = array_unique(array_merge
+		(
+			array_keys($this-&gt;pre_filters),
+			array_keys($this-&gt;rules),
+			array_keys($this-&gt;callbacks),
+			array_keys($this-&gt;post_filters)
+		));
+
+		// Remove wildcard fields
+		$fields = array_diff($fields, array('*'));
+
+		return $fields;
+	}
+
+	/**
+	 * Returns the array values of the current object.
 	 *
 	 * @return  array
 	 */
@@ -93,39 +136,41 @@ class Validation_Core extends ArrayObject {
 	 * Returns the ArrayObject values, removing all inputs without rules.
 	 * To choose specific inputs, list the field name as arguments.
 	 *
+	 * @param   boolean  return only fields with filters, rules, and callbacks
 	 * @return  array
 	 */
 	public function safe_array()
 	{
-		// All the fields that are being validated
-		$all_fields = array_unique(array_merge
-		(
-			array_keys($this-&gt;pre_filters),
-			array_keys($this-&gt;rules),
-			array_keys($this-&gt;callbacks),
-			array_keys($this-&gt;post_filters)
-		));
-
 		// Load choices
 		$choices = func_get_args();
 		$choices = empty($choices) ? NULL : array_combine($choices, $choices);
 
+		// Get field names
+		$fields = $this-&gt;field_names();
+
 		$safe = array();
-		foreach ($all_fields as $i =&gt; $field)
+		foreach ($fields as $field)
 		{
-			// Ignore &quot;any field&quot; key
-			if ($field === $this-&gt;any_field) continue;
-
-			if (isset($this-&gt;array_fields[$field]))
-			{
-				// Use the key field
-				$field = $this-&gt;array_fields[$field];
-			}
-
 			if ($choices === NULL OR isset($choices[$field]))
 			{
-				// Make sure all fields are defined
-				$safe[$field] = isset($this[$field]) ? $this[$field] : NULL;
+				if (isset($this[$field]))
+				{
+					$value = $this[$field];
+
+					if (is_object($value))
+					{
+						// Convert the value back into an array
+						$value = $value-&gt;getArrayCopy();
+					}
+				}
+				else
+				{
+					// Even if the field is not in this array, it must be set
+					$value = NULL;
+				}
+
+				// Add the field to the array
+				$safe[$field] = $value;
 			}
 		}
 
@@ -152,7 +197,65 @@ class Validation_Core extends ArrayObject {
 	}
 
 	/**
-	 * Add a pre-filter to one or more inputs.
+	 * Converts a filter, rule, or callback into a fully-qualified callback array.
+	 *
+	 * @return  mixed
+	 */
+	protected function callback($callback)
+	{
+		if (is_string($callback))
+		{
+			if (strpos($callback, '::') !== FALSE)
+			{
+				$callback = explode('::', $callback);
+			}
+			elseif (function_exists($callback))
+			{
+				// No need to check if the callback is a method
+				$callback = $callback;
+			}
+			elseif (method_exists($this, $callback))
+			{
+				// The callback exists in Validation
+				$callback = array($this, $callback);
+			}
+			elseif (method_exists('valid', $callback))
+			{
+				// The callback exists in valid::
+				$callback = array('valid', $callback);
+			}
+		}
+
+		if ( ! is_callable($callback, FALSE))
+		{
+			if (is_array($callback))
+			{
+				if (is_object($callback[0]))
+				{
+					// Object instance syntax
+					$name = get_class($callback[0]).'-&gt;'.$callback[1];
+				}
+				else
+				{
+					// Static class syntax
+					$name = $callback[0].'::'.$callback[1];
+				}
+			}
+			else
+			{
+				// Function syntax
+				$name = $callback;
+			}
+
+			throw new Kohana_Exception('validation.not_callable', $name);
+		}
+
+		return $callback;
+	}
+
+	/**
+	 * Add a pre-filter to one or more inputs. Pre-filters are applied before
+	 * rules or callbacks are executed.
 	 *
 	 * @chainable
 	 * @param   callback  filter
@@ -161,15 +264,10 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function pre_filter($filter, $field = TRUE)
 	{
-		if ( ! is_callable($filter))
-			throw new Kohana_Exception('validation.filter_not_callable');
-
-		$filter = (is_string($filter) AND strpos($filter, '::') !== FALSE) ? explode('::', $filter) : $filter;
-
-		if ($field === TRUE)
+		if ($field === TRUE OR $field === '*')
 		{
-			// Handle &quot;any field&quot; filters
-			$fields = array($this-&gt;any_field);
+			// Use wildcard
+			$fields = array('*');
 		}
 		else
 		{
@@ -178,17 +276,11 @@ class Validation_Core extends ArrayObject {
 			$fields = array_slice($fields, 1);
 		}
 
+		// Convert to a proper callback
+		$filter = $this-&gt;callback($filter);
+
 		foreach ($fields as $field)
 		{
-			if (strpos($field, '.') &gt; 0)
-			{
-				// Field keys
-				$keys = explode('.', $field);
-
-				// Add to array fields
-				$this-&gt;array_fields[$field] = $keys[0];
-			}
-
 			// Add the filter to specified field
 			$this-&gt;pre_filters[$field][] = $filter;
 		}
@@ -197,7 +289,8 @@ class Validation_Core extends ArrayObject {
 	}
 
 	/**
-	 * Add a post-filter to one or more inputs.
+	 * Add a post-filter to one or more inputs. Post-filters are applied after
+	 * rules and callbacks have been executed.
 	 *
 	 * @chainable
 	 * @param   callback  filter
@@ -206,15 +299,10 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function post_filter($filter, $field = TRUE)
 	{
-		if ( ! is_callable($filter, TRUE))
-			throw new Kohana_Exception('validation.filter_not_callable');
-
-		$filter = (is_string($filter) AND strpos($filter, '::') !== FALSE) ? explode('::', $filter) : $filter;
-
 		if ($field === TRUE)
 		{
-			// Handle &quot;any field&quot; filters
-			$fields = array($this-&gt;any_field);
+			// Use wildcard
+			$fields = array('*');
 		}
 		else
 		{
@@ -223,17 +311,11 @@ class Validation_Core extends ArrayObject {
 			$fields = array_slice($fields, 1);
 		}
 
+		// Convert to a proper callback
+		$filter = $this-&gt;callback($filter);
+
 		foreach ($fields as $field)
 		{
-			if (strpos($field, '.') &gt; 0)
-			{
-				// Field keys
-				$keys = explode('.', $field);
-
-				// Add to array fields
-				$this-&gt;array_fields[$field] = $keys[0];
-			}
-
 			// Add the filter to specified field
 			$this-&gt;post_filters[$field][] = $filter;
 		}
@@ -242,26 +324,29 @@ class Validation_Core extends ArrayObject {
 	}
 
 	/**
-	 * Add rules to a field. Rules are callbacks or validation methods. Rules can
-	 * only return TRUE or FALSE.
+	 * Add rules to a field. Validation rules may only return TRUE or FALSE and
+	 * can not manipulate the value of a field.
 	 *
 	 * @chainable
 	 * @param   string    field name
-	 * @param   callback  rules (unlimited number)
+	 * @param   callback  rules (one or more arguments)
 	 * @return  object
 	 */
 	public function add_rules($field, $rules)
 	{
-		// Handle &quot;any field&quot; filters
-		($field === TRUE) and $field = $this-&gt;any_field;
-
 		// Get the rules
 		$rules = func_get_args();
 		$rules = array_slice($rules, 1);
 
+		if ($field === TRUE)
+		{
+			// Use wildcard
+			$field = '*';
+		}
+
 		foreach ($rules as $rule)
 		{
-			// Rule arguments
+			// Arguments for rule
 			$args = NULL;
 
 			if (is_string($rule))
@@ -275,34 +360,18 @@ class Validation_Core extends ArrayObject {
 					// Replace escaped comma with comma
 					$args = str_replace('\,', ',', $args);
 				}
-
-				if (method_exists($this, $rule))
-				{
-					// Make the rule a valid callback
-					$rule = array($this, $rule);
-				}
-				elseif (method_exists('valid', $rule))
-				{
-					// Make the rule a callback for the valid:: helper
-					$rule = array('valid', $rule);
-				}
 			}
 
-			if ( ! is_callable($rule, TRUE))
-				throw new Kohana_Exception('validation.rule_not_callable');
-
-			$rule = (is_string($rule) AND strpos($rule, '::') !== FALSE) ? explode('::', $rule) : $rule;
-
-			if (strpos($field, '.') &gt; 0)
+			if ($rule === 'is_array')
 			{
-				// Field keys
-				$keys = explode('.', $field);
-
-				// Add to array fields
-				$this-&gt;array_fields[$field] = $keys[0];
+				// This field is expected to be an array
+				$this-&gt;array_fields[$field] = $field;
 			}
 
-			// Add the rule to specified field
+			// Convert to a proper callback
+			$rule = $this-&gt;callback($rule);
+
+			// Add the rule, with args, to the field
 			$this-&gt;rules[$field][] = array($rule, $args);
 		}
 
@@ -320,35 +389,20 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function add_callbacks($field, $callbacks)
 	{
-		// Handle &quot;any field&quot; filters
-		($field === TRUE) and $field = $this-&gt;any_field;
+		// Get all callbacks as an array
+		$callbacks = func_get_args();
+		$callbacks = array_slice($callbacks, 1);
 
-		if (func_get_args() &gt; 2)
-		{
-			// Multiple callback
-			$callbacks = array_slice(func_get_args(), 1);
-		}
-		else
+		if ($field === TRUE)
 		{
-			// Only one callback
-			$callbacks = array($callbacks);
+			// Use wildcard
+			$field = '*';
 		}
 
 		foreach ($callbacks as $callback)
 		{
-			if ( ! is_callable($callback, TRUE))
-				throw new Kohana_Exception('validation.callback_not_callable');
-
-			$callback = (is_string($callback) AND strpos($callback, '::') !== FALSE) ? explode('::', $callback) : $callback;
-
-			if (strpos($field, '.') &gt; 0)
-			{
-				// Field keys
-				$keys = explode('.', $field);
-
-				// Add to array fields
-				$this-&gt;array_fields[$field] = $keys[0];
-			}
+			// Convert to a proper callback
+			$callback = $this-&gt;callback($callback);
 
 			// Add the callback to specified field
 			$this-&gt;callbacks[$field][] = $callback;
@@ -363,65 +417,66 @@ class Validation_Core extends ArrayObject {
 	 * they are undefined. Validation will only be run if there is data already
 	 * in the array.
 	 *
-	 * @return bool
+	 * @param   object  Validation object, used only for recursion
+	 * @param   object  name of field for errors
+	 * @return  bool
 	 */
-	public function validate()
+	public function validate($object = NULL, $field_name = NULL)
 	{
-		// All the fields that are being validated
-		$all_fields = array_unique(array_merge
-		(
-			array_keys($this-&gt;pre_filters),
-			array_keys($this-&gt;rules),
-			array_keys($this-&gt;callbacks),
-			array_keys($this-&gt;post_filters)
-		));
+		if ($object === NULL)
+		{
+			// Use the current object
+			$object = $this;
+		}
+
+		// Get all field names
+		$fields = $this-&gt;field_names();
 
 		// Copy the array from the object, to optimize multiple sets
-		$object_array = $this-&gt;getArrayCopy();
+		$array = $this-&gt;getArrayCopy();
 
-		foreach ($all_fields as $i =&gt; $field)
+		foreach ($fields as $field)
 		{
-			if ($field === $this-&gt;any_field)
+			if ($field === '*')
 			{
-				// Remove &quot;any field&quot; from the list of fields
-				unset($all_fields[$i]);
+				// Ignore wildcard
 				continue;
 			}
 
-			if (substr($field, -2) === '.*')
-			{
-				// Set the key to be an array
-				Kohana::key_string_set($object_array, substr($field, 0, -2), array());
-			}
-			else
+			if ( ! isset($array[$field]))
 			{
-				// Set the key to be NULL
-				Kohana::key_string_set($object_array, $field, NULL);
+				if (isset($this-&gt;array_fields[$field]))
+				{
+					// This field must be an array
+					$array[$field] = array();
+				}
+				else
+				{
+					$array[$field] = NULL;
+				}
 			}
 		}
 
 		// Swap the array back into the object
-		$this-&gt;exchangeArray($object_array);
+		$this-&gt;exchangeArray($array);
 
-		// Reset all fields to ALL defined fields
-		$all_fields = array_keys($this-&gt;getArrayCopy());
+		// Get all defined field names
+		$fields = array_keys($array);
 
-		foreach ($this-&gt;pre_filters as $field =&gt; $calls)
+		foreach ($this-&gt;pre_filters as $field =&gt; $callbacks)
 		{
-			foreach ($calls as $func)
+			foreach ($callbacks as $callback)
 			{
-				if ($field === $this-&gt;any_field)
+				if ($field === '*')
 				{
-					foreach ($all_fields as $f)
+					foreach ($fields as $f)
 					{
-						// Process each filter
-						$this[$f] = is_array($this[$f]) ? arr::map_recursive($func, $this[$f]) : call_user_func($func, $this[$f]);
+						$this[$f] = is_array($this[$f]) ? array_map($callback, $this[$f]) : call_user_func($callback, $this[$f]);
 					}
 				}
 				else
 				{
-					// Process each filter
-					$this[$field] = is_array($this[$field]) ? arr::map_recursive($func, $this[$field]) : call_user_func($func, $this[$field]);
+					$this[$field] = is_array($this[$field]) ? array_map($callback, $this[$field]) : call_user_func($callback, $this[$field]);
 				}
 			}
 		}
@@ -429,96 +484,89 @@ class Validation_Core extends ArrayObject {
 		if ($this-&gt;submitted === FALSE)
 			return FALSE;
 
-		foreach ($this-&gt;rules as $field =&gt; $calls)
+		foreach ($this-&gt;rules as $field =&gt; $callbacks)
 		{
-			foreach ($calls as $call)
+			foreach ($callbacks as $callback)
 			{
-				// Split the rule into function and args
-				list($func, $args) = $call;
+				// Separate the callback and arguments
+				list ($callback, $args) = $callback;
+
+				// Function or method name of the rule
+				$rule = is_array($callback) ? $callback[1] : $callback;
 
-				if ($field === $this-&gt;any_field)
+				if ($field === '*')
 				{
-					foreach ($all_fields as $f)
+					foreach ($fields as $f)
 					{
-						if (isset($this-&gt;array_fields[$f]))
-						{
-							// Use the field key
-							$f_key = $this-&gt;array_fields[$f];
+						// Note that continue, instead of break, is used when
+						// applying rules using a wildcard, so that all fields
+						// will be validated.
 
-							// Prevent other rules from running when this field already has errors
-							if ( ! empty($this-&gt;errors[$f_key])) break;
+						if (isset($this-&gt;errors[$f]))
+						{
+							// Prevent other rules from being evaluated if an error has occurred
+							continue;
+						}
 
-							// Don't process rules on empty fields
-							if ( ! in_array($func[1], $this-&gt;empty_rules, TRUE) AND $this[$f_key] == NULL)
-								continue;
+						if (empty($this[$f]) AND ! in_array($rule, $this-&gt;empty_rules))
+						{
+							// This rule does not need to be processed on empty fields
+							continue;
+						}
 
-							foreach ($this[$f_key] as $k =&gt; $v)
+						if ($args === NULL)
+						{
+							if ( ! call_user_func($callback, $this[$f]))
 							{
-								if ( ! call_user_func($func, $this[$f_key][$k], $args))
-								{
-									// Run each rule
-									$this-&gt;errors[$f_key] = is_array($func) ? $func[1] : $func;
-								}
+								$this-&gt;errors[$f] = $rule;
+
+								// Stop validating this field when an error is found
+								continue;
 							}
 						}
 						else
 						{
-							// Prevent other rules from running when this field already has errors
-							if ( ! empty($this-&gt;errors[$f])) break;
+							if ( ! call_user_func($callback, $this[$f], $args))
+							{
+								$this-&gt;errors[$f] = $rule;
 
-							// Don't process rules on empty fields
-							if ( ! in_array($func[1], $this-&gt;empty_rules, TRUE) AND $this[$f] == NULL)
+								// Stop validating this field when an error is found
 								continue;
-
-							if ( ! call_user_func($func, $this[$f], $args))
-							{
-								// Run each rule
-								$this-&gt;errors[$f] = is_array($func) ? $func[1] : $func;
 							}
 						}
 					}
 				}
 				else
 				{
-					if (isset($this-&gt;array_fields[$field]))
+					if (isset($this-&gt;errors[$field]))
 					{
-						// Use the field key
-						$field_key = $this-&gt;array_fields[$field];
-
-						// Prevent other rules from running when this field already has errors
-						if ( ! empty($this-&gt;errors[$field_key])) break;
+						// Prevent other rules from being evaluated if an error has occurred
+						break;
+					}
 
-						// Don't process rules on empty fields
-						if ( ! in_array($func[1], $this-&gt;empty_rules, TRUE) AND $this[$field_key] == NULL)
-							continue;
+					if ( ! in_array($rule, $this-&gt;empty_rules) AND ! $this-&gt;required($this[$field]))
+					{
+						// This rule does not need to be processed on empty fields
+						continue;
+					}
 
-						foreach ($this[$field_key] as $k =&gt; $val)
+					if ($args === NULL)
+					{
+						if ( ! call_user_func($callback, $this[$field]))
 						{
-							if ( ! call_user_func($func, $this[$field_key][$k], $args))
-							{
-								// Run each rule
-								$this-&gt;errors[$field_key] = is_array($func) ? $func[1] : $func;
+							$this-&gt;errors[$field] = $rule;
 
-								// Stop after an error is found
-								break 2;
-							}
+							// Stop validating this field when an error is found
+							break;
 						}
 					}
 					else
 					{
-						// Prevent other rules from running when this field already has errors
-						if ( ! empty($this-&gt;errors[$field])) break;
-
-						// Don't process rules on empty fields
-						if ( ! in_array($func[1], $this-&gt;empty_rules, TRUE) AND $this[$field] == NULL)
-							continue;
-
-						if ( ! call_user_func($func, $this[$field], $args))
+						if ( ! call_user_func($callback, $this[$field], $args))
 						{
-							// Run each rule
-							$this-&gt;errors[$field] = is_array($func) ? $func[1] : $func;
+							$this-&gt;errors[$field] = $rule;
 
-							// Stop after an error is found
+							// Stop validating this field when an error is found
 							break;
 						}
 					}
@@ -526,66 +574,60 @@ class Validation_Core extends ArrayObject {
 			}
 		}
 
-		foreach ($this-&gt;callbacks as $field =&gt; $calls)
+		foreach ($this-&gt;callbacks as $field =&gt; $callbacks)
 		{
-			foreach ($calls as $func)
+			foreach ($callbacks as $callback)
 			{
-				if ($field === $this-&gt;any_field)
+				if ($field === '*')
 				{
-					foreach ($all_fields as $f)
+					foreach ($fields as $f)
 					{
-						// Execute the callback
-						call_user_func($func, $this, $f);
+						// Note that continue, instead of break, is used when
+						// applying rules using a wildcard, so that all fields
+						// will be validated.
 
-						// Stop after an error is found
-						if ( ! empty($errors[$f])) break 2;
+						if (isset($this-&gt;errors[$f]))
+						{
+							// Stop validating this field when an error is found
+							continue;
+						}
+
+						call_user_func($callback, $this, $f);
 					}
 				}
 				else
 				{
-					// Execute the callback
-					call_user_func($func, $this, $field);
+					if (isset($this-&gt;errors[$field]))
+					{
+						// Stop validating this field when an error is found
+						break;
+					}
 
-					// Stop after an error is found
-					if ( ! empty($errors[$field])) break;
+					call_user_func($callback, $this, $field);
 				}
 			}
 		}
 
-		foreach ($this-&gt;post_filters as $field =&gt; $calls)
+		foreach ($this-&gt;post_filters as $field =&gt; $callbacks)
 		{
-			foreach ($calls as $func)
+			foreach ($callbacks as $callback)
 			{
-				if ($field === $this-&gt;any_field)
+				if ($field === '*')
 				{
-					foreach ($all_fields as $f)
+					foreach ($fields as $f)
 					{
-						if (isset($this-&gt;array_fields[$f]))
-						{
-							// Use the field key
-							$f = $this-&gt;array_fields[$f];
-						}
-
-						// Process each filter
-						$this[$f] = is_array($this[$f]) ? array_map($func, $this[$f]) : call_user_func($func, $this[$f]);
+						$this[$f] = is_array($this[$f]) ? array_map($callback, $this[$f]) : call_user_func($callback, $this[$f]);
 					}
 				}
 				else
 				{
-					if (isset($this-&gt;array_fields[$field]))
-					{
-						// Use the field key
-						$field = $this-&gt;array_fields[$field];
-					}
-
-					// Process each filter
-					$this[$field] = is_array($this[$field]) ? array_map($func, $this[$field]) : call_user_func($func, $this[$field]);
+					$this[$field] = is_array($this[$field]) ? array_map($callback, $this[$field]) : call_user_func($callback, $this[$field]);
 				}
 			}
 		}
 
 		// Return TRUE if there are no errors
-		return (count($this-&gt;errors) === 0);
+		return $this-&gt;errors === array();
 	}
 
 	/**
@@ -598,10 +640,7 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function add_error($field, $name)
 	{
-		if (isset($this[$field]))
-		{
-			$this-&gt;errors[$field] = $name;
-		}
+		$this-&gt;errors[$field] = $name;
 
 		return $this;
 	}
@@ -660,6 +699,7 @@ class Validation_Core extends ArrayObject {
 		}
 		else
 		{
+
 			$errors = array();
 			foreach ($this-&gt;errors as $input =&gt; $error)
 			{
@@ -672,7 +712,7 @@ class Validation_Core extends ArrayObject {
 					$errors[$input] = Kohana::lang(&quot;$file.$input.default&quot;);
 				}
 			}
-			
+
 			return $errors;
 		}
 	}
@@ -685,7 +725,20 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function required($str)
 	{
-		return ! ($str === '' OR $str === NULL OR $str === FALSE OR (is_array($str) AND empty($str)));
+		if (is_object($str) AND $str instanceof ArrayObject)
+		{
+			// Get the array from the ArrayObject
+			$str = $str-&gt;getArrayCopy();
+		}
+
+		if (is_array($str))
+		{
+			return ! empty($str);
+		}
+		else
+		{
+			return ! ($str === '' OR $str === NULL OR $str === FALSE);
+		}
 	}
 
 	/**
@@ -767,7 +820,7 @@ class Validation_Core extends ArrayObject {
 	 */
 	public function chars($value, array $chars)
 	{
-		return ! preg_match('![^'.preg_quote(implode(',', $chars)).']!', $value);
+		return ! preg_match('![^'.implode('', $chars).']!u', $value);
 	}
 
 } // End Validation</diff>
      <filename>system/libraries/Validation.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,9 +1,9 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Loads and displays Kohana view files. Can also handle output of some binary
  * files, such as image, Javascript, and CSS files.
  *
- * $Id: View.php 3209 2008-07-27 08:55:43Z Geert $
+ * $Id: View.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -56,6 +56,17 @@ class View_Core {
 			$this-&gt;kohana_local_data = array_merge($this-&gt;kohana_local_data, $data);
 		}
 	}
+	
+	/**
+	 * Magic method access to test for view property
+	 *
+	 * @param   string   View property to test for
+	 * @return  boolean
+	 */
+	public function __isset($key = NULL)
+	{
+		return $this-&gt;is_set($key);
+	}
 
 	/**
 	 * Sets the view filename.
@@ -118,6 +129,43 @@ class View_Core {
 	}
 
 	/**
+	 * Checks for a property existence in the view locally or globally. Unlike the built in __isset(), 
+	 * this method can take an array of properties to test simultaneously.
+	 *
+	 * @param string $key property name to test for
+	 * @param array $key array of property names to test for
+	 * @return boolean property test result
+	 * @return array associative array of keys and boolean test result
+	 */
+	public function is_set( $key = FALSE )
+	{
+		// Setup result;
+		$result = FALSE;
+
+		// If key is an array
+		if (is_array($key))
+		{
+			// Set the result to an array
+			$result = array();
+			
+			// Foreach key
+			foreach ($key as $property)
+			{
+				// Set the result to an associative array
+				$result[$property] = (array_key_exists($property, $this-&gt;kohana_local_data) OR array_key_exists($property, self::$kohana_global_data)) ? TRUE : FALSE;
+			}
+		}
+		else
+		{
+			// Otherwise just check one property
+			$result = (array_key_exists($key, $this-&gt;kohana_local_data) OR array_key_exists($key, self::$kohana_global_data)) ? TRUE : FALSE;
+		}
+
+		// Return the result
+		return $result;
+	}
+
+	/**
 	 * Sets a bound variable by reference.
 	 *
 	 * @param   string   name of variable
@@ -164,10 +212,7 @@ class View_Core {
 	 */
 	public function __set($key, $value)
 	{
-		if ( ! isset($this-&gt;$key))
-		{
-			$this-&gt;kohana_local_data[$key] = $value;
-		}
+		$this-&gt;kohana_local_data[$key] = $value;
 	}
 
 	/**
@@ -177,7 +222,7 @@ class View_Core {
 	 * @return mixed   variable value if the key is found
 	 * @return void    if the key is not found
 	 */
-	public function __get($key)
+	public function &amp;__get($key)
 	{
 		if (isset($this-&gt;kohana_local_data[$key]))
 			return $this-&gt;kohana_local_data[$key];
@@ -255,5 +300,4 @@ class View_Core {
 
 		return $output;
 	}
-
 } // End View
\ No newline at end of file</diff>
      <filename>system/libraries/View.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Cache driver interface.
  *
- * $Id: Cache.php 3135 2008-07-17 13:14:17Z Geert $
+ * $Id: Cache.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * APC-based Cache driver.
  *
- * $Id: Apc.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Apc.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/Apc.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Eaccelerator-based Cache driver.
  *
- * $Id: Eaccelerator.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Eaccelerator.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/Eaccelerator.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * File-based Cache driver.
  *
- * $Id: File.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: File.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/File.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Memcache-based Cache driver.
  *
- * $Id: Memcache.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Memcache.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/Memcache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * SQLite-based Cache driver.
  *
- * $Id: Sqlite.php 3168 2008-07-21 01:34:36Z Shadowhand $
+ * $Id: Sqlite.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/Sqlite.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Xcache Cache driver.
  *
- * $Id: Xcache.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Xcache.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Cache
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Cache/Xcache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver class.
  *
- * $Id: Captcha.php 3237 2008-07-30 12:10:20Z Geert $
+ * $Id: Captcha.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team
@@ -117,7 +117,7 @@ abstract class Captcha_Driver {
 		if ( ! empty($background))
 		{
 			// Create the image using the right function for the filetype
-			$function = 'imagecreatefrom'.$this-&gt;image_type($filename);
+			$function = 'imagecreatefrom'.$this-&gt;image_type($background);
 			$this-&gt;background_image = $function($background);
 
 			// Resize the image if needed</diff>
      <filename>system/libraries/drivers/Captcha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;alpha&quot; style.
  *
- * $Id: Alpha.php 3103 2008-07-13 10:37:32Z Geert $
+ * $Id: Alpha.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Alpha.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;basic&quot; style.
  *
- * $Id: Basic.php 3104 2008-07-13 12:06:52Z Geert $
+ * $Id: Basic.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Basic.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;black&quot; style.
  *
- * $Id: Black.php 3103 2008-07-13 10:37:32Z Geert $
+ * $Id: Black.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Black.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;math&quot; style.
  *
- * $Id: Math.php 3024 2008-07-10 05:21:07Z Geert $
+ * $Id: Math.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Math.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;riddle&quot; style.
  *
- * $Id: Riddle.php 3032 2008-07-10 16:31:35Z Geert $
+ * $Id: Riddle.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Riddle.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Captcha driver for &quot;word&quot; style.
  *
- * $Id: Word.php 3028 2008-07-10 13:33:05Z Geert $
+ * $Id: Word.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Captcha
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Captcha/Word.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Database API driver
  *
- * $Id: Database.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Database.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -163,7 +163,7 @@ abstract class Database_Driver {
 		if ($auto === TRUE)
 		{
 			// Add the start and end quotes
-			$match = '%'.$match.'%';
+			$match = '%'.str_replace('%', '\\%', $match).'%';
 		}
 
 		return $prefix.' '.$this-&gt;escape_column($field).' LIKE \''.$match . '\'';
@@ -337,7 +337,7 @@ abstract class Database_Driver {
 	 *
 	 * @return  array
 	 */
-	abstract public function list_tables();
+	abstract public function list_tables(Database $db);
 
 	/**
 	 * Lists all fields in a table.
@@ -603,7 +603,8 @@ abstract class Database_Result implements ArrayAccess, Iterator, Countable {
 	 */
 	public function next()
 	{
-		return ++$this-&gt;current_row;
+		++$this-&gt;current_row;
+		return $this;
 	}
 
 	/**
@@ -611,7 +612,8 @@ abstract class Database_Result implements ArrayAccess, Iterator, Countable {
 	 */
 	public function prev()
 	{
-		return --$this-&gt;current_row;
+		--$this-&gt;current_row;
+		return $this;
 	}
 
 	/**
@@ -619,7 +621,8 @@ abstract class Database_Result implements ArrayAccess, Iterator, Countable {
 	 */
 	public function rewind()
 	{
-		return $this-&gt;current_row = 0;
+		$this-&gt;current_row = 0;
+		return $this;
 	}
 
 	/**</diff>
      <filename>system/libraries/drivers/Database.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,7 +1,7 @@
-&lt;?php  defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * MSSQL Database Driver
- * 
+ *
  * @package    Core
  * @author     Kohana Team
  * @copyright  (c) 2007-2008 Kohana Team
@@ -30,7 +30,7 @@ class Database_Mssql_Driver extends Database_Driver
 
 		Kohana::log('debug', 'MSSQL Database Driver Initialized');
 	}
-	
+
 	/**
 	 * Closes the database connection.
 	 */
@@ -38,7 +38,7 @@ class Database_Mssql_Driver extends Database_Driver
 	{
 		is_resource($this-&gt;link) and mssql_close($this-&gt;link);
 	}
-	
+
 	/**
 	 * Make the connection
 	 *
@@ -58,13 +58,15 @@ class Database_Mssql_Driver extends Database_Driver
 
 		// Build the connection info
 		$host = isset($host) ? $host : $socket;
-		$port = (isset($port) AND is_string($port)) ? ':'.$port : '';
+
+		// Windows uses a comma instead of a colon
+		$port = (isset($port) AND is_string($port)) ? (KOHANA_IS_WIN ? ',' : ':').$port : '';
 
 		// Make the connection and select the database
 		if (($this-&gt;link = $connect($host.$port, $user, $pass, TRUE)) AND mssql_select_db($database, $this-&gt;link))
 		{
 			/* This is being removed so I can use it, will need to come up with a more elegant workaround in the future...
-			 * 
+			 *
 			if ($charset = $this-&gt;db_config['character_set'])
 			{
 				$this-&gt;set_charset($charset);
@@ -79,7 +81,7 @@ class Database_Mssql_Driver extends Database_Driver
 
 		return FALSE;
 	}
-	
+
 	public function query($sql)
 	{
 		// Only cache if it's turned on, and only cache if it's not a write statement
@@ -159,7 +161,7 @@ class Database_Mssql_Driver extends Database_Driver
 		}
 		return $column;
 	}
-	
+
 	/**
 	 * Limit in SQL Server 2000 only uses the keyword
 	 * 'TOP'; 2007 may have an offset keyword, but
@@ -191,7 +193,10 @@ class Database_Mssql_Driver extends Database_Driver
 
 		if (count($database['join']) &gt; 0)
 		{
-			$sql .= ' '.$database['join']['type'].'JOIN ('.implode(', ', $database['join']['tables']).') ON '.implode(' AND ', $database['join']['conditions']);
+			foreach($database['join'] AS $join)
+			{
+				$sql .= &quot;\n&quot;.$join['type'].'JOIN '.implode(', ', $join['tables']).' ON '.$join['conditions'];
+			}
 		}
 
 		if (count($database['where']) &gt; 0)
@@ -241,7 +246,7 @@ class Database_Mssql_Driver extends Database_Driver
 		return preg_replace($characters, $replace, $str);
 	}
 
-	public function list_tables()
+	public function list_tables(Database $db)
 	{
 		$sql    = 'SHOW TABLES FROM ['.$this-&gt;db_config['connection']['database'].']';
 		$result = $this-&gt;query($sql)-&gt;result(FALSE, MSSQL_ASSOC);
@@ -257,7 +262,7 @@ class Database_Mssql_Driver extends Database_Driver
 
 	public function show_error()
 	{
-		return mssql_error($this-&gt;link);
+		return mssql_get_last_message($this-&gt;link);
 	}
 
 	public function list_fields($table)
@@ -328,7 +333,7 @@ class Mssql_Result extends Database_Result {
 			if ($result == FALSE)
 			{
 				// SQL error
-				throw new Kohana_Database_Exception('database.error', MSSQL_error($link).' - '.$sql);
+				throw new Kohana_Database_Exception('database.error', mssql_get_last_message($link).' - '.$sql);
 			}
 			else
 			{</diff>
      <filename>system/libraries/drivers/Database/Mssql.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * MySQL Database Driver
  *
- * $Id: Mysql.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Mysql.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -201,14 +201,19 @@ class Database_Mysql_Driver extends Database_Driver {
 			// Escape the tables
 			$froms = array();
 			foreach ($database['from'] as $from)
+			{
 				$froms[] = $this-&gt;escape_column($from);
+			}
 			$sql .= &quot;\nFROM &quot;;
 			$sql .= implode(', ', $froms);
 		}
 
 		if (count($database['join']) &gt; 0)
 		{
-			$sql .= ' '.$database['join']['type'].'JOIN ('.implode(', ', $database['join']['tables']).') ON '.implode(' AND ', $database['join']['conditions']);
+			foreach($database['join'] AS $join)
+			{
+				$sql .= &quot;\n&quot;.$join['type'].'JOIN '.implode(', ', $join['tables']).' ON '.$join['conditions'];
+			}
 		}
 
 		if (count($database['where']) &gt; 0)
@@ -255,18 +260,19 @@ class Database_Mysql_Driver extends Database_Driver {
 		return mysql_real_escape_string($str, $this-&gt;link);
 	}
 
-	public function list_tables()
+	public function list_tables(Database $db)
 	{
-		$sql    = 'SHOW TABLES FROM `'.$this-&gt;db_config['connection']['database'].'`';
-		$result = $this-&gt;query($sql)-&gt;result(FALSE, MYSQL_ASSOC);
+		static $tables;
 
-		$retval = array();
-		foreach ($result as $row)
+		if (empty($tables) AND $query = $db-&gt;query('SHOW TABLES FROM '.$this-&gt;escape_table($this-&gt;db_config['connection']['database'])))
 		{
-			$retval[] = current($row);
+			foreach ($query-&gt;result(FALSE) as $row)
+			{
+				$tables[] = current($row);
+			}
 		}
 
-		return $retval;
+		return $tables;
 	}
 
 	public function show_error()
@@ -311,7 +317,7 @@ class Database_Mysql_Driver extends Database_Driver {
 
 		if ($query = mysql_query('SHOW COLUMNS FROM '.$this-&gt;escape_table($table), $this-&gt;link))
 		{
-			if (mysql_num_rows($query) &gt; 0)
+			if (mysql_num_rows($query))
 			{
 				while ($row = mysql_fetch_object($query))
 				{
@@ -470,10 +476,17 @@ class Mysql_Result extends Database_Result {
 
 	public function seek($offset)
 	{
-		if ( ! $this-&gt;offsetExists($offset))
-			return FALSE;
+		if ($this-&gt;offsetExists($offset) AND mysql_data_seek($this-&gt;result, $offset))
+		{
+			// Set the current row to the offset
+			$this-&gt;current_row = $offset;
 
-		return mysql_data_seek($this-&gt;result, $offset);
+			return TRUE;
+		}
+		else
+		{
+			return FALSE;
+		}
 	}
 
 } // End Mysql_Result Class
\ No newline at end of file</diff>
      <filename>system/libraries/drivers/Database/Mysql.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * MySQLi Database Driver
  *
- * $Id: Mysqli.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Mysqli.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -49,7 +49,7 @@ class Database_Mysqli_Driver extends Database_Mysql_Driver {
 		$host = isset($host) ? $host : $socket;
 
 		// Make the connection and select the database
-		if ($this-&gt;link = new mysqli($host, $user, $pass, $database))
+		if ($this-&gt;link = new mysqli($host, $user, $pass, $database, $port))
 		{
 			if ($charset = $this-&gt;db_config['character_set'])
 			{
@@ -114,15 +114,18 @@ class Database_Mysqli_Driver extends Database_Mysql_Driver {
 
 	public function field_data($table)
 	{
-		$query  = $this-&gt;link-&gt;query('SHOW COLUMNS FROM '.$this-&gt;escape_table($table));
+		$columns = array();
+		$query = $this-&gt;link-&gt;query('SHOW COLUMNS FROM '.$this-&gt;escape_table($table));
 
-		$table  = array();
-		while ($row = $query-&gt;fetch_object())
+		if (is_object($query))
 		{
-			$table[] = $row;
+			while ($row = $query-&gt;fetch_object())
+			{
+				$columns[] = $row;
+			}
 		}
 
-		return $table;
+		return $columns;
 	}
 
 } // End Database_Mysqli_Driver Class</diff>
      <filename>system/libraries/drivers/Database/Mysqli.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /*
  * Class: Database_PdoSqlite_Driver
  *  Provides specific database items for Sqlite.
@@ -149,7 +149,10 @@ class Database_Pdosqlite_Driver extends Database_Driver {
 
 		if (count($database['join']) &gt; 0)
 		{
-			$sql .= ' '.$database['join']['type'].'JOIN ('.implode(', ', $database['join']['tables']).') ON '.implode(' AND ', $database['join']['conditions']);
+			foreach($database['join'] AS $join)
+			{
+				$sql .= &quot;\n&quot;.$join['type'].'JOIN '.implode(', ', $join['tables']).' ON '.$join['conditions'];
+			}
 		}
 
 		if (count($database['where']) &gt; 0)
@@ -202,23 +205,23 @@ class Database_Pdosqlite_Driver extends Database_Driver {
 		return $res;
 	}
 
-	public function list_tables()
+	public function list_tables(Database $db)
 	{
 		$sql = &quot;SELECT `name` FROM `sqlite_master` WHERE `type`='table' ORDER BY `name`;&quot;;
 		try
 		{
-			$result = $this-&gt;query($sql)-&gt;result(FALSE, PDO::FETCH_ASSOC);
-			$retval = array();
+			$result = $db-&gt;query($sql)-&gt;result(FALSE, PDO::FETCH_ASSOC);
+			$tables = array();
 			foreach ($result as $row)
 			{
-				$retval[] = current($row);
+				$tables[] = current($row);
 			}
 		}
 		catch (PDOException $e)
 		{
 			throw new Kohana_Database_Exception('database.error', $e-&gt;getMessage());
 		}
-		return $retval;
+		return $tables;
 	}
 
 	public function show_error()</diff>
      <filename>system/libraries/drivers/Database/Pdosqlite.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * PostgreSQL 8.1+ Database Driver
  *
- * $Id: Pgsql.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Pgsql.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team
@@ -175,7 +175,10 @@ class Database_Pgsql_Driver extends Database_Driver {
 
 		if (count($database['join']) &gt; 0)
 		{
-			$sql .= ' '.$database['join']['type'].'JOIN ('.implode(', ', $database['join']['tables']).') ON '.implode(' AND ', $database['join']['conditions']);
+			foreach($database['join'] AS $join)
+			{
+				$sql .= &quot;\n&quot;.$join['type'].'JOIN '.implode(', ', $join['tables']).' ON '.$join['conditions'];
+			}
 		}
 
 		if (count($database['where']) &gt; 0)
@@ -222,10 +225,10 @@ class Database_Pgsql_Driver extends Database_Driver {
 		return pg_escape_string($this-&gt;link, $str);
 	}
 
-	public function list_tables()
+	public function list_tables(Database $db)
 	{
 		$sql    = 'SELECT table_schema || \'.\' || table_name FROM information_schema.tables WHERE table_schema NOT IN (\'pg_catalog\', \'information_schema\')';
-		$result = $this-&gt;query($sql)-&gt;result(FALSE, PGSQL_ASSOC);
+		$result = $db-&gt;query($sql)-&gt;result(FALSE, PGSQL_ASSOC);
 
 		$retval = array();
 		foreach ($result as $row)
@@ -291,14 +294,17 @@ FROM pg_class
     ON (pg_class.oid=pg_attrdef.adrelid AND pg_attribute.attnum=pg_attrdef.adnum)
 WHERE pg_class.relname=\''.$this-&gt;escape_str($table).'\' AND pg_attribute.attnum&gt;=1 AND NOT pg_attribute.attisdropped
 ORDER BY pg_attribute.attnum');
-                $fields = array();
-                foreach ($query as $row)
-                {
-                        $fields[$row-&gt;Field]=$row-&gt;Type;
-                }
 
-                return $fields;
+				// Load the result as objects
+				$query-&gt;result(TRUE);
+
+				$fields = array();
+				foreach ($query as $row)
+				{
+					$fields[$row-&gt;Field] = $row-&gt;Type;
+				}
 
+				return $fields;
 	}
 
 	public function field_data($table)
@@ -345,7 +351,7 @@ class Pgsql_Result extends Database_Result {
 		if (is_resource($result))
 		{
 			// Its an DELETE, INSERT, REPLACE, or UPDATE query
-			if (preg_match('/^(?:delete|insert|replace|update)\s+/i', trim($sql), $matches))
+			if (preg_match('/^(?:delete|insert|replace|update)\b/iD', trim($sql), $matches))
 			{
 				$this-&gt;insert_id  = (strtolower($matches[0]) == 'insert') ? $this-&gt;insert_id() : FALSE;
 				$this-&gt;total_rows = pg_affected_rows($this-&gt;result);
@@ -453,10 +459,17 @@ class Pgsql_Result extends Database_Result {
 		{
 			$query = 'SELECT LASTVAL() AS insert_id';
 
-			$result = pg_query($link, $query);
+			// Disable error reporting for this, just to silence errors on
+			// tables that have no serial column.
+			$ER = error_reporting(0);
+
+			$result = pg_query($query);
 			$insert_id = pg_fetch_array($result, NULL, PGSQL_ASSOC);
 
 			$this-&gt;insert_id = $insert_id['insert_id'];
+
+			// Reset error reporting
+			error_reporting($ER);
 		}
 
 		return $this-&gt;insert_id;</diff>
      <filename>system/libraries/drivers/Database/Pgsql.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Image API driver.
  *
- * $Id: Image.php 3287 2008-08-07 11:28:44Z OscarB $
+ * $Id: Image.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Image
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Image.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * GD Image Driver.
  *
- * $Id: GD.php 3248 2008-08-01 21:02:18Z Geert $
+ * $Id: GD.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Image
  * @author     Kohana Team
@@ -211,17 +211,17 @@ class Image_GD_Driver extends Image_Driver {
 			// Recalculate the percentage to a pixel size
 			$properties['height'] = round($height * (substr($properties['height'], 0, -1) / 100));
 		}
-
+		
+		// Recalculate the width and height, if they are missing
+		empty($properties['width'])  and $properties['width']  = round($width * $properties['height'] / $height);
+		empty($properties['height']) and $properties['height'] = round($height * $properties['width'] / $width);
+		
 		if ($properties['master'] === Image::AUTO)
 		{
 			// Change an automatic master dim to the correct type
 			$properties['master'] = (($width / $properties['width']) &gt; ($height / $properties['height'])) ? Image::WIDTH : Image::HEIGHT;
 		}
 
-		// Recalculate the width and height, if they are missing
-		empty($properties['width'])  and $properties['width']  = round($width * $properties['height'] / $height);
-		empty($properties['height']) and $properties['height'] = round($height * $properties['width'] / $width);
-
 		if (empty($properties['height']) OR $properties['master'] === Image::WIDTH)
 		{
 			// Recalculate the height based on the width</diff>
      <filename>system/libraries/drivers/Image/GD.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * ImageMagick Image Driver.
  *
- * $Id: ImageMagick.php 3248 2008-08-01 21:02:18Z Geert $
+ * $Id: ImageMagick.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Image
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Image/ImageMagick.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Session driver interface
  *
- * $Id: Session.php 1928 2008-02-05 21:00:14Z PugFish $
+ * $Id: Session.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Session.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Session cache driver.
  *
@@ -10,7 +10,7 @@
  * Lifetime does not need to be set as it is
  * overridden by the session expiration setting.
  *
- * $Id: Cache.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Cache.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Session/Cache.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Session cookie driver.
  *
- * $Id: Cookie.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Cookie.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Session/Cookie.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,8 +1,8 @@
-&lt;?php defined('SYSPATH') or die('No direct script access.');
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Session database driver.
  *
- * $Id: Database.php 3160 2008-07-20 16:03:48Z Shadowhand $
+ * $Id: Database.php 3917 2009-01-21 03:06:22Z zombor $
  *
  * @package    Core
  * @author     Kohana Team</diff>
      <filename>system/libraries/drivers/Session/Database.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 #
 # Markdown Extra  -  A text-to-HTML conversion tool for web writers
 #</diff>
      <filename>system/vendor/Markdown.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,4 @@
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.'); ?&gt;
 &lt;!DOCTYPE html PUBLIC &quot;-//W3C//DTD XHTML 1.0 Strict//EN&quot; &quot;http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd&quot;&gt;
 
 &lt;html xmlns=&quot;http://www.w3.org/1999/xhtml&quot; xml:lang=&quot;en&quot; lang=&quot;en&quot;&gt;</diff>
      <filename>system/views/kohana/template.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,7 +1,7 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 
 // Get the day names
-$days = Calendar::days(TRUE);
+$days = Calendar::days(2);
 
 // Previous and next month timestamps
 $next = mktime(0, 0, 0, $month + 1, 1, $year);</diff>
      <filename>system/views/kohana_calendar.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,4 @@
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.'); ?&gt;
 &lt;!DOCTYPE html PUBLIC &quot;-//W3C//DTD XHTML 1.0 Strict//EN&quot; &quot;http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd&quot;&gt;
 &lt;html xmlns=&quot;http://www.w3.org/1999/xhtml&quot; xml:lang=&quot;en&quot; lang=&quot;en&quot;&gt;
 &lt;head&gt;</diff>
      <filename>system/views/kohana_error_disabled.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,4 @@
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.'); ?&gt;
 &lt;!DOCTYPE html PUBLIC &quot;-//W3C//DTD XHTML 1.0 Strict//EN&quot; &quot;http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd&quot;&gt;
 &lt;html xmlns=&quot;http://www.w3.org/1999/xhtml&quot; xml:lang=&quot;en&quot; lang=&quot;en&quot;&gt;
 &lt;head&gt;</diff>
      <filename>system/views/kohana_error_page.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,4 @@
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.'); ?&gt;
 &lt;style type=&quot;text/css&quot;&gt;
 #kohana-profiler
 {</diff>
      <filename>system/views/kohana_profiler.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,53 +1,53 @@
-#kohana-profiler .kp-table
-{
-	font-size: 1.0em;
-	color: #4D6171;
-	width: 100%;
-	border-collapse: collapse;
-	border-top: 1px solid #E5EFF8;
-	border-right: 1px solid #E5EFF8;
-	border-left: 1px solid #E5EFF8;
-	margin-bottom: 10px;
-}
-#kohana-profiler .kp-table td
-{
-	background-color: #FFFFFF;
-	border-bottom: 1px solid #E5EFF8;
-	padding: 3px;
-	vertical-align: top;
-}
-#kohana-profiler .kp-table .kp-title td
-{
-	font-weight: bold;
-	background-color: inherit;
-}
-#kohana-profiler .kp-table .kp-altrow td
-{
-	background-color: #F7FBFF;
-}
-#kohana-profiler .kp-table .kp-totalrow td
-{
-	background-color: #FAFAFA;
-	border-top: 1px solid #D2DCE5;
-	font-weight: bold;
-}
-#kohana-profiler .kp-table .kp-column
-{
-	width: 100px;
-	border-left: 1px solid #E5EFF8;
-	text-align: center;
-}
-#kohana-profiler .kp-table .kp-data, #kohana-profiler .kp-table .kp-name
-{
-	background-color: #FAFAFB;
-	vertical-align: top;
-}
-#kohana-profiler .kp-table .kp-name
-{
-	width: 200px;
-	border-right: 1px solid #E5EFF8;
-}
-#kohana-profiler .kp-table .kp-altrow .kp-data, #kohana-profiler .kp-table .kp-altrow .kp-name
-{
-	background-color: #F6F8FB;
+#kohana-profiler .kp-table
+{
+	font-size: 1.0em;
+	color: #4D6171;
+	width: 100%;
+	border-collapse: collapse;
+	border-top: 1px solid #E5EFF8;
+	border-right: 1px solid #E5EFF8;
+	border-left: 1px solid #E5EFF8;
+	margin-bottom: 10px;
+}
+#kohana-profiler .kp-table td
+{
+	background-color: #FFFFFF;
+	border-bottom: 1px solid #E5EFF8;
+	padding: 3px;
+	vertical-align: top;
+}
+#kohana-profiler .kp-table .kp-title td
+{
+	font-weight: bold;
+	background-color: inherit;
+}
+#kohana-profiler .kp-table .kp-altrow td
+{
+	background-color: #F7FBFF;
+}
+#kohana-profiler .kp-table .kp-totalrow td
+{
+	background-color: #FAFAFA;
+	border-top: 1px solid #D2DCE5;
+	font-weight: bold;
+}
+#kohana-profiler .kp-table .kp-column
+{
+	width: 100px;
+	border-left: 1px solid #E5EFF8;
+	text-align: center;
+}
+#kohana-profiler .kp-table .kp-data, #kohana-profiler .kp-table .kp-name
+{
+	background-color: #FAFAFB;
+	vertical-align: top;
+}
+#kohana-profiler .kp-table .kp-name
+{
+	width: 200px;
+	border-right: 1px solid #E5EFF8;
+}
+#kohana-profiler .kp-table .kp-altrow .kp-data, #kohana-profiler .kp-table .kp-altrow .kp-name
+{
+	background-color: #F6F8FB;
 }
\ No newline at end of file</diff>
      <filename>system/views/kohana_profiler_table.css</filename>
    </modified>
    <modified>
      <diff>@@ -1,3 +1,4 @@
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.'); ?&gt;
 &lt;table class=&quot;kp-table&quot;&gt;
 &lt;?php
 foreach ($rows as $row):</diff>
      <filename>system/views/kohana_profiler_table.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Classic pagination style
  * </diff>
      <filename>system/views/pagination/classic.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Digg pagination style
  * </diff>
      <filename>system/views/pagination/digg.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * Extended pagination style
  * </diff>
      <filename>system/views/pagination/extended.php</filename>
    </modified>
    <modified>
      <diff>@@ -1,4 +1,4 @@
-&lt;?php
+&lt;?php defined('SYSPATH') OR die('No direct access allowed.');
 /**
  * PunBB pagination style
  * </diff>
      <filename>system/views/pagination/punbb.php</filename>
    </modified>
  </modified>
  <removed type="array">
    <removed>
      <filename>modules/auth/controllers/auth_demo.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/i18n/.gitignore</filename>
    </removed>
    <removed>
      <filename>modules/auth/models/auth_pending_user.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/models/pending_user.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/confirmationrequest.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/confirmationrequestemail.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/confirmed.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/create.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/install.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/login.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/register.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/auth/user.php</filename>
    </removed>
    <removed>
      <filename>modules/auth/views/template.php</filename>
    </removed>
    <removed>
      <filename>system/config/database.php</filename>
    </removed>
    <removed>
      <filename>system/config/payment.php</filename>
    </removed>
    <removed>
      <filename>system/fonts/GeosansLight.ttf</filename>
    </removed>
    <removed>
      <filename>system/fonts/MankSans.ttf</filename>
    </removed>
    <removed>
      <filename>system/fonts/Silkscreen.ttf</filename>
    </removed>
    <removed>
      <filename>system/fonts/pf_arma_five.ttf</filename>
    </removed>
    <removed>
      <filename>system/fonts/tahoma.ttf</filename>
    </removed>
    <removed>
      <filename>system/helpers/.ftpssh_settings</filename>
    </removed>
    <removed>
      <filename>system/i18n/en_US/database.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.auto.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.autoload.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.func.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.includes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.kses.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.path.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier.safe-includes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrCollections.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/AlphaValue.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Background.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Border.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Color.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Composite.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Filter.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Font.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/FontFamily.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Length.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/ListStyle.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Multiple.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Number.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/Percentage.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/TextDecoration.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/CSS/URI.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/Enum.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/Bool.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/Color.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/FrameTarget.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/ID.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/Length.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/LinkTypes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/MultiLength.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/Nmtokens.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/HTML/Pixels.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/Integer.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/Lang.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/Switch.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/Text.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI/Email.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI/Host.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv4.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv6.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/BdoDir.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/BgColor.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/BoolToCSS.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/Border.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/EnumToCSS.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/ImgRequired.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/ImgSpace.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/Lang.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/Length.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/Name.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/SafeEmbed.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/SafeObject.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/SafeParam.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTransform/ScriptRequired.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrTypes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/AttrValidator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Bootstrap.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/CSSDefinition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Chameleon.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Custom.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Empty.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Optional.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Required.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/StrictBlockquote.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ChildDef/Table.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Config.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/Xml.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Exception.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Directive.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Id.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Namespace.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/InterchangeBuilder.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/Validator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/ValidatorAtom.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema.ser</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.PurifierLinkifyDocURL.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.MaxImgLength.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Language.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksEscaping.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksScope.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksTidyImpl.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.MaxImgLength.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.SafeEmbed.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.SafeObject.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Base.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Host.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MungeResources.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MungeSecretKey.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.txt</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ConfigSchema/schema/info.ini</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ContentSets.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Context.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Definition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Memory.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Template.php.in</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Null.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Serializer.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Serializer/CSS/.gitignore</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Serializer/HTML/.gitignore</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Serializer/Test/.gitignore</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCache/Serializer/URI/.gitignore</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DefinitionCacheFactory.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Doctype.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/DoctypeRegistry.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ElementDef.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Encoder.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/EntityLookup.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/EntityLookup/entities.ser</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/EntityParser.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/ErrorCollector.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Exception.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Filter.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Filter/ExtractStyleBlocks.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Filter/YouTube.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Generator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLDefinition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Bdo.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/CommonAttributes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Edit.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Hypertext.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Image.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Legacy.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/List.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/NonXMLCommonAttributes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Object.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Presentation.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Proprietary.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Ruby.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/SafeEmbed.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/SafeObject.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Scripting.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/StyleAttribute.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tables.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Target.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Text.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/Proprietary.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/Strict.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/Transitional.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/XHTML.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/XHTMLAndHTML4.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModule/XMLCommonAttributes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/HTMLModuleManager.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/IDAccumulator.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Injector.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Injector/AutoParagraph.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Injector/Linkify.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Injector/PurifierLinkify.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Injector/SafeObject.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Language.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Language/classes/en-x-test.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Language/messages/en-x-test.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Language/messages/en-x-testmini.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Language/messages/en.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/LanguageFactory.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Length.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Lexer.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Lexer/DOMLex.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Lexer/DirectLex.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Lexer/PEARSax3.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Lexer/PH5P.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/PercentEncoder.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer/CSSDefinition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer/ConfigForm.css</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer/ConfigForm.js</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer/ConfigForm.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Printer/HTMLDefinition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/Composite.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/Core.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/FixNesting.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/MakeWellFormed.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/RemoveForeignElements.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Strategy/ValidateAttributes.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/StringHash.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/StringHashParser.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/TagTransform.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/TagTransform/Font.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/TagTransform/Simple.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/Comment.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/Empty.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/End.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/Start.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/Tag.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/Token/Text.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/TokenFactory.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URI.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIDefinition.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter/DisableExternal.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter/DisableExternalResources.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter/HostBlacklist.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter/MakeAbsolute.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIFilter/Munge.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIParser.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/ftp.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/http.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/https.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/mailto.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/news.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URIScheme/nntp.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/URISchemeRegistry.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/UnitConverter.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/VarParser.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/VarParser/Flexible.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/VarParser/Native.php</filename>
    </removed>
    <removed>
      <filename>system/vendor/htmlpurifier/HTMLPurifier/VarParserException.php</filename>
    </removed>
  </removed>
  <parents type="array">
    <parent>
      <id>4dbb30db916547b7fc8bdfdd950c48ff960bd6af</id>
    </parent>
  </parents>
  <author>
    <name>David Kobia</name>
    <email>david@ushahidi.com</email>
  </author>
  <url>http://github.com/gabelula/Ushahidi_Web/commit/d60cd99239edc4a0054cfc1ae9eb20651f6b2fbf</url>
  <id>d60cd99239edc4a0054cfc1ae9eb20651f6b2fbf</id>
  <committed-date>2009-03-02T13:16:11-08:00</committed-date>
  <authored-date>2009-03-02T12:34:42-08:00</authored-date>
  <message>* Upgraded to Kohana 2.3 (Needs further testing)
* Updated Auth Module
* Used 2.2 Validation Library. 2.3 has issues with validation arrays
* Patched OpenLayers 2.7 to allow for Marker Labels
* New Cluster controller for Server Side Clustering
* Cluster controller saves clusters to DB for serving on the fly
* New Media controller mimics media folder
* Media controller gzip compression on CSS and JS
* Media controller reduces site loading time by more than half</message>
  <tree>b9fa040db3f829b7b4bf8b3c6cb9ff754a5758ff</tree>
  <committer>
    <name>David Kobia</name>
    <email>david@ushahidi.com</email>
  </committer>
</commit>
