All pastes #545199 Raw Edit

Stuff

public text v1 · immutable
·published 2007-06-06 18:52 UTC
rendered paste body
--- C:\Documents and Settings\Dave\Local Settings\Temp\TCV49189.tmp\oracle.1.40.php	Tue Jun 05 23:23:30 2007
+++ C:\Documents and Settings\Dave\Desktop\flexcvs\phpBB3\includes\db\oracle.php	Wed Jun 06 00:04:56 2007
@@ -48,7 +48,7 @@
 			$connect = $sqlserver . (($port) ? ':' . $port : '') . '/' . $database;
 		}
 
-		$this->db_connect_id = ($new_link) ? @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8') : (($this->persistency) ? @ociplogon($this->user, $sqlpassword, $connect, 'UTF8') : @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8'));
+		$this->db_connect_id = ($new_link) ? @ocinlogon($this->user, $sqlpassword, $connect, 'UTF8') : (($this->persistency) ? @ociplogon($this->user, $sqlpassword, $connect, 'UTF8') : @ocilogon($this->user, $sqlpassword, $connect, 'UTF8'));
 
 		return ($this->db_connect_id) ? $this->db_connect_id : $this->sql_error('');
 	}
@@ -86,6 +86,90 @@
 	}
 
 	/**
+	* Oracle specific code to handle the fact that it does not compare columns properly
+	* @access private
+	*/
+	function _rewrite_col_compare($args)
+	{
+		if (sizeof($args) == 4)
+		{
+			if ($args[2] == '=')
+			{
+				return '(' . $args[0] . ' OR (' . $args[1] . ' is NULL AND ' . $args[3] . ' is NULL))';
+			}
+			else if ($args[2] == '<>')
+			{
+				// really just a fancy way of saying foo <> bar or (foo is NULL XOR bar is NULL) but SQL has no XOR :P
+				return '(' . $args[0] . ' OR ((' . $args[1] . ' is NULL AND ' . $args[3] . ' is NOT NULL) OR (' . $args[1] . ' is NOT NULL AND ' . $args[3] . ' is NULL)))';
+			}
+		}
+		else
+		{
+			return $this->_rewrite_where($args[0]);
+		}
+	}
+
+	/**
+	* Oracle specific code to handle it's lack of sanity
+	* @access private
+	*/
+	function _rewrite_where($where_clause)
+	{
+		preg_match_all('/\s*(AND|OR)?\s*([\w_.]++)\s*(?:(=|<>)\s*((?>\'(?>[^\']++|\'\')*+\'|\d+))|((NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d+,? ?)*+\)))/', $where_clause, $result, PREG_SET_ORDER);
+		$out = '';
+		foreach ($result as $val)
+		{
+			if (!isset($val[5]))
+			{
+				if ($val[4] !== "''")
+				{
+					$out .= $val[0];
+				}
+				else
+				{
+					$out .= ' ' . $val[1] . ' ' . $val[2];
+					if ($val[3] == '=')
+					{
+						$out .= ' is NULL';
+					}
+					else if ($val[3] == '<>')
+					{
+						$out .= ' is NOT NULL';
+					}
+				}
+			}
+			else
+			{
+				$in_clause = array();
+				$sub_exp = substr($val[5], strpos($val[5], '(') + 1, -1);
+				$extra = false;
+				preg_match_all('/\'(?>[^\']++|\'\')*+\'|\d++/', $sub_exp, $sub_vals, PREG_PATTERN_ORDER);
+				foreach ($sub_vals[0] as $sub_val)
+				{
+					if ($sub_val !== "''")
+					{
+						$in_clause[] = $sub_val;
+					}
+					else
+					{
+						$extra = true;
+					}
+				}
+				if (!$extra)
+				{
+					$out .= $val[0];
+				}
+				else
+				{
+					$out .= ' ' . $val[1] . ' (' . $val[2]. ' ' . (isset($val[6]) ? $val[6] : '') . 'IN(' . implode(', ', $in_clause) . ') OR ' . $val[2] . ' is ' . (isset($val[6]) ? $val[6] : '') . 'NULL)';
+				}
+			}
+		}
+
+		return $out;
+	}
+
+	/**
 	* Base query method
 	*
 	* @param	string	$query		Contains the SQL query which shall be executed
@@ -151,13 +234,13 @@
 							unset($art);
 						}
 					}
-					else if (preg_match_all('/^(UPDATE [\\w_]++\\s+SET )(\\w+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+)(?:, \\w+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+))*+)\\s+(WHERE.*)$/s', $query, $data, PREG_SET_ORDER))
+					else if (preg_match_all('/^(UPDATE [\\w_]++\\s+SET )([\\w_]+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+)(?:, [\\w_]+ = (?:\'(?:[^\']++|\'\')*+\'|\\d+))*+)\\s+(WHERE.*)$/s', $query, $data, PREG_SET_ORDER))
 					{
 						if (strlen($data[0][2]) > 4000)
 						{
 							$update = $data[0][1];
 							$where = $data[0][3];
-							preg_match_all('/(\\w++) = (\'(?:[^\']++|\'\')*+\'|\\d++)/', $data[0][2], $temp, PREG_SET_ORDER);
+							preg_match_all('/([\\w_]++) = (\'(?:[^\']++|\'\')*+\'|\\d++)/', $data[0][2], $temp, PREG_SET_ORDER);
 							unset($data);
 
 							$art = array();
@@ -178,6 +261,29 @@
 							unset($art);
 						}
 					}
+				}
+
+				switch (substr($query, 0, 6))
+				{
+					case 'DELETE':
+						if (preg_match('/^(DELETE FROM [\w_]++ WHERE)((?:\s*(?:AND|OR)?\s*[\w_]+\s*(?:(?:=|<>)\s*(?>\'(?>[^\']++|\'\')*+\'|\d+)|(?:NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d+,? ?)*+\)))*+)$/', $query, $regs))
+						{
+							$query = $regs[1] . $this->_rewrite_where($regs[2]);
+							unset($regs);
+						}
+					break;
+
+					case 'UPDATE':
+						if (preg_match('/^(UPDATE [\\w_]++\\s+SET [\\w_]+\s*=\s*(?:\'(?:[^\']++|\'\')*+\'|\\d++|:\w++)(?:, [\\w_]+\s*=\s*(?:\'(?:[^\']++|\'\')*+\'|\\d++|:\w++))*+\\s+WHERE)(.*)$/s',  $query, $regs))
+						{
+							$query = $regs[1] . $this->_rewrite_where($regs[2]);
+							unset($regs);
+						}
+					break;
+
+					case 'SELECT':
+						$query = preg_replace_callback('/([\w_.]++)\s*(?:(=|<>)\s*(?>\'(?>[^\']++|\'\')*+\'|\d++|([\w_.]++))|(?:NOT )?IN\s*\((?>\'(?>[^\']++|\'\')*+\',? ?|\d++,? ?)*+\))/', array($this, '_rewrite_col_compare'), $query);
+					break;
 				}
 
 				$this->query_result = @ociparse($this->db_connect_id, $query);