/* cryptojs v3.1.2 code.google.com/p/crypto-js (c) 2009-2013 by jeff mott. all rights reserved. code.google.com/p/crypto-js/wiki/license */ /** * cryptojs core components. */ var cryptojs = cryptojs || (function (math, undefined) { /** * cryptojs namespace. */ var c = {}; /** * library namespace. */ var c_lib = c.lib = {}; /** * base object for prototypal inheritance. */ var base = c_lib.base = (function () { function f() {} return { /** * creates a new object that inherits from this object. * * @param {object} overrides properties to copy into the new object. * * @return {object} the new object. * * @static * * @example * * var mytype = cryptojs.lib.base.extend({ * field: 'value', * * method: function () { * } * }); */ extend: function (overrides) { // spawn f.prototype = this; var subtype = new f(); // augment if (overrides) { subtype.mixin(overrides); } // create default initializer if (!subtype.hasownproperty('init')) { subtype.init = function () { subtype.$super.init.apply(this, arguments); }; } // initializer's prototype is the subtype object subtype.init.prototype = subtype; // reference supertype subtype.$super = this; return subtype; }, /** * extends this object and runs the init method. * arguments to create() will be passed to init(). * * @return {object} the new object. * * @static * * @example * * var instance = mytype.create(); */ create: function () { var instance = this.extend(); instance.init.apply(instance, arguments); return instance; }, /** * initializes a newly created object. * override this method to add some logic when your objects are created. * * @example * * var mytype = cryptojs.lib.base.extend({ * init: function () { * // ... * } * }); */ init: function () { }, /** * copies properties into this object. * * @param {object} properties the properties to mix in. * * @example * * mytype.mixin({ * field: 'value' * }); */ mixin: function (properties) { for (var propertyname in properties) { if (properties.hasownproperty(propertyname)) { this[propertyname] = properties[propertyname]; } } // ie won't copy tostring using the loop above if (properties.hasownproperty('tostring')) { this.tostring = properties.tostring; } }, /** * creates a copy of this object. * * @return {object} the clone. * * @example * * var clone = instance.clone(); */ clone: function () { return this.init.prototype.extend(this); } }; }()); /** * an array of 32-bit words. * * @property {array} words the array of 32-bit words. * @property {number} sigbytes the number of significant bytes in this word array. */ var wordarray = c_lib.wordarray = base.extend({ /** * initializes a newly created word array. * * @param {array} words (optional) an array of 32-bit words. * @param {number} sigbytes (optional) the number of significant bytes in the words. * * @example * * var wordarray = cryptojs.lib.wordarray.create(); * var wordarray = cryptojs.lib.wordarray.create([0x00010203, 0x04050607]); * var wordarray = cryptojs.lib.wordarray.create([0x00010203, 0x04050607], 6); */ init: function (words, sigbytes) { words = this.words = words || []; if (sigbytes != undefined) { this.sigbytes = sigbytes; } else { this.sigbytes = words.length * 4; } }, /** * converts this word array to a string. * * @param {encoder} encoder (optional) the encoding strategy to use. default: cryptojs.enc.hex * * @return {string} the stringified word array. * * @example * * var string = wordarray + ''; * var string = wordarray.tostring(); * var string = wordarray.tostring(cryptojs.enc.utf8); */ tostring: function (encoder) { return (encoder || hex).stringify(this); }, /** * concatenates a word array to this word array. * * @param {wordarray} wordarray the word array to append. * * @return {wordarray} this word array. * * @example * * wordarray1.concat(wordarray2); */ concat: function (wordarray) { // shortcuts var thiswords = this.words; var thatwords = wordarray.words; var thissigbytes = this.sigbytes; var thatsigbytes = wordarray.sigbytes; // clamp excess bits this.clamp(); // concat if (thissigbytes % 4) { // copy one byte at a time for (var i = 0; i < thatsigbytes; i++) { var thatbyte = (thatwords[i >>> 2] >>> (24 - (i % 4) * 8)) & 0xff; thiswords[(thissigbytes + i) >>> 2] |= thatbyte << (24 - ((thissigbytes + i) % 4) * 8); } } else if (thatwords.length > 0xffff) { // copy one word at a time for (var i = 0; i < thatsigbytes; i += 4) { thiswords[(thissigbytes + i) >>> 2] = thatwords[i >>> 2]; } } else { // copy all words at once thiswords.push.apply(thiswords, thatwords); } this.sigbytes += thatsigbytes; // chainable return this; }, /** * removes insignificant bits. * * @example * * wordarray.clamp(); */ clamp: function () { // shortcuts var words = this.words; var sigbytes = this.sigbytes; // clamp words[sigbytes >>> 2] &= 0xffffffff << (32 - (sigbytes % 4) * 8); words.length = math.ceil(sigbytes / 4); }, /** * creates a copy of this word array. * * @return {wordarray} the clone. * * @example * * var clone = wordarray.clone(); */ clone: function () { var clone = base.clone.call(this); clone.words = this.words.slice(0); return clone; }, /** * creates a word array filled with random bytes. * * @param {number} nbytes the number of random bytes to generate. * * @return {wordarray} the random word array. * * @static * * @example * * var wordarray = cryptojs.lib.wordarray.random(16); */ random: function (nbytes) { var words = []; for (var i = 0; i < nbytes; i += 4) { words.push((math.random() * 0x100000000) | 0); } return new wordarray.init(words, nbytes); } }); /** * encoder namespace. */ var c_enc = c.enc = {}; /** * hex encoding strategy. */ var hex = c_enc.hex = { /** * converts a word array to a hex string. * * @param {wordarray} wordarray the word array. * * @return {string} the hex string. * * @static * * @example * * var hexstring = cryptojs.enc.hex.stringify(wordarray); */ stringify: function (wordarray) { // shortcuts var words = wordarray.words; var sigbytes = wordarray.sigbytes; // convert var hexchars = []; for (var i = 0; i < sigbytes; i++) { var bite = (words[i >>> 2] >>> (24 - (i % 4) * 8)) & 0xff; hexchars.push((bite >>> 4).tostring(16)); hexchars.push((bite & 0x0f).tostring(16)); } return hexchars.join(''); }, /** * converts a hex string to a word array. * * @param {string} hexstr the hex string. * * @return {wordarray} the word array. * * @static * * @example * * var wordarray = cryptojs.enc.hex.parse(hexstring); */ parse: function (hexstr) { // shortcut var hexstrlength = hexstr.length; // convert var words = []; for (var i = 0; i < hexstrlength; i += 2) { words[i >>> 3] |= parseint(hexstr.substr(i, 2), 16) << (24 - (i % 8) * 4); } return new wordarray.init(words, hexstrlength / 2); } }; /** * latin1 encoding strategy. */ var latin1 = c_enc.latin1 = { /** * converts a word array to a latin1 string. * * @param {wordarray} wordarray the word array. * * @return {string} the latin1 string. * * @static * * @example * * var latin1string = cryptojs.enc.latin1.stringify(wordarray); */ stringify: function (wordarray) { // shortcuts var words = wordarray.words; var sigbytes = wordarray.sigbytes; // convert var latin1chars = []; for (var i = 0; i < sigbytes; i++) { var bite = (words[i >>> 2] >>> (24 - (i % 4) * 8)) & 0xff; latin1chars.push(string.fromcharcode(bite)); } return latin1chars.join(''); }, /** * converts a latin1 string to a word array. * * @param {string} latin1str the latin1 string. * * @return {wordarray} the word array. * * @static * * @example * * var wordarray = cryptojs.enc.latin1.parse(latin1string); */ parse: function (latin1str) { // shortcut var latin1strlength = latin1str.length; // convert var words = []; for (var i = 0; i < latin1strlength; i++) { words[i >>> 2] |= (latin1str.charcodeat(i) & 0xff) << (24 - (i % 4) * 8); } return new wordarray.init(words, latin1strlength); } }; /** * utf-8 encoding strategy. */ var utf8 = c_enc.utf8 = { /** * converts a word array to a utf-8 string. * * @param {wordarray} wordarray the word array. * * @return {string} the utf-8 string. * * @static * * @example * * var utf8string = cryptojs.enc.utf8.stringify(wordarray); */ stringify: function (wordarray) { try { return decodeuricomponent(escape(latin1.stringify(wordarray))); } catch (e) { throw new error('malformed utf-8 data'); } }, /** * converts a utf-8 string to a word array. * * @param {string} utf8str the utf-8 string. * * @return {wordarray} the word array. * * @static * * @example * * var wordarray = cryptojs.enc.utf8.parse(utf8string); */ parse: function (utf8str) { return latin1.parse(unescape(encodeuricomponent(utf8str))); } }; /** * abstract buffered block algorithm template. * * the property blocksize must be implemented in a concrete subtype. * * @property {number} _minbuffersize the number of blocks that should be kept unprocessed in the buffer. default: 0 */ var bufferedblockalgorithm = c_lib.bufferedblockalgorithm = base.extend({ /** * resets this block algorithm's data buffer to its initial state. * * @example * * bufferedblockalgorithm.reset(); */ reset: function () { // initial values this._data = new wordarray.init(); this._ndatabytes = 0; }, /** * adds new data to this block algorithm's buffer. * * @param {wordarray|string} data the data to append. strings are converted to a wordarray using utf-8. * * @example * * bufferedblockalgorithm._append('data'); * bufferedblockalgorithm._append(wordarray); */ _append: function (data) { // convert string to wordarray, else assume wordarray already if (typeof data == 'string') { data = utf8.parse(data); } // append this._data.concat(data); this._ndatabytes += data.sigbytes; }, /** * processes available data blocks. * * this method invokes _doprocessblock(offset), which must be implemented by a concrete subtype. * * @param {boolean} doflush whether all blocks and partial blocks should be processed. * * @return {wordarray} the processed data. * * @example * * var processeddata = bufferedblockalgorithm._process(); * var processeddata = bufferedblockalgorithm._process(!!'flush'); */ _process: function (doflush) { // shortcuts var data = this._data; var datawords = data.words; var datasigbytes = data.sigbytes; var blocksize = this.blocksize; var blocksizebytes = blocksize * 4; // count blocks ready var nblocksready = datasigbytes / blocksizebytes; if (doflush) { // round up to include partial blocks nblocksready = math.ceil(nblocksready); } else { // round down to include only full blocks, // less the number of blocks that must remain in the buffer nblocksready = math.max((nblocksready | 0) - this._minbuffersize, 0); } // count words ready var nwordsready = nblocksready * blocksize; // count bytes ready var nbytesready = math.min(nwordsready * 4, datasigbytes); // process blocks if (nwordsready) { for (var offset = 0; offset < nwordsready; offset += blocksize) { // perform concrete-algorithm logic this._doprocessblock(datawords, offset); } // remove processed words var processedwords = datawords.splice(0, nwordsready); data.sigbytes -= nbytesready; } // return processed words return new wordarray.init(processedwords, nbytesready); }, /** * creates a copy of this object. * * @return {object} the clone. * * @example * * var clone = bufferedblockalgorithm.clone(); */ clone: function () { var clone = base.clone.call(this); clone._data = this._data.clone(); return clone; }, _minbuffersize: 0 }); /** * abstract hasher template. * * @property {number} blocksize the number of 32-bit words this hasher operates on. default: 16 (512 bits) */ var hasher = c_lib.hasher = bufferedblockalgorithm.extend({ /** * configuration options. */ cfg: base.extend(), /** * initializes a newly created hasher. * * @param {object} cfg (optional) the configuration options to use for this hash computation. * * @example * * var hasher = cryptojs.algo.sha256.create(); */ init: function (cfg) { // apply config defaults this.cfg = this.cfg.extend(cfg); // set initial values this.reset(); }, /** * resets this hasher to its initial state. * * @example * * hasher.reset(); */ reset: function () { // reset data buffer bufferedblockalgorithm.reset.call(this); // perform concrete-hasher logic this._doreset(); }, _doreset: function() { //this._hash = new wordarray.init([0x7380166f, 0x4914b2b9, 0x172442d7, 0xda8a0600, 0xa96f30bc, 0x163138aa, 0xe38dee4d, 0xb0fb0e4e]); //this._hash = new wordarray.init([1937774191, 1226093241, 388252375, -628488704, -1452330820, 372324522, -477237683, -1325724082]); }, /** * updates this hasher with a message. * * @param {wordarray|string} messageupdate the message to append. * * @return {hasher} this hasher. * * @example * * hasher.update('message'); * hasher.update(wordarray); */ update: function (messageupdate) { // append this._append(messageupdate); // update the hash this._process(); // chainable return this; }, /** * finalizes the hash computation. * note that the finalize operation is effectively a destructive, read-once operation. * * @param {wordarray|string} messageupdate (optional) a final message update. * * @return {wordarray} the hash. * * @example * * var hash = hasher.finalize(); * var hash = hasher.finalize('message'); * var hash = hasher.finalize(wordarray); */ finalize: function (messageupdate) { // final message update if (messageupdate) { this._append(messageupdate); } // perform concrete-hasher logic var hash = this._dofinalize(); return hash; }, blocksize: 512/32, /** * creates a shortcut function to a hasher's object interface. * * @param {hasher} hasher the hasher to create a helper for. * * @return {function} the shortcut function. * * @static * * @example * * var sha256 = cryptojs.lib.hasher._createhelper(cryptojs.algo.sha256); */ _createhelper: function (hasher) { return function (message, cfg) { return new hasher.init(cfg).finalize(message); }; }, /** * creates a shortcut function to the hmac's object interface. * * @param {hasher} hasher the hasher to use in this hmac helper. * * @return {function} the shortcut function. * * @static * * @example * * var hmacsha256 = cryptojs.lib.hasher._createhmachelper(cryptojs.algo.sha256); */ _createhmachelper: function (hasher) { return function (message, key) { return new c_algo.hmac.init(hasher, key).finalize(message); }; } }); /** * algorithm namespace. */ var c_algo = c.algo = {}; return c; }(math));