<?php  if ( ! defined('BASEPATH')) exit('No direct script access allowed');
/**
 * CodeIgniter
 *
 * An open source application development framework for PHP 4.3.2 or newer
 *
 * @package		CodeIgniter
 * @author		ExpressionEngine Dev Team
 * @copyright	Copyright (c) 2008, EllisLab, Inc.
 * @license		http://codeigniter.com/user_guide/license.html
 * @link		http://codeigniter.com
 * @since		Version 1.0
 * @filesource
 */

// ------------------------------------------------------------------------

/**
 * CodeIgniter Compatibility Helpers
 *
 * This helper contains some functions based on the PEAR PHP_Compat library
 * http://pear.php.net/package/PHP_Compat
 * 
 * The PEAR compat library is a little bloated and the code doesn't harmonize
 * well with CodeIgniter, so those functions have been refactored.
 * We cheat a little and use CI's _exception_handler() to output our own PHP errors
 * so that the behavior fully mimicks the PHP 5 counterparts.  -- Derek Jones
 * 
 * @package		CodeIgniter
 * @subpackage	Helpers
 * @category	Helpers
 * @author		ExpressionEngine Dev Team
 * @link		http://codeigniter.com/user_guide/helpers/compatibility_helper.html
 */

// ------------------------------------------------------------------------

if ( ! defined('PHP_EOL'))
{
	define('PHP_EOL', (DIRECTORY_SEPARATOR == '/') ? "\n" : "\r\n");
} 

// ------------------------------------------------------------------------

/**
 * file_put_contents()
 *
 * Writes a string to a file
 * http://us.php.net/manual/en/function.file_put_contents.php
 * argument 4, $context, not supported
 *
 * @access	public
 * @param	string		file name
 * @param	mixed		data to be written
 * @param	int			flags
 * @return	int			length of written string
 */
if ( ! function_exists('file_put_contents'))
{
	function file_put_contents($filename, $data, $flags = NULL)
	{
		if (is_scalar($data))
		{
			settype($data, 'STRING');
		}

		if ( ! is_string($data) && ! is_array($data) && ! is_resource($data))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'file_put_contents(): the 2nd parameter should be either a string or an array', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}

		// read stream if given a stream resource
		if (is_resource($data))
		{
			if (get_resource_type($data) !== 'stream')
			{
				$backtrace = debug_backtrace();
				_exception_handler(E_USER_WARNING, 'file_put_contents(): supplied resource is not a valid stream resource', $backtrace[0]['file'], $backtrace[0]['line']);
				return FALSE;
			}

			$text = '';
			
			while ( ! feof($data))
			{
				$text .= fread($data, 4096);
			}
			
			$data = $text;
			unset($text);
		}
	
		// strings only please!
		if (is_array($data))
		{
			$data = implode('', $data);
		}

		// Set the appropriate mode
		if (($flags & 8) > 0) // 8 = FILE_APPEND flag
		{
			$mode = FOPEN_WRITE_CREATE;
		}
		else
		{
			$mode = FOPEN_WRITE_CREATE_DESTRUCTIVE;
		}
	
		// Check if we're using the include path
		if (($flags & 1) > 0) // 1 = FILE_USE_INCLUDE_PATH flag
		{
			$use_include_path = TRUE;
		}
		else
		{
			$use_include_path = FALSE;
		}
	
		$fp = @fopen($filename, $mode, $use_include_path);
	
		if ($fp === FALSE)
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'file_put_contents('.htmlentities($filename).') failed to open stream', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		if (($flags & LOCK_EX) > 0)
		{
			if ( ! flock($fp, LOCK_EX))
			{
				$backtrace = debug_backtrace();
				_exception_handler(E_USER_WARNING, 'file_put_contents('.htmlentities($filename).') unable to acquire an exclusive lock on file', $backtrace[0]['file'], $backtrace[0]['line']);
				return FALSE;
			}
		}
		
		// write it
		if (($written = @fwrite($fp, $data)) === FALSE)
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'file_put_contents('.htmlentities($filename).') failed to write to '.htmlentities($filename), $backtrace[0]['file'], $backtrace[0]['line']);
		}
	
		// Close the handle
		@fclose($fp);
	
		// Return length
		return $written;
	}
}

// ------------------------------------------------------------------------

