function Files_CookieUtils(cookieName, cbOnIdNumberChange, daysToKeep, domain, path, secure) {

	this.name = cookieName;

	this.limitExceeded = false;

	if (cbOnIdNumberChange) {
		this.callback = cbOnIdNumberChange
	}

	//number of days to keep, 0 - session cookie
	if (! (daysToKeep)) daysToKeep = 30;
	if (daysToKeep > 0) {
			var expiresDate = new Date(); // get current time
        	expiresDate.setTime(expiresDate.getTime() + (daysToKeep*24*60*60*1000));
			this.expire = "; expires=" + expiresDate.toGMTString(); // get formatted date string
	} else {
  		this.expire = "";
	}

	if (path) {
		this.path = "; path=" + path;
	} else {
		this.path = "; path=/";
	}

	if (domain) {
		if (domain == 1) {
			this.domain = "; domain=.files.mail.ru";
		} else {
			if (domain.substr(0,1) == ".") domain = domain.substr(1);
			this.domain = "; domain=." + domain;
		}
	} else {

		this.domain = "";
	}



	this.getCookie = function  () {
	        var prefix = this.name + "=";
	        var cookieStartIndex = document.cookie.indexOf(prefix);
	        if (cookieStartIndex == -1) return null;
	        var cookieEndIndex = document.cookie.indexOf(";", cookieStartIndex + prefix.length);
	        if (cookieEndIndex == -1) cookieEndIndex = document.cookie.length;
	        return unescape(document.cookie.substring(cookieStartIndex + prefix.length, cookieEndIndex));
	}

	this.setCookie = function (value) {
	        var valueEscaped = escape(value);
	        var newCookie = this.name + "=" + valueEscaped + this.path + this.domain + this.expire;
	        if (valueEscaped.length <= 4000) {
				document.cookie = newCookie + ";";
				this.limitExceeded = false;
			} else {
				this.limitExceeded = true;
			}
	}

	this.expireCookie = function() {
		var futher_cookie = this.name + "=." + this.path + this.domain + "; expires=Sun, 23 May 1982 20:00:00 GMT;"
		document.cookie = futher_cookie;
		if (this.callback) this.callback.apply(window, [this.countIds(), this.name]);
	}

	this.setId = function (toAdd, newId) {
		if (toAdd == true) {
			this.addId(newId);
		} else {
			this.removeId(newId);
		}
	}

	this.addId = function (newId) {
		var cookieString = this.getCookie();
		var idNewStr = LCvt(newId);
		if (! cookieString) cookieString = "";
		var idStartIndex = cookieString.indexOf("." + idNewStr + ".");
		if (idStartIndex == -1) {
			if (cookieString.length == 0) cookieString = ".";
			cookieString = cookieString + idNewStr + ".";
			this.setCookie(cookieString);
			if (this.callback) this.callback.apply(window, [this.countIds(), this.name]);
		}
	}

	this.removeId = function (newId) {
		var cookieString = this.getCookie();
		var idNewStr =  LCvt(newId);
		if (! cookieString) cookieString = "";
		var idStartIndex = cookieString.indexOf("." + idNewStr + ".");
		if (idStartIndex != -1) {
			cookieString = cookieString.substr(0, idStartIndex) + cookieString.substr(idStartIndex + idNewStr.length + 1);
			this.setCookie(cookieString);
			if (this.callback) {
				if (this.callback) this.callback.apply(window, [this.countIds(), this.name]);
			}
		}
	}

	this.isLimitOk = function() {
		return this.limitExceeded;
	}

	this.countIds = function () {
		var cookieString = this.getCookie();
		if (! cookieString) return 0;
		//alert(this.getCookie())
		var numberOfItems = cookieString.split(".");
		return numberOfItems.length - 2;
	}
}


var  MRIS_COOKIE = 1;
var MRIS_COOTIME = 2;
var MRIS_RUNTIME = 3;


