function serialize(data){
	var i;
	var string = '';
	var count = 0;
	if (typeof(data) == 'string'){
		if (parseInt(data) == data)
			data = parseInt(data);
	}
	if (data == null)
		return 'N;';
	else if (typeof(data) == 'object' && data.constructor == Array){
		for (i in data){
			if (typeof(data[i]) != "function"){
				count++;
				string += serialize(i) + serialize(data[i]);
			}
		}
		string = 'a:' + count + ':{' + string + '}';
		return string;
	}
	else if (typeof(data) == 'object'){
		var regex = /function\s(.*?)\(.*?\)\s\{/
		var constructor = data.constructor;
		constructor = regex.exec(constructor.toString())[1];
		for (i in data){
			if (typeof(data[i]) != "function"){
				count++;
				string += serialize(i) + serialize(data[i]);
			}
		}
		string = 'O:'+constructor.length+':"'+constructor+'":' + count + ':{' + string + '}';
		return string;
	}
	else if (typeof(data) == 'string'){
		return 's:' + data.length + ':"' + data + '";';
	}
	else if (typeof(data) == 'number'){
		if (Math.round(data) == data){
			return 'i:' + data + ';';
		}
		else{
			return 'd:' + data + ';';
		}
	}
	else if (typeof(data) == 'boolean'){
		if (data == true){
			return 'b:1;';
		}
		else{
			return 'b:0;';
		}
	}
}
	
var lengths = new Array();
function unserialize(data){
	if (data.substring(0, 1) == 'a'){
		var regex = new RegExp(/a\:([^\:]*)\:/);
		if (match = regex.exec(data)){
			var elements = Number(match[1]);
			var counter = elements * 2;
		 	var arr = new Array(elements);
		 	var len = 0;
			var arrLength = 4 + match[1].length;
			data = data.substr(arrLength);  
			for (var i = 0; i < counter; i+=2){
				var key = unserialize(data);  
				len = lengths.pop();
				data = data.substr(len);
				arrLength += len;

				var value = unserialize(data);      
				len = lengths.pop();
				data = data.substr(len);
				arrLength += len;
				
				arr[key] = value;
			}
			arrLength++;
			lengths.push(arrLength);
			return arr;
		}
	}
	else if (data.substring(0, 1) == 'O'){
		var regex = new RegExp(/O\:(\d+)\:"([^"]*)"\:(\d+)\:/);
		if (match = regex.exec(data)){
			eval("var obj = new "+match[2]+"();");
			var elements = Number(match[3]);
			var counter = elements * 2;
		 	var len = 0;
			var objLength = match[0].length + 1;
			data = data.substr(objLength);  
			for (var i = 0; i < counter; i+=2){
				var key = unserialize(data);  
				len = lengths.pop();
				data = data.substr(len);
				objLength += len;

				var value = unserialize(data);      
				len = lengths.pop();
				data = data.substr(len);
				objLength += len;
				
				obj[key] = value;
			}
			objLength++;
			lengths.push(objLength);
			return obj;
		}
	}
	else if (data.substring(0, 1) == 'i'){
		var regex = new RegExp(/i\:([^;]*);/);
		if (match = regex.exec(data)){  
			var returnVal = match[1];
			lengths.push(3 + returnVal.toString().length);
			return Number(returnVal);
		}
	}
	else if (data.substring(0, 1) == 'd'){
		var regex = new RegExp(/d\:([^;]*);/);
		if (match = regex.exec(data)){
			var returnVal = match[1];
			lengths.push(3 + returnVal.toString().length);
			return Number(match[1]);
		}
	}                            
	
	else if (data.substring(0, 1) == 'N'){
		lengths.push(2);
		return null;
	}
	else if (data.substring(0, 1) == 's'){
		var regex = new RegExp(/s\:([^\:]*)\:/);
		if (match = regex.exec(data)){
			var returnVal = data.substr(4 + match[1].length, Number(match[1]));
			lengths.push(6 + match[1].length + returnVal.length);
			return returnVal;
		}
	}
	else if (data.substring(0, 1) == 'b'){
		lengths.push(4);
		if (data.substring(0, 3) == 'b:1'){
			return true;
		}
		else if (data.substring(0, 3) == 'b:0'){
			return false;
		}
	}
}