/**
 * fputcsv()
 *
 * Format line as CSV and write to file pointer
 * http://us.php.net/manual/en/function.fputcsv.php
 *
 * @access	public
 * @param	resource	file pointer
 * @param	array		data to be written
 * @param	string		delimiter
 * @param	string		enclosure
 * @return	int			length of written string
 */
if ( ! function_exists('fputcsv'))
{
	function fputcsv($handle, $fields, $delimiter = ',', $enclosure = '"')
	{
		// Checking for a handle resource
		if ( ! is_resource($handle))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'fputcsv() expects parameter 1 to be stream resource, '.gettype($handle).' given', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		// OK, it is a resource, but is it a stream?
		if (get_resource_type($handle) !== 'stream')
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'fputcsv() expects parameter 1 to be stream resource, '.get_resource_type($handle).' given', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		// Checking for an array of fields
		if ( ! is_array($fields))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'fputcsv() expects parameter 2 to be array, '.gettype($fields).' given', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		// validate delimiter
		if (strlen($delimiter) > 1)
		{
			$delimiter = substr($delimiter, 0, 1);
			$backtrace = debug_backtrace();
			_exception_handler(E_NOTICE, 'fputcsv() delimiter must be one character long, "'.htmlentities($delimiter).'" used', $backtrace[0]['file'], $backtrace[0]['line']);
		}
	
		// validate enclosure
		if (strlen($enclosure) > 1)
		{
			$enclosure = substr($enclosure, 0, 1);
			$backtrace = debug_backtrace();
			_exception_handler(E_NOTICE, 'fputcsv() enclosure must be one character long, "'.htmlentities($enclosure).'" used', $backtrace[0]['file'], $backtrace[0]['line']);

		}
	
		$out = '';
	
		foreach ($fields as $cell)
		{
			$cell = str_replace($enclosure, $enclosure.$enclosure, $cell);

			if (strpos($cell, $delimiter) !== FALSE OR strpos($cell, $enclosure) !== FALSE OR strpos($cell, "\n") !== FALSE)
			{
				$out .= $enclosure.$cell.$enclosure.$delimiter;
			}
			else
			{
				$out .= $cell.$delimiter;
			}
		}
	
		$length = @fwrite($handle, substr($out, 0, -1)."\n");
	
		return $length;
	}
}

// ------------------------------------------------------------------------

/**
 * stripos()
 *
 * Find position of first occurrence of a case-insensitive string
 * http://us.php.net/manual/en/function.stripos.php
 *
 * @access	public
 * @param	string		haystack
 * @param	string		needle
 * @param	int			offset
 * @return	int			numeric position of the first occurrence of needle in the haystack
 */
if ( ! function_exists('stripos'))
{
	function stripos($haystack, $needle, $offset = NULL)
	{
		// Cast non string scalar values
		if (is_scalar($haystack))
		{
			settype($haystack, 'STRING');
		}
	
		if ( ! is_string($haystack))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'stripos() expects parameter 1 to be string, '.gettype($haystack).' given', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		if ( ! is_scalar($needle))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'stripos() needle is not a string or an integer in '.$backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		if (is_float($offset))
		{
			$offset = (int)$offset;
		}
	
		if ( ! is_int($offset) && ! is_bool($offset) && ! is_null($offset))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'stripos() expects parameter 3 to be long, '.gettype($offset).' given', $backtrace[0]['file'], $backtrace[0]['line']);
			return NULL;
		}
	
		return strpos(strtolower($haystack), strtolower($needle), $offset);
	}
}

// ------------------------------------------------------------------------

/**
 * str_ireplace()
 *
 * Find position of first occurrence of a case-insensitive string
 * http://us.php.net/manual/en/function.str-ireplace.php
 * (parameter 4, $count, is not supported as to do so in PHP 4 would make
 * it a required parameter)
 *
 * @access	public
 * @param	mixed		search
 * @param	mixed		replace
 * @param	mixed		subject
 * @return	int			numeric position of the first occurrence of needle in the haystack
 */
