Work around database corruption reported on WP:VPT -- unlinked title instead of PHP...
[lhc/web/wiklou.git] / includes / IP.php
index e76f66c..7f7fc3c 100644 (file)
@@ -150,6 +150,24 @@ class IP {
                $ip_oct = preg_replace( '/(^|:)0+' . RE_IPV6_WORD . '/', '$1$2', $ip_oct );
                return $ip_oct;
        }
+       
+       /**
+        * Given an unsigned integer, returns an IPv6 address in octet notation
+        * @param $ip string hex IP
+        * @return string
+        */
+       public static function HextoOctet( $ip_hex ) {
+               // Convert to padded uppercase hex
+               $ip_hex = str_pad( strtoupper($ip_hex), 32, '0');
+               // Seperate into 8 octets
+               $ip_oct = substr( $ip_hex, 0, 4 );
+               for ($n=1; $n < 8; $n++) {
+                       $ip_oct .= ':' . substr($ip_hex, 4*$n, 4);
+               }
+               // NO leading zeroes
+               $ip_oct = preg_replace( '/(^|:)0+' . RE_IPV6_WORD . '/', '$1$2', $ip_oct );
+               return $ip_oct;
+       }
 
        /**
         * Convert a network specification in IPv6 CIDR notation to an integer network and a number of bits
@@ -320,7 +338,7 @@ class IP {
        public static function toHex( $ip ) {
                $n = self::toUnsigned( $ip );
                if ( $n !== false ) {
-                       $n = ( self::isIPv6($ip) ) ? "v6-" . wfBaseConvert( $n, 10, 16, 32, false ) : wfBaseConvert( $n, 10, 16, 8, false );
+                       $n = self::isIPv6($ip) ? "v6-" . wfBaseConvert( $n, 10, 16, 32, false ) : wfBaseConvert( $n, 10, 16, 8, false );
                }
                return $n;
        }
@@ -426,12 +444,16 @@ class IP {
                } elseif ( strpos( $range, '-' ) !== false ) {
                        # Explicit range
                        list( $start, $end ) = array_map( 'trim', explode( '-', $range, 2 ) );
-                       $start = self::toUnsigned( $start ); $end = self::toUnsigned( $end );
-                       if ( $start > $end ) {
-                               $start = $end = false;
+                       if( self::isIPAddress( $start ) && self::isIPAddress( $end ) ) {
+                               $start = self::toUnsigned( $start ); $end = self::toUnsigned( $end );
+                               if ( $start > $end ) {
+                                       $start = $end = false;
+                               } else {
+                                       $start = sprintf( '%08X', $start );
+                                       $end = sprintf( '%08X', $end );
+                               }
                        } else {
-                               $start = sprintf( '%08X', $start );
-                               $end = sprintf( '%08X', $end );
+                               $start = $end = false;
                        }
                } else {
                        # Single IP