From ffb1997902facb36b78a7cfa522f41f2b3d71cda Mon Sep 17 00:00:00 2001 From: Mike Macgirvin Date: Wed, 8 Sep 2010 20:14:17 -0700 Subject: mistpark 2.0 infrasturcture lands --- library/HTMLPurifier/AttrDef/URI/Email.php | 17 ++++ .../HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php | 21 +++++ library/HTMLPurifier/AttrDef/URI/Host.php | 62 ++++++++++++++ library/HTMLPurifier/AttrDef/URI/IPv4.php | 39 +++++++++ library/HTMLPurifier/AttrDef/URI/IPv6.php | 99 ++++++++++++++++++++++ 5 files changed, 238 insertions(+) create mode 100644 library/HTMLPurifier/AttrDef/URI/Email.php create mode 100644 library/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php create mode 100644 library/HTMLPurifier/AttrDef/URI/Host.php create mode 100644 library/HTMLPurifier/AttrDef/URI/IPv4.php create mode 100644 library/HTMLPurifier/AttrDef/URI/IPv6.php (limited to 'library/HTMLPurifier/AttrDef/URI') diff --git a/library/HTMLPurifier/AttrDef/URI/Email.php b/library/HTMLPurifier/AttrDef/URI/Email.php new file mode 100644 index 000000000..bfee9d166 --- /dev/null +++ b/library/HTMLPurifier/AttrDef/URI/Email.php @@ -0,0 +1,17 @@ +" + // that needs more percent encoding to be done + if ($string == '') return false; + $string = trim($string); + $result = preg_match('/^[A-Z0-9._%-]+@[A-Z0-9.-]+\.[A-Z]{2,4}$/i', $string); + return $result ? $string : false; + } + +} + +// vim: et sw=4 sts=4 diff --git a/library/HTMLPurifier/AttrDef/URI/Host.php b/library/HTMLPurifier/AttrDef/URI/Host.php new file mode 100644 index 000000000..2156c10c6 --- /dev/null +++ b/library/HTMLPurifier/AttrDef/URI/Host.php @@ -0,0 +1,62 @@ +ipv4 = new HTMLPurifier_AttrDef_URI_IPv4(); + $this->ipv6 = new HTMLPurifier_AttrDef_URI_IPv6(); + } + + public function validate($string, $config, $context) { + $length = strlen($string); + if ($string === '') return ''; + if ($length > 1 && $string[0] === '[' && $string[$length-1] === ']') { + //IPv6 + $ip = substr($string, 1, $length - 2); + $valid = $this->ipv6->validate($ip, $config, $context); + if ($valid === false) return false; + return '['. $valid . ']'; + } + + // need to do checks on unusual encodings too + $ipv4 = $this->ipv4->validate($string, $config, $context); + if ($ipv4 !== false) return $ipv4; + + // A regular domain name. + + // This breaks I18N domain names, but we don't have proper IRI support, + // so force users to insert Punycode. If there's complaining we'll + // try to fix things into an international friendly form. + + // The productions describing this are: + $a = '[a-z]'; // alpha + $an = '[a-z0-9]'; // alphanum + $and = '[a-z0-9-]'; // alphanum | "-" + // domainlabel = alphanum | alphanum *( alphanum | "-" ) alphanum + $domainlabel = "$an($and*$an)?"; + // toplabel = alpha | alpha *( alphanum | "-" ) alphanum + $toplabel = "$a($and*$an)?"; + // hostname = *( domainlabel "." ) toplabel [ "." ] + $match = preg_match("/^($domainlabel\.)*$toplabel\.?$/i", $string); + if (!$match) return false; + + return $string; + } + +} + +// vim: et sw=4 sts=4 diff --git a/library/HTMLPurifier/AttrDef/URI/IPv4.php b/library/HTMLPurifier/AttrDef/URI/IPv4.php new file mode 100644 index 000000000..ec4cf591b --- /dev/null +++ b/library/HTMLPurifier/AttrDef/URI/IPv4.php @@ -0,0 +1,39 @@ +ip4) $this->_loadRegex(); + + if (preg_match('#^' . $this->ip4 . '$#s', $aIP)) + { + return $aIP; + } + + return false; + + } + + /** + * Lazy load function to prevent regex from being stuffed in + * cache. + */ + protected function _loadRegex() { + $oct = '(?:25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]|[0-9])'; // 0-255 + $this->ip4 = "(?:{$oct}\\.{$oct}\\.{$oct}\\.{$oct})"; + } + +} + +// vim: et sw=4 sts=4 diff --git a/library/HTMLPurifier/AttrDef/URI/IPv6.php b/library/HTMLPurifier/AttrDef/URI/IPv6.php new file mode 100644 index 000000000..9454e9be5 --- /dev/null +++ b/library/HTMLPurifier/AttrDef/URI/IPv6.php @@ -0,0 +1,99 @@ +ip4) $this->_loadRegex(); + + $original = $aIP; + + $hex = '[0-9a-fA-F]'; + $blk = '(?:' . $hex . '{1,4})'; + $pre = '(?:/(?:12[0-8]|1[0-1][0-9]|[1-9][0-9]|[0-9]))'; // /0 - /128 + + // prefix check + if (strpos($aIP, '/') !== false) + { + if (preg_match('#' . $pre . '$#s', $aIP, $find)) + { + $aIP = substr($aIP, 0, 0-strlen($find[0])); + unset($find); + } + else + { + return false; + } + } + + // IPv4-compatiblity check + if (preg_match('#(?<=:'.')' . $this->ip4 . '$#s', $aIP, $find)) + { + $aIP = substr($aIP, 0, 0-strlen($find[0])); + $ip = explode('.', $find[0]); + $ip = array_map('dechex', $ip); + $aIP .= $ip[0] . $ip[1] . ':' . $ip[2] . $ip[3]; + unset($find, $ip); + } + + // compression check + $aIP = explode('::', $aIP); + $c = count($aIP); + if ($c > 2) + { + return false; + } + elseif ($c == 2) + { + list($first, $second) = $aIP; + $first = explode(':', $first); + $second = explode(':', $second); + + if (count($first) + count($second) > 8) + { + return false; + } + + while(count($first) < 8) + { + array_push($first, '0'); + } + + array_splice($first, 8 - count($second), 8, $second); + $aIP = $first; + unset($first,$second); + } + else + { + $aIP = explode(':', $aIP[0]); + } + $c = count($aIP); + + if ($c != 8) + { + return false; + } + + // All the pieces should be 16-bit hex strings. Are they? + foreach ($aIP as $piece) + { + if (!preg_match('#^[0-9a-fA-F]{4}$#s', sprintf('%04s', $piece))) + { + return false; + } + } + + return $original; + + } + +} + +// vim: et sw=4 sts=4 -- cgit v1.2.3