if ( ! function_exists('str_ireplace'))
{
	function str_ireplace($search, $replace, $subject)
	{
		// Nothing to do here
		if ($search === NULL OR $subject === NULL)
		{
			return $subject;
		}
	
		// Crazy arguments
		if (is_scalar($search) && is_array($replace))
		{
			$backtrace = debug_backtrace();

			if (is_object($replace))
			{
				show_error('Object of class '.get_class($replace).' could not be converted to string in '.$backtrace[0]['file'].' on line '.$backtrace[0]['line']);
			}
			else
			{
				_exception_handler(E_USER_NOTICE, 'Array to string conversion in '.$backtrace[0]['file'], $backtrace[0]['line']);
			}
		}
	
		// Searching for an array
		if (is_array($search))
		{
			// Replacing with an array
			if (is_array($replace))
			{
				$search = array_values($search);
				$replace = array_values($replace);

				if (count($search) >= count($replace))
				{
					$replace = array_pad($replace, count($search), '');
				}
				else
				{
					$replace = array_slice($replace, 0, count($search));
				}
			}
			else
			{
				// Replacing with a string all positions
				$replace = array_fill(0, count($search), $replace);
			}
		}
		else
		{
			//Searching for a string and replacing with a string.
			$search  = array((string)$search);
			$replace = array((string)$replace);
		}
		
		// Prepare the search array
		foreach ($search as $search_key => $search_value)
		{
			$search[$search_key] = '/'.preg_quote($search_value, '/').'/i';
		}
		
		// Prepare the replace array (escape backreferences)
		foreach ($replace as $k => $v)
		{
			$replace[$k] = str_replace(array(chr(92), '$'), array(chr(92).chr(92), '\$'), $v);
		}
	
		// do the replacement
		$result = preg_replace($search, $replace, (array)$subject);
	
		// Check if subject was initially a string and return it as a string
		if ( ! is_array($subject))
		{
			return current($result);
		}
	
		// Otherwise, just return the array
		return $result;
	}
}

// ------------------------------------------------------------------------

/**
 * http_build_query()
 *
 * Generate URL-encoded query string
 * http://us.php.net/manual/en/function.http-build-query.php
 *
 * @access	public
 * @param	array		form data
 * @param	string		numeric prefix
 * @param	string		argument separator
 * @return	string		URL-encoded string
 */
if ( ! function_exists('http_build_query'))
{
	function http_build_query($formdata, $numeric_prefix = NULL, $separator = NULL)
	{
		// Check the data
		if ( ! is_array($formdata) && ! is_object($formdata))
		{
			$backtrace = debug_backtrace();
			_exception_handler(E_USER_WARNING, 'http_build_query() Parameter 1 expected to be Array or Object. Incorrect value given', $backtrace[0]['file'], $backtrace[0]['line']);
			return FALSE;
		}
	
		// Cast it as array
		if (is_object($formdata))
		{
			$formdata = get_object_vars($formdata);
		}
	
		// If the array is empty, return NULL
		if (empty($formdata))
		{
			return NULL;
		}
	
		// Argument separator
		if ($separator === NULL)
		{
			$separator = ini_get('arg_separator.output');

			if (strlen($separator) == 0)
			{
				$separator = '&';
			}
		}
	
		// Start building the query
		$tmp = array();

		foreach ($formdata as $key => $val)
		{
			if ($val === NULL)
			{
				continue;
			}
	
			if (is_integer($key) && $numeric_prefix != NULL)
			{
				$key = $numeric_prefix.$key;
			}
	
			if (is_resource($val))
			{
				return NULL;
			}
			
			// hand it off to a recursive parser
			$tmp[] = _http_build_query_helper($key, $val, $separator);
		}
	
		return implode($separator, $tmp);
	}
	
	
	// Helper helper.  Remind anyone of college?
	// Required to handle recursion in nested arrays.
	// 
	// You could shave fractions of fractions of a second by moving where
	// the urlencoding takes place, but it's much less intuitive, and if
	// your application has 10,000 form fields, well, you have other problems ;)
	function _http_build_query_helper($key, $val, $separator = '&')
	{	
		if (is_scalar($val))
		{
			return urlencode($key).'='.urlencode($val);			
		}
		else
		{
			// arrays please
			if (is_object($val))
			{
				$val = get_object_vars($val);
			}
			
			foreach ($val as $k => $v)
			{
				$tmp[] = _http_build_query_helper($key.'['.$k.']', $v, $separator);
			}
		}
			
		return implode($separator, $tmp);
	}
}


/* End of file compatibility_helper.php */
/* Location: ./system/helpers/compatibility_helper.php */