<?php
 class vB_Utility_Unserialize { use vB_Utility_Trait_NoSerialize; public static function unserialize($string) { $index = 0; $strlen = strlen($string); $value = static::getValue($index, $strlen, $string); if ($index != $strlen) { throw new Exception('Finished but not at end of string'); } return $value; } protected static function getValue(&$index, $strlen, $string) { switch($string[$index]) { case 'a': return static::getArray($index, $strlen, $string); break; case 's': $length = intval(static::getPrefix($index, $strlen, $string, ':')); return static::getString($index, $strlen, $string, $length); break; case 'i': return intval(static::getPrefix($index, $strlen, $string, ';')); break; case 'd': $value = static::getPrefix($index, $strlen, $string, ';'); return floatval($value); break; case 'b': return boolval(static::getPrefix($index, $strlen, $string, ';')); break; case 'N': return static::getNull($index, $strlen, $string); break; default: throw new Exception('Invalid unserialize type: ' . $string[$index] . ' at position ' . $index); break; } } protected static function getArray(&$index, $strlen, $string) { $length = (int) static::getPrefix($index, $strlen, $string, ':'); if ($index + 1 >= $strlen) { throw new Exception('Unexpected end of string'); } if ($string[$index] != '{') { throw new Exception('Expected { at position ' . $index); } $index++; $array = []; for ($i = 0; $i < $length; $i++) { $keystart = $index; $key = static::getValue($index, $strlen, $string); if (!(is_int($key) OR is_string($key))) { throw new Exception('Invalid key type ' . gettype($key) . ' at index ' . $keystart); } $value = static::getValue($index, $strlen, $string); $array[$key] = $value; } if ($string[$index] != '}') { throw new Exception('Expected } at position ' . $index); } $index++; return $array; } protected static function getNull(&$index, $strlen, $string) { if ($index+1 >= $strlen) { throw new Exception('Unexpected end of string'); } $index++; if ($string[$index] != ';') { throw new Exception('Expected ; at position ' . $index); } $index++; return null; } protected static function getPrefix(&$index, $strlen, $string, $lastchar) { $start = $index+2; if ($start >= $strlen) { throw new Exception('Unexpected end of string'); } if ($string[$index+1] != ':') { throw new Exception('Expected : at position ' . ($index + 1)); } $end = strpos($string, $lastchar, $start); if ($end === false) { throw new Exception('Expected ' . $lastchar . ', reached end of string'); } $value = substr($string, $start, $end - ($start)); $index += (2+strlen($value)); if ($string[$index] != $lastchar) { throw new Exception('Expected ' . $lastchar . ' at position ' . $index); } $index++; return $value; } protected static function getString(&$index, $strlen, $string, $length) { if ($index+2+$length >= $strlen) { throw new Exception('Unexpected end of string'); } if ($string[$index] != '"') { throw new Exception('Expected " at position ' . $index); } $value = substr($string, $index+1, $length); $index += $length+1; if ($string[$index] != '"') { throw new Exception('Expected " at position ' . $index); } $index++; if ($string[$index] != ';') { throw new Exception('Expected " at position ' . $index); } $index++; return $value; } } ?>