function MRIdStorage (mode, storageName) {
	this.name = storageName;

	if (mode) this.mode = mode;
	if (this.mode == MRIS_COOKIE || this.mode == MRIS_COOTIME) {
		this.cookieObj = new Files_CookieUtils(this.name, 0, -1);
	}

	this.idArr = new Array ();
	this.idHash = {};

	this.AddId = function (newId) {
		newId = newId - 0;
		var curIdx = this.idArr.find(newId);
		if (!curIdx) { this.idArr.push(newId) }
		if (this.cookieObj) { this.cookieObj.addId(newId) }
	}

	this.AddIdToHash = function (id, vfileid) {
		id = id -0;
		vfileid = vfileid -0;

		this.idHash[id] = {
			vfileid: vfileid
		};
	}
	
	this.GetUploadId = function (vfileid) {
		for (var cur_val in this.idHash) {
			if (this.idHash[cur_val].vfileid == vfileid) {
				return cur_val;
			}
		}
		return;
	}

	this.AddIds = function (curIdArr) {
		for (i = 0; i<curIdArr.length; i++) {
			this.AddId(curIdArr[i]);
		}
	}

	this.RemoveId = function (newId) {
		newId = newId - 0;
		var curIdx = this.idArr.find(newId);
		if (curIdx) { this.idArr.splice(curIdx,1) }
		if (this.cookieObj) { this.cookieObj.removeId(newId) }
	}

	this.SetId = function (toAdd, newId) {
		if (toAdd == true) {
			this.addId(newId);
		} else {
			this.removeId(newId);
		}
	}

	this.Clear = function () {
		this.idArr = [];
		if (this.cookieObj) { this.cookieObj.expireCookie() }
	}
	
	this.GetEncodedIds = function () {
		var enc_str = ".";
		for (i = 0; i<this.idArr.length; i++) {
			enc_str += LCvt(this.idArr[i]) + ".";
		}
		return enc_str;
	}

	this.GetURLIds = function () {
		var enc_str = "";
		for (i = 0; i<this.idArr.length; i++) {
			enc_str += "%26id%3D" + this.idArr[i];
		}
		return enc_str.substr(3);
	}

	this.GetList = function (alternativeListFlag) {
		if (this.mode == MRIS_COOKIE) {
			return this.cookieObj.getCookie();
		} else if (this.mode == MRIS_RUNTIME) {
			return this.GetEncodedIds();
		} else if (this.mode == MRIS_COOTIME) {
			if (alternativeListFlag) {
				return this.cookieObj.getCookie();
			} else {
				return this.GetEncodedIds;
			}
		}
	}

	this.ApplyList = function (e) {
		if (this.mode == MRIS_COOKIE) {
			// nothing here...
		} else if (this.mode == MRIS_RUNTIME) {
			try {
				e.value = this.GetList();
			} catch (e) {}
		} else if (this.mode == MRIS_COOTIME) {
			this.SetCookieData();
			this.cookieObj.getCookie();
		}
	}

	this.SetCookieData = function () {
		for (i = 0; i<this.idArr.length; i++) {
			if (this.cookieObj) { this.cookieObj.addId(newId) }
		}
	}
}


if (!Array.prototype.find) {
	Array.prototype.find = function(searchStr) {
	  var returnArray = false;
	  for (i=0; i<this.length; i++) {
	    if (typeof(searchStr) == 'function') {
	      if (searchStr.test(this[i])) {
	        if (!returnArray) { returnArray = [] }
	        returnArray.push(i);
	      }
	    } else {
	      if (this[i]===searchStr) {
	        if (!returnArray) { returnArray = [] }
	        returnArray.push(i);
	      }
	    }
	  }
	  return returnArray;
	}
}

function LCvt(valueToConvert) {
	var code_base = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz*";
    var C, S = "", T = 0, CV = code_base, X = valueToConvert;
    if (!( isFinite(X) && X>=0 )) { return }
    if ( (B = +CV.length) < 2 ) { return }
    // Convert Number to Base :-
    do { C = X%B ; C = CV.charAt(C)
      S = C + S ; X = Math.floor(X/B) } while (X!=0)
    // Convert back to Number :-
    for (var J = 0 ; J < S.length ; J++)
      T = T*B + CV.indexOf(S.substr(J, 1))
    return S;
}
