8e942dd462279e91d6e3da197c492bca1a257fb5
[aai/esr-gui.git] /
1 var bson = (function(){
2
3   var pkgmap        = {},
4       global        = {},
5       nativeRequire = typeof require != 'undefined' && require,
6       lib, ties, main, async;
7
8   function exports(){ return main(); };
9
10   exports.main     = exports;
11   exports.module   = module;
12   exports.packages = pkgmap;
13   exports.pkg      = pkg;
14   exports.require  = function require(uri){
15     return pkgmap.main.index.require(uri);
16   };
17
18
19   ties             = {};
20
21   aliases          = {};
22
23
24   return exports;
25
26 function join() {
27   return normalize(Array.prototype.join.call(arguments, "/"));
28 };
29
30 function normalize(path) {
31   var ret = [], parts = path.split('/'), cur, prev;
32
33   var i = 0, l = parts.length-1;
34   for (; i <= l; i++) {
35     cur = parts[i];
36
37     if (cur === "." && prev !== undefined) continue;
38
39     if (cur === ".." && ret.length && prev !== ".." && prev !== "." && prev !== undefined) {
40       ret.pop();
41       prev = ret.slice(-1)[0];
42     } else {
43       if (prev === ".") ret.pop();
44       ret.push(cur);
45       prev = cur;
46     }
47   }
48
49   return ret.join("/");
50 };
51
52 function dirname(path) {
53   return path && path.substr(0, path.lastIndexOf("/")) || ".";
54 };
55
56 function findModule(workingModule, uri){
57   var moduleId      = join(dirname(workingModule.id), /\.\/$/.test(uri) ? (uri + 'index') : uri ).replace(/\.js$/, ''),
58       moduleIndexId = join(moduleId, 'index'),
59       pkg           = workingModule.pkg,
60       module;
61
62   var i = pkg.modules.length,
63       id;
64
65   while(i-->0){
66     id = pkg.modules[i].id;
67
68     if(id==moduleId || id == moduleIndexId){
69       module = pkg.modules[i];
70       break;
71     }
72   }
73
74   return module;
75 }
76
77 function newRequire(callingModule){
78   function require(uri){
79     var module, pkg;
80
81     if(/^\./.test(uri)){
82       module = findModule(callingModule, uri);
83     } else if ( ties && ties.hasOwnProperty( uri ) ) {
84       return ties[uri];
85     } else if ( aliases && aliases.hasOwnProperty( uri ) ) {
86       return require(aliases[uri]);
87     } else {
88       pkg = pkgmap[uri];
89
90       if(!pkg && nativeRequire){
91         try {
92           pkg = nativeRequire(uri);
93         } catch (nativeRequireError) {}
94
95         if(pkg) return pkg;
96       }
97
98       if(!pkg){
99         throw new Error('Cannot find module "'+uri+'" @[module: '+callingModule.id+' package: '+callingModule.pkg.name+']');
100       }
101
102       module = pkg.index;
103     }
104
105     if(!module){
106       throw new Error('Cannot find module "'+uri+'" @[module: '+callingModule.id+' package: '+callingModule.pkg.name+']');
107     }
108
109     module.parent = callingModule;
110     return module.call();
111   };
112
113
114   return require;
115 }
116
117
118 function module(parent, id, wrapper){
119   var mod    = { pkg: parent, id: id, wrapper: wrapper },
120       cached = false;
121
122   mod.exports = {};
123   mod.require = newRequire(mod);
124
125   mod.call = function(){
126     if(cached) {
127       return mod.exports;
128     }
129
130     cached = true;
131
132     global.require = mod.require;
133
134     mod.wrapper(mod, mod.exports, global, global.require);
135     return mod.exports;
136   };
137
138   if(parent.mainModuleId == mod.id){
139     parent.index = mod;
140     parent.parents.length === 0 && ( main = mod.call );
141   }
142
143   parent.modules.push(mod);
144 }
145
146 function pkg(/* [ parentId ...], wrapper */){
147   var wrapper = arguments[ arguments.length - 1 ],
148       parents = Array.prototype.slice.call(arguments, 0, arguments.length - 1),
149       ctx     = wrapper(parents);
150
151
152   pkgmap[ctx.name] = ctx;
153
154   arguments.length == 1 && ( pkgmap.main = ctx );
155
156   return function(modules){
157     var id;
158     for(id in modules){
159       module(ctx, id, modules[id]);
160     }
161   };
162 }
163
164
165 }(this));
166
167 bson.pkg(function(parents){
168
169   return {
170     'name'         : 'bson',
171     'mainModuleId' : 'bson',
172     'modules'      : [],
173     'parents'      : parents
174   };
175
176 })({ 'binary': function(module, exports, global, require, undefined){
177   /**
178  * Module dependencies.
179  */
180 if(typeof window === 'undefined') { 
181   var Buffer = require('buffer').Buffer; // TODO just use global Buffer
182 }
183
184 // Binary default subtype
185 var BSON_BINARY_SUBTYPE_DEFAULT = 0;
186
187 /**
188  * @ignore
189  * @api private
190  */
191 var writeStringToArray = function(data) {
192   // Create a buffer
193   var buffer = typeof Uint8Array != 'undefined' ? new Uint8Array(new ArrayBuffer(data.length)) : new Array(data.length);
194   // Write the content to the buffer
195   for(var i = 0; i < data.length; i++) {
196     buffer[i] = data.charCodeAt(i);
197   }  
198   // Write the string to the buffer
199   return buffer;
200 }
201
202 /**
203  * Convert Array ot Uint8Array to Binary String
204  *
205  * @ignore
206  * @api private
207  */
208 var convertArraytoUtf8BinaryString = function(byteArray, startIndex, endIndex) {
209   var result = "";
210   for(var i = startIndex; i < endIndex; i++) {
211    result = result + String.fromCharCode(byteArray[i]);
212   }
213   return result;  
214 };
215
216 /**
217  * A class representation of the BSON Binary type.
218  * 
219  * Sub types
220  *  - **BSON.BSON_BINARY_SUBTYPE_DEFAULT**, default BSON type.
221  *  - **BSON.BSON_BINARY_SUBTYPE_FUNCTION**, BSON function type.
222  *  - **BSON.BSON_BINARY_SUBTYPE_BYTE_ARRAY**, BSON byte array type.
223  *  - **BSON.BSON_BINARY_SUBTYPE_UUID**, BSON uuid type.
224  *  - **BSON.BSON_BINARY_SUBTYPE_MD5**, BSON md5 type.
225  *  - **BSON.BSON_BINARY_SUBTYPE_USER_DEFINED**, BSON user defined type.
226  *
227  * @class Represents the Binary BSON type.
228  * @param {Buffer} buffer a buffer object containing the binary data.
229  * @param {Number} [subType] the option binary type.
230  * @return {Grid}
231  */
232 function Binary(buffer, subType) {
233   if(!(this instanceof Binary)) return new Binary(buffer, subType);
234   
235   this._bsontype = 'Binary';
236
237   if(buffer instanceof Number) {
238     this.sub_type = buffer;
239     this.position = 0;
240   } else {    
241     this.sub_type = subType == null ? BSON_BINARY_SUBTYPE_DEFAULT : subType;
242     this.position = 0;
243   }
244
245   if(buffer != null && !(buffer instanceof Number)) {
246     // Only accept Buffer, Uint8Array or Arrays
247     if(typeof buffer == 'string') {
248       // Different ways of writing the length of the string for the different types
249       if(typeof Buffer != 'undefined') {
250         this.buffer = new Buffer(buffer);
251       } else if(typeof Uint8Array != 'undefined' || (Object.prototype.toString.call(buffer) == '[object Array]')) {
252         this.buffer = writeStringToArray(buffer);
253       } else {
254         throw new Error("only String, Buffer, Uint8Array or Array accepted");
255       }
256     } else {
257       this.buffer = buffer;      
258     }
259     this.position = buffer.length;
260   } else {
261     if(typeof Buffer != 'undefined') {
262       this.buffer =  new Buffer(Binary.BUFFER_SIZE);      
263     } else if(typeof Uint8Array != 'undefined'){
264       this.buffer = new Uint8Array(new ArrayBuffer(Binary.BUFFER_SIZE));
265     } else {
266       this.buffer = new Array(Binary.BUFFER_SIZE);
267     }
268     // Set position to start of buffer
269     this.position = 0;
270   }
271 };
272
273 /**
274  * Updates this binary with byte_value.
275  *
276  * @param {Character} byte_value a single byte we wish to write.
277  * @api public
278  */
279 Binary.prototype.put = function put(byte_value) {
280   // If it's a string and a has more than one character throw an error
281   if(byte_value['length'] != null && typeof byte_value != 'number' && byte_value.length != 1) throw new Error("only accepts single character String, Uint8Array or Array");
282   if(typeof byte_value != 'number' && byte_value < 0 || byte_value > 255) throw new Error("only accepts number in a valid unsigned byte range 0-255");
283   
284   // Decode the byte value once
285   var decoded_byte = null;
286   if(typeof byte_value == 'string') {
287     decoded_byte = byte_value.charCodeAt(0);      
288   } else if(byte_value['length'] != null) {
289     decoded_byte = byte_value[0];
290   } else {
291     decoded_byte = byte_value;
292   }
293   
294   if(this.buffer.length > this.position) {
295     this.buffer[this.position++] = decoded_byte;
296   } else {
297     if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {    
298       // Create additional overflow buffer
299       var buffer = new Buffer(Binary.BUFFER_SIZE + this.buffer.length);
300       // Combine the two buffers together
301       this.buffer.copy(buffer, 0, 0, this.buffer.length);
302       this.buffer = buffer;
303       this.buffer[this.position++] = decoded_byte;
304     } else {
305       var buffer = null;
306       // Create a new buffer (typed or normal array)
307       if(Object.prototype.toString.call(this.buffer) == '[object Uint8Array]') {
308         buffer = new Uint8Array(new ArrayBuffer(Binary.BUFFER_SIZE + this.buffer.length));
309       } else {
310         buffer = new Array(Binary.BUFFER_SIZE + this.buffer.length);
311       }      
312       
313       // We need to copy all the content to the new array
314       for(var i = 0; i < this.buffer.length; i++) {
315         buffer[i] = this.buffer[i];
316       }
317       
318       // Reassign the buffer
319       this.buffer = buffer;
320       // Write the byte
321       this.buffer[this.position++] = decoded_byte;
322     }
323   }
324 };
325
326 /**
327  * Writes a buffer or string to the binary.
328  *
329  * @param {Buffer|String} string a string or buffer to be written to the Binary BSON object.
330  * @param {Number} offset specify the binary of where to write the content.
331  * @api public
332  */
333 Binary.prototype.write = function write(string, offset) {
334   offset = typeof offset == 'number' ? offset : this.position;
335
336   // If the buffer is to small let's extend the buffer
337   if(this.buffer.length < offset + string.length) {
338     var buffer = null;
339     // If we are in node.js
340     if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {      
341       buffer = new Buffer(this.buffer.length + string.length);
342       this.buffer.copy(buffer, 0, 0, this.buffer.length);      
343     } else if(Object.prototype.toString.call(this.buffer) == '[object Uint8Array]') {
344       // Create a new buffer
345       buffer = new Uint8Array(new ArrayBuffer(this.buffer.length + string.length))
346       // Copy the content
347       for(var i = 0; i < this.position; i++) {
348         buffer[i] = this.buffer[i];
349       }
350     }
351     
352     // Assign the new buffer
353     this.buffer = buffer;
354   }
355
356   if(typeof Buffer != 'undefined' && Buffer.isBuffer(string) && Buffer.isBuffer(this.buffer)) {
357     string.copy(this.buffer, offset, 0, string.length);
358     this.position = (offset + string.length) > this.position ? (offset + string.length) : this.position;
359     // offset = string.length
360   } else if(typeof Buffer != 'undefined' && typeof string == 'string' && Buffer.isBuffer(this.buffer)) {
361     this.buffer.write(string, 'binary', offset);
362     this.position = (offset + string.length) > this.position ? (offset + string.length) : this.position;
363     // offset = string.length;
364   } else if(Object.prototype.toString.call(string) == '[object Uint8Array]' 
365     || Object.prototype.toString.call(string) == '[object Array]' && typeof string != 'string') {      
366     for(var i = 0; i < string.length; i++) {
367       this.buffer[offset++] = string[i];
368     }    
369
370     this.position = offset > this.position ? offset : this.position;
371   } else if(typeof string == 'string') {
372     for(var i = 0; i < string.length; i++) {
373       this.buffer[offset++] = string.charCodeAt(i);
374     }
375
376     this.position = offset > this.position ? offset : this.position;
377   }
378 };
379
380 /**
381  * Reads **length** bytes starting at **position**.
382  *
383  * @param {Number} position read from the given position in the Binary.
384  * @param {Number} length the number of bytes to read.
385  * @return {Buffer}
386  * @api public
387  */
388 Binary.prototype.read = function read(position, length) {
389   length = length && length > 0
390     ? length
391     : this.position;
392   
393   // Let's return the data based on the type we have
394   if(this.buffer['slice']) {
395     return this.buffer.slice(position, position + length);
396   } else {
397     // Create a buffer to keep the result
398     var buffer = typeof Uint8Array != 'undefined' ? new Uint8Array(new ArrayBuffer(length)) : new Array(length);
399     for(var i = 0; i < length; i++) {
400       buffer[i] = this.buffer[position++];
401     }
402   }
403   // Return the buffer
404   return buffer;
405 };
406
407 /**
408  * Returns the value of this binary as a string.
409  *
410  * @return {String}
411  * @api public
412  */
413 Binary.prototype.value = function value(asRaw) {
414   asRaw = asRaw == null ? false : asRaw;  
415   
416   // If it's a node.js buffer object
417   if(typeof Buffer != 'undefined' && Buffer.isBuffer(this.buffer)) {
418     return asRaw ? this.buffer.slice(0, this.position) : this.buffer.toString('binary', 0, this.position);
419   } else {
420     if(asRaw) {
421       // we support the slice command use it
422       if(this.buffer['slice'] != null) {
423         return this.buffer.slice(0, this.position);
424       } else {
425         // Create a new buffer to copy content to
426         var newBuffer = Object.prototype.toString.call(this.buffer) == '[object Uint8Array]' ? new Uint8Array(new ArrayBuffer(this.position)) : new Array(this.position);
427         // Copy content
428         for(var i = 0; i < this.position; i++) {
429           newBuffer[i] = this.buffer[i];
430         }
431         // Return the buffer
432         return newBuffer;
433       }
434     } else {
435       return convertArraytoUtf8BinaryString(this.buffer, 0, this.position);
436     }
437   }
438 };
439
440 /**
441  * Length.
442  *
443  * @return {Number} the length of the binary.
444  * @api public
445  */
446 Binary.prototype.length = function length() {
447   return this.position;
448 };
449
450 /**
451  * @ignore
452  * @api private
453  */
454 Binary.prototype.toJSON = function() {
455   return this.buffer != null ? this.buffer.toString('base64') : '';
456 }
457
458 /**
459  * @ignore
460  * @api private
461  */
462 Binary.prototype.toString = function(format) {
463   return this.buffer != null ? this.buffer.slice(0, this.position).toString(format) : '';
464 }
465
466 Binary.BUFFER_SIZE = 256;
467
468 /**
469  * Default BSON type
470  *  
471  * @classconstant SUBTYPE_DEFAULT
472  **/
473 Binary.SUBTYPE_DEFAULT = 0;
474 /**
475  * Function BSON type
476  *  
477  * @classconstant SUBTYPE_DEFAULT
478  **/
479 Binary.SUBTYPE_FUNCTION = 1;
480 /**
481  * Byte Array BSON type
482  *  
483  * @classconstant SUBTYPE_DEFAULT
484  **/
485 Binary.SUBTYPE_BYTE_ARRAY = 2;
486 /**
487  * OLD UUID BSON type
488  *  
489  * @classconstant SUBTYPE_DEFAULT
490  **/
491 Binary.SUBTYPE_UUID_OLD = 3;
492 /**
493  * UUID BSON type
494  *  
495  * @classconstant SUBTYPE_DEFAULT
496  **/
497 Binary.SUBTYPE_UUID = 4;
498 /**
499  * MD5 BSON type
500  *  
501  * @classconstant SUBTYPE_DEFAULT
502  **/
503 Binary.SUBTYPE_MD5 = 5;
504 /**
505  * User BSON type
506  *  
507  * @classconstant SUBTYPE_DEFAULT
508  **/
509 Binary.SUBTYPE_USER_DEFINED = 128;
510
511 /**
512  * Expose.
513  */
514 exports.Binary = Binary;
515
516
517 }, 
518
519
520
521 'binary_parser': function(module, exports, global, require, undefined){
522   /**
523  * Binary Parser.
524  * Jonas Raoni Soares Silva
525  * http://jsfromhell.com/classes/binary-parser [v1.0]
526  */
527 var chr = String.fromCharCode;
528
529 var maxBits = [];
530 for (var i = 0; i < 64; i++) {
531         maxBits[i] = Math.pow(2, i);
532 }
533
534 function BinaryParser (bigEndian, allowExceptions) {
535   if(!(this instanceof BinaryParser)) return new BinaryParser(bigEndian, allowExceptions);
536   
537         this.bigEndian = bigEndian;
538         this.allowExceptions = allowExceptions;
539 };
540
541 BinaryParser.warn = function warn (msg) {
542         if (this.allowExceptions) {
543                 throw new Error(msg);
544   }
545
546         return 1;
547 };
548
549 BinaryParser.decodeFloat = function decodeFloat (data, precisionBits, exponentBits) {
550         var b = new this.Buffer(this.bigEndian, data);
551
552         b.checkBuffer(precisionBits + exponentBits + 1);
553
554         var bias = maxBits[exponentBits - 1] - 1
555     , signal = b.readBits(precisionBits + exponentBits, 1)
556     , exponent = b.readBits(precisionBits, exponentBits)
557     , significand = 0
558     , divisor = 2
559     , curByte = b.buffer.length + (-precisionBits >> 3) - 1;
560
561         do {
562                 for (var byteValue = b.buffer[ ++curByte ], startBit = precisionBits % 8 || 8, mask = 1 << startBit; mask >>= 1; ( byteValue & mask ) && ( significand += 1 / divisor ), divisor *= 2 );
563         } while (precisionBits -= startBit);
564
565         return exponent == ( bias << 1 ) + 1 ? significand ? NaN : signal ? -Infinity : +Infinity : ( 1 + signal * -2 ) * ( exponent || significand ? !exponent ? Math.pow( 2, -bias + 1 ) * significand : Math.pow( 2, exponent - bias ) * ( 1 + significand ) : 0 );
566 };
567
568 BinaryParser.decodeInt = function decodeInt (data, bits, signed, forceBigEndian) {
569   var b = new this.Buffer(this.bigEndian || forceBigEndian, data)
570       , x = b.readBits(0, bits)
571       , max = maxBits[bits]; //max = Math.pow( 2, bits );
572   
573   return signed && x >= max / 2
574       ? x - max
575       : x;
576 };
577
578 BinaryParser.encodeFloat = function encodeFloat (data, precisionBits, exponentBits) {
579         var bias = maxBits[exponentBits - 1] - 1
580     , minExp = -bias + 1
581     , maxExp = bias
582     , minUnnormExp = minExp - precisionBits
583     , n = parseFloat(data)
584     , status = isNaN(n) || n == -Infinity || n == +Infinity ? n : 0
585     ,   exp = 0
586     , len = 2 * bias + 1 + precisionBits + 3
587     , bin = new Array(len)
588     , signal = (n = status !== 0 ? 0 : n) < 0
589     , intPart = Math.floor(n = Math.abs(n))
590     , floatPart = n - intPart
591     , lastBit
592     , rounded
593     , result
594     , i
595     , j;
596
597         for (i = len; i; bin[--i] = 0);
598
599         for (i = bias + 2; intPart && i; bin[--i] = intPart % 2, intPart = Math.floor(intPart / 2));
600
601         for (i = bias + 1; floatPart > 0 && i; (bin[++i] = ((floatPart *= 2) >= 1) - 0 ) && --floatPart);
602
603         for (i = -1; ++i < len && !bin[i];);
604
605         if (bin[(lastBit = precisionBits - 1 + (i = (exp = bias + 1 - i) >= minExp && exp <= maxExp ? i + 1 : bias + 1 - (exp = minExp - 1))) + 1]) {
606                 if (!(rounded = bin[lastBit])) {
607                         for (j = lastBit + 2; !rounded && j < len; rounded = bin[j++]);
608                 }
609
610                 for (j = lastBit + 1; rounded && --j >= 0; (bin[j] = !bin[j] - 0) && (rounded = 0));
611         }
612
613         for (i = i - 2 < 0 ? -1 : i - 3; ++i < len && !bin[i];);
614
615         if ((exp = bias + 1 - i) >= minExp && exp <= maxExp) {
616                 ++i;
617   } else if (exp < minExp) {
618                 exp != bias + 1 - len && exp < minUnnormExp && this.warn("encodeFloat::float underflow");
619                 i = bias + 1 - (exp = minExp - 1);
620         }
621
622         if (intPart || status !== 0) {
623                 this.warn(intPart ? "encodeFloat::float overflow" : "encodeFloat::" + status);
624                 exp = maxExp + 1;
625                 i = bias + 2;
626
627                 if (status == -Infinity) {
628                         signal = 1;
629     } else if (isNaN(status)) {
630                         bin[i] = 1;
631     }
632         }
633
634         for (n = Math.abs(exp + bias), j = exponentBits + 1, result = ""; --j; result = (n % 2) + result, n = n >>= 1);
635
636         for (n = 0, j = 0, i = (result = (signal ? "1" : "0") + result + bin.slice(i, i + precisionBits).join("")).length, r = []; i; j = (j + 1) % 8) {
637                 n += (1 << j) * result.charAt(--i);
638                 if (j == 7) {
639                         r[r.length] = String.fromCharCode(n);
640                         n = 0;
641                 }
642         }
643
644         r[r.length] = n
645     ? String.fromCharCode(n)
646     : "";
647
648         return (this.bigEndian ? r.reverse() : r).join("");
649 };
650
651 BinaryParser.encodeInt = function encodeInt (data, bits, signed, forceBigEndian) {
652         var max = maxBits[bits];
653
654   if (data >= max || data < -(max / 2)) {
655     this.warn("encodeInt::overflow");
656     data = 0;
657   }
658
659         if (data < 0) {
660     data += max;
661   }
662
663         for (var r = []; data; r[r.length] = String.fromCharCode(data % 256), data = Math.floor(data / 256));
664
665         for (bits = -(-bits >> 3) - r.length; bits--; r[r.length] = "\0");
666
667   return ((this.bigEndian || forceBigEndian) ? r.reverse() : r).join("");
668 };
669
670 BinaryParser.toSmall    = function( data ){ return this.decodeInt( data,  8, true  ); };
671 BinaryParser.fromSmall  = function( data ){ return this.encodeInt( data,  8, true  ); };
672 BinaryParser.toByte     = function( data ){ return this.decodeInt( data,  8, false ); };
673 BinaryParser.fromByte   = function( data ){ return this.encodeInt( data,  8, false ); };
674 BinaryParser.toShort    = function( data ){ return this.decodeInt( data, 16, true  ); };
675 BinaryParser.fromShort  = function( data ){ return this.encodeInt( data, 16, true  ); };
676 BinaryParser.toWord     = function( data ){ return this.decodeInt( data, 16, false ); };
677 BinaryParser.fromWord   = function( data ){ return this.encodeInt( data, 16, false ); };
678 BinaryParser.toInt      = function( data ){ return this.decodeInt( data, 32, true  ); };
679 BinaryParser.fromInt    = function( data ){ return this.encodeInt( data, 32, true  ); };
680 BinaryParser.toLong     = function( data ){ return this.decodeInt( data, 64, true  ); };
681 BinaryParser.fromLong   = function( data ){ return this.encodeInt( data, 64, true  ); };
682 BinaryParser.toDWord    = function( data ){ return this.decodeInt( data, 32, false ); };
683 BinaryParser.fromDWord  = function( data ){ return this.encodeInt( data, 32, false ); };
684 BinaryParser.toQWord    = function( data ){ return this.decodeInt( data, 64, true ); };
685 BinaryParser.fromQWord  = function( data ){ return this.encodeInt( data, 64, true ); };
686 BinaryParser.toFloat    = function( data ){ return this.decodeFloat( data, 23, 8   ); };
687 BinaryParser.fromFloat  = function( data ){ return this.encodeFloat( data, 23, 8   ); };
688 BinaryParser.toDouble   = function( data ){ return this.decodeFloat( data, 52, 11  ); };
689 BinaryParser.fromDouble = function( data ){ return this.encodeFloat( data, 52, 11  ); };
690
691 // Factor out the encode so it can be shared by add_header and push_int32
692 BinaryParser.encode_int32 = function encode_int32 (number, asArray) {
693   var a, b, c, d, unsigned;
694   unsigned = (number < 0) ? (number + 0x100000000) : number;
695   a = Math.floor(unsigned / 0xffffff);
696   unsigned &= 0xffffff;
697   b = Math.floor(unsigned / 0xffff);
698   unsigned &= 0xffff;
699   c = Math.floor(unsigned / 0xff);
700   unsigned &= 0xff;
701   d = Math.floor(unsigned);
702   return asArray ? [chr(a), chr(b), chr(c), chr(d)] : chr(a) + chr(b) + chr(c) + chr(d);
703 };
704
705 BinaryParser.encode_int64 = function encode_int64 (number) {
706   var a, b, c, d, e, f, g, h, unsigned;
707   unsigned = (number < 0) ? (number + 0x10000000000000000) : number;
708   a = Math.floor(unsigned / 0xffffffffffffff);
709   unsigned &= 0xffffffffffffff;
710   b = Math.floor(unsigned / 0xffffffffffff);
711   unsigned &= 0xffffffffffff;
712   c = Math.floor(unsigned / 0xffffffffff);
713   unsigned &= 0xffffffffff;
714   d = Math.floor(unsigned / 0xffffffff);
715   unsigned &= 0xffffffff;
716   e = Math.floor(unsigned / 0xffffff);
717   unsigned &= 0xffffff;
718   f = Math.floor(unsigned / 0xffff);
719   unsigned &= 0xffff;
720   g = Math.floor(unsigned / 0xff);
721   unsigned &= 0xff;
722   h = Math.floor(unsigned);
723   return chr(a) + chr(b) + chr(c) + chr(d) + chr(e) + chr(f) + chr(g) + chr(h);
724 };
725
726 /**
727  * UTF8 methods
728  */
729
730 // Take a raw binary string and return a utf8 string
731 BinaryParser.decode_utf8 = function decode_utf8 (binaryStr) {
732   var len = binaryStr.length
733     , decoded = ''
734     , i = 0
735     , c = 0
736     , c1 = 0
737     , c2 = 0
738     , c3;
739
740   while (i < len) {
741     c = binaryStr.charCodeAt(i);
742     if (c < 128) {
743       decoded += String.fromCharCode(c);
744       i++;
745     } else if ((c > 191) && (c < 224)) {
746             c2 = binaryStr.charCodeAt(i+1);
747       decoded += String.fromCharCode(((c & 31) << 6) | (c2 & 63));
748       i += 2;
749     } else {
750             c2 = binaryStr.charCodeAt(i+1);
751             c3 = binaryStr.charCodeAt(i+2);
752       decoded += String.fromCharCode(((c & 15) << 12) | ((c2 & 63) << 6) | (c3 & 63));
753       i += 3;
754     }
755   }
756
757   return decoded;
758 };
759
760 // Encode a cstring
761 BinaryParser.encode_cstring = function encode_cstring (s) {
762   return unescape(encodeURIComponent(s)) + BinaryParser.fromByte(0);
763 };
764
765 // Take a utf8 string and return a binary string
766 BinaryParser.encode_utf8 = function encode_utf8 (s) {
767   var a = ""
768     , c;
769
770   for (var n = 0, len = s.length; n < len; n++) {
771     c = s.charCodeAt(n);
772
773     if (c < 128) {
774             a += String.fromCharCode(c);
775     } else if ((c > 127) && (c < 2048)) {
776             a += String.fromCharCode((c>>6) | 192) ;
777             a += String.fromCharCode((c&63) | 128);
778     } else {
779       a += String.fromCharCode((c>>12) | 224);
780       a += String.fromCharCode(((c>>6) & 63) | 128);
781       a += String.fromCharCode((c&63) | 128);
782     }
783   }
784
785   return a;
786 };
787
788 BinaryParser.hprint = function hprint (s) {
789   var number;
790
791   for (var i = 0, len = s.length; i < len; i++) {
792     if (s.charCodeAt(i) < 32) {
793       number = s.charCodeAt(i) <= 15
794         ? "0" + s.charCodeAt(i).toString(16)
795         : s.charCodeAt(i).toString(16);        
796       process.stdout.write(number + " ")
797     } else {
798       number = s.charCodeAt(i) <= 15
799         ? "0" + s.charCodeAt(i).toString(16)
800         : s.charCodeAt(i).toString(16);
801         process.stdout.write(number + " ")
802     }
803   }
804   
805   process.stdout.write("\n\n");
806 };
807
808 BinaryParser.ilprint = function hprint (s) {
809   var number;
810
811   for (var i = 0, len = s.length; i < len; i++) {
812     if (s.charCodeAt(i) < 32) {
813       number = s.charCodeAt(i) <= 15
814         ? "0" + s.charCodeAt(i).toString(10)
815         : s.charCodeAt(i).toString(10);
816
817       require('util').debug(number+' : ');
818     } else {
819       number = s.charCodeAt(i) <= 15
820         ? "0" + s.charCodeAt(i).toString(10)
821         : s.charCodeAt(i).toString(10);
822       require('util').debug(number+' : '+ s.charAt(i));
823     }
824   }
825 };
826
827 BinaryParser.hlprint = function hprint (s) {
828   var number;
829
830   for (var i = 0, len = s.length; i < len; i++) {
831     if (s.charCodeAt(i) < 32) {
832       number = s.charCodeAt(i) <= 15
833         ? "0" + s.charCodeAt(i).toString(16)
834         : s.charCodeAt(i).toString(16);
835       require('util').debug(number+' : ');
836     } else {
837       number = s.charCodeAt(i) <= 15
838         ? "0" + s.charCodeAt(i).toString(16)
839         : s.charCodeAt(i).toString(16);
840       require('util').debug(number+' : '+ s.charAt(i));
841     }
842   }
843 };
844
845 /**
846  * BinaryParser buffer constructor.
847  */
848 function BinaryParserBuffer (bigEndian, buffer) {
849   this.bigEndian = bigEndian || 0;
850   this.buffer = [];
851   this.setBuffer(buffer);
852 };
853
854 BinaryParserBuffer.prototype.setBuffer = function setBuffer (data) {
855   var l, i, b;
856
857         if (data) {
858     i = l = data.length;
859     b = this.buffer = new Array(l);
860                 for (; i; b[l - i] = data.charCodeAt(--i));
861                 this.bigEndian && b.reverse();
862         }
863 };
864
865 BinaryParserBuffer.prototype.hasNeededBits = function hasNeededBits (neededBits) {
866         return this.buffer.length >= -(-neededBits >> 3);
867 };
868
869 BinaryParserBuffer.prototype.checkBuffer = function checkBuffer (neededBits) {
870         if (!this.hasNeededBits(neededBits)) {
871                 throw new Error("checkBuffer::missing bytes");
872   }
873 };
874
875 BinaryParserBuffer.prototype.readBits = function readBits (start, length) {
876         //shl fix: Henri Torgemane ~1996 (compressed by Jonas Raoni)
877
878         function shl (a, b) {
879                 for (; b--; a = ((a %= 0x7fffffff + 1) & 0x40000000) == 0x40000000 ? a * 2 : (a - 0x40000000) * 2 + 0x7fffffff + 1);
880                 return a;
881         }
882
883         if (start < 0 || length <= 0) {
884                 return 0;
885   }
886
887         this.checkBuffer(start + length);
888
889   var offsetLeft
890     , offsetRight = start % 8
891     , curByte = this.buffer.length - ( start >> 3 ) - 1
892     , lastByte = this.buffer.length + ( -( start + length ) >> 3 )
893     , diff = curByte - lastByte
894     , sum = ((this.buffer[ curByte ] >> offsetRight) & ((1 << (diff ? 8 - offsetRight : length)) - 1)) + (diff && (offsetLeft = (start + length) % 8) ? (this.buffer[lastByte++] & ((1 << offsetLeft) - 1)) << (diff-- << 3) - offsetRight : 0);
895
896         for(; diff; sum += shl(this.buffer[lastByte++], (diff-- << 3) - offsetRight));
897
898         return sum;
899 };
900
901 /**
902  * Expose.
903  */
904 BinaryParser.Buffer = BinaryParserBuffer;
905
906 exports.BinaryParser = BinaryParser;
907
908 }, 
909
910
911
912 'bson': function(module, exports, global, require, undefined){
913   var Long = require('./long').Long
914   , Double = require('./double').Double
915   , Timestamp = require('./timestamp').Timestamp
916   , ObjectID = require('./objectid').ObjectID
917   , Symbol = require('./symbol').Symbol
918   , Code = require('./code').Code
919   , MinKey = require('./min_key').MinKey
920   , MaxKey = require('./max_key').MaxKey
921   , DBRef = require('./db_ref').DBRef
922   , Binary = require('./binary').Binary
923   , BinaryParser = require('./binary_parser').BinaryParser
924   , writeIEEE754 = require('./float_parser').writeIEEE754
925   , readIEEE754 = require('./float_parser').readIEEE754
926
927 // To ensure that 0.4 of node works correctly
928 var isDate = function isDate(d) {
929   return typeof d === 'object' && Object.prototype.toString.call(d) === '[object Date]';
930 }
931
932 /**
933  * Create a new BSON instance
934  *
935  * @class Represents the BSON Parser
936  * @return {BSON} instance of BSON Parser.
937  */
938 function BSON () {};
939
940 /**
941  * @ignore
942  * @api private
943  */
944 // BSON MAX VALUES
945 BSON.BSON_INT32_MAX = 0x7FFFFFFF;
946 BSON.BSON_INT32_MIN = -0x80000000;
947
948 BSON.BSON_INT64_MAX = Math.pow(2, 63) - 1;
949 BSON.BSON_INT64_MIN = -Math.pow(2, 63);
950
951 // JS MAX PRECISE VALUES
952 BSON.JS_INT_MAX = 0x20000000000000;  // Any integer up to 2^53 can be precisely represented by a double.
953 BSON.JS_INT_MIN = -0x20000000000000;  // Any integer down to -2^53 can be precisely represented by a double.
954
955 // Internal long versions
956 var JS_INT_MAX_LONG = Long.fromNumber(0x20000000000000);  // Any integer up to 2^53 can be precisely represented by a double.
957 var JS_INT_MIN_LONG = Long.fromNumber(-0x20000000000000);  // Any integer down to -2^53 can be precisely represented by a double.
958
959 /**
960  * Number BSON Type
961  *
962  * @classconstant BSON_DATA_NUMBER
963  **/
964 BSON.BSON_DATA_NUMBER = 1;
965 /**
966  * String BSON Type
967  *
968  * @classconstant BSON_DATA_STRING
969  **/
970 BSON.BSON_DATA_STRING = 2;
971 /**
972  * Object BSON Type
973  *
974  * @classconstant BSON_DATA_OBJECT
975  **/
976 BSON.BSON_DATA_OBJECT = 3;
977 /**
978  * Array BSON Type
979  *
980  * @classconstant BSON_DATA_ARRAY
981  **/
982 BSON.BSON_DATA_ARRAY = 4;
983 /**
984  * Binary BSON Type
985  *
986  * @classconstant BSON_DATA_BINARY
987  **/
988 BSON.BSON_DATA_BINARY = 5;
989 /**
990  * ObjectID BSON Type
991  *
992  * @classconstant BSON_DATA_OID
993  **/
994 BSON.BSON_DATA_OID = 7;
995 /**
996  * Boolean BSON Type
997  *
998  * @classconstant BSON_DATA_BOOLEAN
999  **/
1000 BSON.BSON_DATA_BOOLEAN = 8;
1001 /**
1002  * Date BSON Type
1003  *
1004  * @classconstant BSON_DATA_DATE
1005  **/
1006 BSON.BSON_DATA_DATE = 9;
1007 /**
1008  * null BSON Type
1009  *
1010  * @classconstant BSON_DATA_NULL
1011  **/
1012 BSON.BSON_DATA_NULL = 10;
1013 /**
1014  * RegExp BSON Type
1015  *
1016  * @classconstant BSON_DATA_REGEXP
1017  **/
1018 BSON.BSON_DATA_REGEXP = 11;
1019 /**
1020  * Code BSON Type
1021  *
1022  * @classconstant BSON_DATA_CODE
1023  **/
1024 BSON.BSON_DATA_CODE = 13;
1025 /**
1026  * Symbol BSON Type
1027  *
1028  * @classconstant BSON_DATA_SYMBOL
1029  **/
1030 BSON.BSON_DATA_SYMBOL = 14;
1031 /**
1032  * Code with Scope BSON Type
1033  *
1034  * @classconstant BSON_DATA_CODE_W_SCOPE
1035  **/
1036 BSON.BSON_DATA_CODE_W_SCOPE = 15;
1037 /**
1038  * 32 bit Integer BSON Type
1039  *
1040  * @classconstant BSON_DATA_INT
1041  **/
1042 BSON.BSON_DATA_INT = 16;
1043 /**
1044  * Timestamp BSON Type
1045  *
1046  * @classconstant BSON_DATA_TIMESTAMP
1047  **/
1048 BSON.BSON_DATA_TIMESTAMP = 17;
1049 /**
1050  * Long BSON Type
1051  *
1052  * @classconstant BSON_DATA_LONG
1053  **/
1054 BSON.BSON_DATA_LONG = 18;
1055 /**
1056  * MinKey BSON Type
1057  *
1058  * @classconstant BSON_DATA_MIN_KEY
1059  **/
1060 BSON.BSON_DATA_MIN_KEY = 0xff;
1061 /**
1062  * MaxKey BSON Type
1063  *
1064  * @classconstant BSON_DATA_MAX_KEY
1065  **/
1066 BSON.BSON_DATA_MAX_KEY = 0x7f;
1067
1068 /**
1069  * Binary Default Type
1070  *
1071  * @classconstant BSON_BINARY_SUBTYPE_DEFAULT
1072  **/
1073 BSON.BSON_BINARY_SUBTYPE_DEFAULT = 0;
1074 /**
1075  * Binary Function Type
1076  *
1077  * @classconstant BSON_BINARY_SUBTYPE_FUNCTION
1078  **/
1079 BSON.BSON_BINARY_SUBTYPE_FUNCTION = 1;
1080 /**
1081  * Binary Byte Array Type
1082  *
1083  * @classconstant BSON_BINARY_SUBTYPE_BYTE_ARRAY
1084  **/
1085 BSON.BSON_BINARY_SUBTYPE_BYTE_ARRAY = 2;
1086 /**
1087  * Binary UUID Type
1088  *
1089  * @classconstant BSON_BINARY_SUBTYPE_UUID
1090  **/
1091 BSON.BSON_BINARY_SUBTYPE_UUID = 3;
1092 /**
1093  * Binary MD5 Type
1094  *
1095  * @classconstant BSON_BINARY_SUBTYPE_MD5
1096  **/
1097 BSON.BSON_BINARY_SUBTYPE_MD5 = 4;
1098 /**
1099  * Binary User Defined Type
1100  *
1101  * @classconstant BSON_BINARY_SUBTYPE_USER_DEFINED
1102  **/
1103 BSON.BSON_BINARY_SUBTYPE_USER_DEFINED = 128;
1104
1105 /**
1106  * Calculate the bson size for a passed in Javascript object.
1107  *
1108  * @param {Object} object the Javascript object to calculate the BSON byte size for.
1109  * @param {Boolean} [serializeFunctions] serialize all functions in the object **(default:false)**.
1110  * @return {Number} returns the number of bytes the BSON object will take up.
1111  * @api public
1112  */
1113 BSON.calculateObjectSize = function calculateObjectSize(object, serializeFunctions) {
1114   var totalLength = (4 + 1);
1115
1116   if(Array.isArray(object)) {
1117     for(var i = 0; i < object.length; i++) {
1118       totalLength += calculateElement(i.toString(), object[i], serializeFunctions)
1119     }
1120   } else {
1121                 // If we have toBSON defined, override the current object
1122                 if(object.toBSON) {
1123                         object = object.toBSON();
1124                 }
1125
1126                 // Calculate size
1127     for(var key in object) {
1128       totalLength += calculateElement(key, object[key], serializeFunctions)
1129     }
1130   }
1131
1132   return totalLength;
1133 }
1134
1135 /**
1136  * @ignore
1137  * @api private
1138  */
1139 function calculateElement(name, value, serializeFunctions) {
1140   var isBuffer = typeof Buffer !== 'undefined';
1141
1142   switch(typeof value) {
1143     case 'string':
1144       return 1 + (!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1 + 4 + (!isBuffer ? numberOfBytes(value) : Buffer.byteLength(value, 'utf8')) + 1;
1145     case 'number':
1146       if(Math.floor(value) === value && value >= BSON.JS_INT_MIN && value <= BSON.JS_INT_MAX) {
1147         if(value >= BSON.BSON_INT32_MIN && value <= BSON.BSON_INT32_MAX) { // 32 bit
1148           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (4 + 1);
1149         } else {
1150           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (8 + 1);
1151         }
1152       } else {  // 64 bit
1153         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (8 + 1);
1154       }
1155     case 'undefined':
1156       return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (1);
1157     case 'boolean':
1158       return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (1 + 1);
1159     case 'object':
1160       if(value == null || value instanceof MinKey || value instanceof MaxKey || value['_bsontype'] == 'MinKey' || value['_bsontype'] == 'MaxKey') {
1161         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (1);
1162       } else if(value instanceof ObjectID || value['_bsontype'] == 'ObjectID') {
1163         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (12 + 1);
1164       } else if(value instanceof Date || isDate(value)) {
1165         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (8 + 1);
1166       } else if(typeof Buffer !== 'undefined' && Buffer.isBuffer(value)) {
1167         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (1 + 4 + 1) + value.length;
1168       } else if(value instanceof Long || value instanceof Double || value instanceof Timestamp
1169           || value['_bsontype'] == 'Long' || value['_bsontype'] == 'Double' || value['_bsontype'] == 'Timestamp') {
1170         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (8 + 1);
1171       } else if(value instanceof Code || value['_bsontype'] == 'Code') {
1172         // Calculate size depending on the availability of a scope
1173         if(value.scope != null && Object.keys(value.scope).length > 0) {
1174           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + 4 + 4 + (!isBuffer ? numberOfBytes(value.code.toString()) : Buffer.byteLength(value.code.toString(), 'utf8')) + 1 + BSON.calculateObjectSize(value.scope, serializeFunctions);
1175         } else {
1176           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + 4 + (!isBuffer ? numberOfBytes(value.code.toString()) : Buffer.byteLength(value.code.toString(), 'utf8')) + 1;
1177         }
1178       } else if(value instanceof Binary || value['_bsontype'] == 'Binary') {
1179         // Check what kind of subtype we have
1180         if(value.sub_type == Binary.SUBTYPE_BYTE_ARRAY) {
1181           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (value.position + 1 + 4 + 1 + 4);
1182         } else {
1183           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + (value.position + 1 + 4 + 1);
1184         }
1185       } else if(value instanceof Symbol || value['_bsontype'] == 'Symbol') {
1186         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + ((!isBuffer ? numberOfBytes(value.value) : Buffer.byteLength(value.value, 'utf8')) + 4 + 1 + 1);
1187       } else if(value instanceof DBRef || value['_bsontype'] == 'DBRef') {
1188         // Set up correct object for serialization
1189         var ordered_values = {
1190             '$ref': value.namespace
1191           , '$id' : value.oid
1192         };
1193
1194         // Add db reference if it exists
1195         if(null != value.db) {
1196           ordered_values['$db'] = value.db;
1197         }
1198
1199         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + BSON.calculateObjectSize(ordered_values, serializeFunctions);
1200       } else if(value instanceof RegExp || Object.prototype.toString.call(value) === '[object RegExp]') {
1201           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + (!isBuffer ? numberOfBytes(value.source) : Buffer.byteLength(value.source, 'utf8')) + 1
1202             + (value.global ? 1 : 0) + (value.ignoreCase ? 1 : 0) + (value.multiline ? 1 : 0) + 1
1203       } else {
1204         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + BSON.calculateObjectSize(value, serializeFunctions) + 1;
1205       }
1206     case 'function':
1207       // WTF for 0.4.X where typeof /someregexp/ === 'function'
1208       if(value instanceof RegExp || Object.prototype.toString.call(value) === '[object RegExp]' || String.call(value) == '[object RegExp]') {
1209         return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + (!isBuffer ? numberOfBytes(value.source) : Buffer.byteLength(value.source, 'utf8')) + 1
1210           + (value.global ? 1 : 0) + (value.ignoreCase ? 1 : 0) + (value.multiline ? 1 : 0) + 1
1211       } else {
1212         if(serializeFunctions && value.scope != null && Object.keys(value.scope).length > 0) {
1213           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + 4 + 4 + (!isBuffer ? numberOfBytes(value.toString()) : Buffer.byteLength(value.toString(), 'utf8')) + 1 + BSON.calculateObjectSize(value.scope, serializeFunctions);
1214         } else if(serializeFunctions) {
1215           return (name != null ? ((!isBuffer ? numberOfBytes(name) : Buffer.byteLength(name, 'utf8')) + 1) : 0) + 1 + 4 + (!isBuffer ? numberOfBytes(value.toString()) : Buffer.byteLength(value.toString(), 'utf8')) + 1;
1216         }
1217       }
1218   }
1219
1220   return 0;
1221 }
1222
1223 /**
1224  * Serialize a Javascript object using a predefined Buffer and index into the buffer, useful when pre-allocating the space for serialization.
1225  *
1226  * @param {Object} object the Javascript object to serialize.
1227  * @param {Boolean} checkKeys the serializer will check if keys are valid.
1228  * @param {Buffer} buffer the Buffer you pre-allocated to store the serialized BSON object.
1229  * @param {Number} index the index in the buffer where we wish to start serializing into.
1230  * @param {Boolean} serializeFunctions serialize the javascript functions **(default:false)**.
1231  * @return {Number} returns the new write index in the Buffer.
1232  * @api public
1233  */
1234 BSON.serializeWithBufferAndIndex = function serializeWithBufferAndIndex(object, checkKeys, buffer, index, serializeFunctions) {
1235   // Default setting false
1236   serializeFunctions = serializeFunctions == null ? false : serializeFunctions;
1237   // Write end information (length of the object)
1238   var size = buffer.length;
1239   // Write the size of the object
1240   buffer[index++] = size & 0xff;
1241   buffer[index++] = (size >> 8) & 0xff;
1242   buffer[index++] = (size >> 16) & 0xff;
1243   buffer[index++] = (size >> 24) & 0xff;
1244   return serializeObject(object, checkKeys, buffer, index, serializeFunctions) - 1;
1245 }
1246
1247 /**
1248  * @ignore
1249  * @api private
1250  */
1251 var serializeObject = function(object, checkKeys, buffer, index, serializeFunctions) {
1252   // Process the object
1253   if(Array.isArray(object)) {
1254     for(var i = 0; i < object.length; i++) {
1255       index = packElement(i.toString(), object[i], checkKeys, buffer, index, serializeFunctions);
1256     }
1257   } else {
1258                 // If we have toBSON defined, override the current object
1259                 if(object.toBSON) {
1260                         object = object.toBSON();
1261                 }
1262
1263                 // Serialize the object
1264     for(var key in object) {
1265       // Check the key and throw error if it's illegal
1266       if (key != '$db' && key != '$ref' && key != '$id') {
1267         // dollars and dots ok
1268         BSON.checkKey(key, !checkKeys);
1269       }
1270
1271       // Pack the element
1272       index = packElement(key, object[key], checkKeys, buffer, index, serializeFunctions);
1273     }
1274   }
1275
1276   // Write zero
1277   buffer[index++] = 0;
1278   return index;
1279 }
1280
1281 var stringToBytes = function(str) {
1282   var ch, st, re = [];
1283   for (var i = 0; i < str.length; i++ ) {
1284     ch = str.charCodeAt(i);  // get char
1285     st = [];                 // set up "stack"
1286     do {
1287       st.push( ch & 0xFF );  // push byte to stack
1288       ch = ch >> 8;          // shift value down by 1 byte
1289     }
1290     while ( ch );
1291     // add stack contents to result
1292     // done because chars have "wrong" endianness
1293     re = re.concat( st.reverse() );
1294   }
1295   // return an array of bytes
1296   return re;
1297 }
1298
1299 var numberOfBytes = function(str) {
1300   var ch, st, re = 0;
1301   for (var i = 0; i < str.length; i++ ) {
1302     ch = str.charCodeAt(i);  // get char
1303     st = [];                 // set up "stack"
1304     do {
1305       st.push( ch & 0xFF );  // push byte to stack
1306       ch = ch >> 8;          // shift value down by 1 byte
1307     }
1308     while ( ch );
1309     // add stack contents to result
1310     // done because chars have "wrong" endianness
1311     re = re + st.length;
1312   }
1313   // return an array of bytes
1314   return re;
1315 }
1316
1317 /**
1318  * @ignore
1319  * @api private
1320  */
1321 var writeToTypedArray = function(buffer, string, index) {
1322   var bytes = stringToBytes(string);
1323   for(var i = 0; i < bytes.length; i++) {
1324     buffer[index + i] = bytes[i];
1325   }
1326   return bytes.length;
1327 }
1328
1329 /**
1330  * @ignore
1331  * @api private
1332  */
1333 var supportsBuffer = typeof Buffer != 'undefined';
1334
1335 /**
1336  * @ignore
1337  * @api private
1338  */
1339 var packElement = function(name, value, checkKeys, buffer, index, serializeFunctions) {
1340   var startIndex = index;
1341
1342   switch(typeof value) {
1343     case 'string':
1344       // Encode String type
1345       buffer[index++] = BSON.BSON_DATA_STRING;
1346       // Number of written bytes
1347       var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1348       // Encode the name
1349       index = index + numberOfWrittenBytes + 1;
1350       buffer[index - 1] = 0;
1351
1352       // Calculate size
1353       var size = supportsBuffer ? Buffer.byteLength(value) + 1 : numberOfBytes(value) + 1;
1354       // Write the size of the string to buffer
1355       buffer[index + 3] = (size >> 24) & 0xff;
1356       buffer[index + 2] = (size >> 16) & 0xff;
1357       buffer[index + 1] = (size >> 8) & 0xff;
1358       buffer[index] = size & 0xff;
1359       // Ajust the index
1360       index = index + 4;
1361       // Write the string
1362       supportsBuffer ? buffer.write(value, index, 'utf8') : writeToTypedArray(buffer, value, index);
1363       // Update index
1364       index = index + size - 1;
1365       // Write zero
1366       buffer[index++] = 0;
1367       // Return index
1368       return index;
1369     case 'number':
1370       // We have an integer value
1371       if(Math.floor(value) === value && value >= BSON.JS_INT_MIN && value <= BSON.JS_INT_MAX) {
1372         // If the value fits in 32 bits encode as int, if it fits in a double
1373         // encode it as a double, otherwise long
1374         if(value >= BSON.BSON_INT32_MIN && value <= BSON.BSON_INT32_MAX) {
1375           // Set int type 32 bits or less
1376           buffer[index++] = BSON.BSON_DATA_INT;
1377           // Number of written bytes
1378           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1379           // Encode the name
1380           index = index + numberOfWrittenBytes + 1;
1381           buffer[index - 1] = 0;
1382           // Write the int value
1383           buffer[index++] = value & 0xff;
1384           buffer[index++] = (value >> 8) & 0xff;
1385           buffer[index++] = (value >> 16) & 0xff;
1386           buffer[index++] = (value >> 24) & 0xff;
1387         } else if(value >= BSON.JS_INT_MIN && value <= BSON.JS_INT_MAX) {
1388           // Encode as double
1389           buffer[index++] = BSON.BSON_DATA_NUMBER;
1390           // Number of written bytes
1391           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1392           // Encode the name
1393           index = index + numberOfWrittenBytes + 1;
1394           buffer[index - 1] = 0;
1395           // Write float
1396           writeIEEE754(buffer, value, index, 'little', 52, 8);
1397           // Ajust index
1398           index = index + 8;
1399         } else {
1400           // Set long type
1401           buffer[index++] = BSON.BSON_DATA_LONG;
1402           // Number of written bytes
1403           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1404           // Encode the name
1405           index = index + numberOfWrittenBytes + 1;
1406           buffer[index - 1] = 0;
1407           var longVal = Long.fromNumber(value);
1408           var lowBits = longVal.getLowBits();
1409           var highBits = longVal.getHighBits();
1410           // Encode low bits
1411           buffer[index++] = lowBits & 0xff;
1412           buffer[index++] = (lowBits >> 8) & 0xff;
1413           buffer[index++] = (lowBits >> 16) & 0xff;
1414           buffer[index++] = (lowBits >> 24) & 0xff;
1415           // Encode high bits
1416           buffer[index++] = highBits & 0xff;
1417           buffer[index++] = (highBits >> 8) & 0xff;
1418           buffer[index++] = (highBits >> 16) & 0xff;
1419           buffer[index++] = (highBits >> 24) & 0xff;
1420         }
1421       } else {
1422         // Encode as double
1423         buffer[index++] = BSON.BSON_DATA_NUMBER;
1424         // Number of written bytes
1425         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1426         // Encode the name
1427         index = index + numberOfWrittenBytes + 1;
1428         buffer[index - 1] = 0;
1429         // Write float
1430         writeIEEE754(buffer, value, index, 'little', 52, 8);
1431         // Ajust index
1432         index = index + 8;
1433       }
1434
1435       return index;
1436     case 'undefined':
1437       // Set long type
1438       buffer[index++] = BSON.BSON_DATA_NULL;
1439       // Number of written bytes
1440       var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1441       // Encode the name
1442       index = index + numberOfWrittenBytes + 1;
1443       buffer[index - 1] = 0;
1444       return index;
1445     case 'boolean':
1446       // Write the type
1447       buffer[index++] = BSON.BSON_DATA_BOOLEAN;
1448       // Number of written bytes
1449       var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1450       // Encode the name
1451       index = index + numberOfWrittenBytes + 1;
1452       buffer[index - 1] = 0;
1453       // Encode the boolean value
1454       buffer[index++] = value ? 1 : 0;
1455       return index;
1456     case 'object':
1457       if(value === null || value instanceof MinKey || value instanceof MaxKey
1458           || value['_bsontype'] == 'MinKey' || value['_bsontype'] == 'MaxKey') {
1459         // Write the type of either min or max key
1460         if(value === null) {
1461           buffer[index++] = BSON.BSON_DATA_NULL;
1462         } else if(value instanceof MinKey) {
1463           buffer[index++] = BSON.BSON_DATA_MIN_KEY;
1464         } else {
1465           buffer[index++] = BSON.BSON_DATA_MAX_KEY;
1466         }
1467
1468         // Number of written bytes
1469         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1470         // Encode the name
1471         index = index + numberOfWrittenBytes + 1;
1472         buffer[index - 1] = 0;
1473         return index;
1474       } else if(value instanceof ObjectID || value['_bsontype'] == 'ObjectID') {
1475         // Write the type
1476         buffer[index++] = BSON.BSON_DATA_OID;
1477         // Number of written bytes
1478         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1479         // Encode the name
1480         index = index + numberOfWrittenBytes + 1;
1481         buffer[index - 1] = 0;
1482
1483         // Write objectid
1484         supportsBuffer ? buffer.write(value.id, index, 'binary') : writeToTypedArray(buffer, value.id, index);
1485         // Ajust index
1486         index = index + 12;
1487         return index;
1488       } else if(value instanceof Date || isDate(value)) {
1489         // Write the type
1490         buffer[index++] = BSON.BSON_DATA_DATE;
1491         // Number of written bytes
1492         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1493         // Encode the name
1494         index = index + numberOfWrittenBytes + 1;
1495         buffer[index - 1] = 0;
1496
1497         // Write the date
1498         var dateInMilis = Long.fromNumber(value.getTime());
1499         var lowBits = dateInMilis.getLowBits();
1500         var highBits = dateInMilis.getHighBits();
1501         // Encode low bits
1502         buffer[index++] = lowBits & 0xff;
1503         buffer[index++] = (lowBits >> 8) & 0xff;
1504         buffer[index++] = (lowBits >> 16) & 0xff;
1505         buffer[index++] = (lowBits >> 24) & 0xff;
1506         // Encode high bits
1507         buffer[index++] = highBits & 0xff;
1508         buffer[index++] = (highBits >> 8) & 0xff;
1509         buffer[index++] = (highBits >> 16) & 0xff;
1510         buffer[index++] = (highBits >> 24) & 0xff;
1511         return index;
1512       } else if(typeof Buffer !== 'undefined' && Buffer.isBuffer(value)) {
1513         // Write the type
1514         buffer[index++] = BSON.BSON_DATA_BINARY;
1515         // Number of written bytes
1516         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1517         // Encode the name
1518         index = index + numberOfWrittenBytes + 1;
1519         buffer[index - 1] = 0;
1520         // Get size of the buffer (current write point)
1521         var size = value.length;
1522         // Write the size of the string to buffer
1523         buffer[index++] = size & 0xff;
1524         buffer[index++] = (size >> 8) & 0xff;
1525         buffer[index++] = (size >> 16) & 0xff;
1526         buffer[index++] = (size >> 24) & 0xff;
1527         // Write the default subtype
1528         buffer[index++] = BSON.BSON_BINARY_SUBTYPE_DEFAULT;
1529         // Copy the content form the binary field to the buffer
1530         value.copy(buffer, index, 0, size);
1531         // Adjust the index
1532         index = index + size;
1533         return index;
1534       } else if(value instanceof Long || value instanceof Timestamp || value['_bsontype'] == 'Long' || value['_bsontype'] == 'Timestamp') {
1535         // Write the type
1536         buffer[index++] = value instanceof Long ? BSON.BSON_DATA_LONG : BSON.BSON_DATA_TIMESTAMP;
1537         // Number of written bytes
1538         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1539         // Encode the name
1540         index = index + numberOfWrittenBytes + 1;
1541         buffer[index - 1] = 0;
1542         // Write the date
1543         var lowBits = value.getLowBits();
1544         var highBits = value.getHighBits();
1545         // Encode low bits
1546         buffer[index++] = lowBits & 0xff;
1547         buffer[index++] = (lowBits >> 8) & 0xff;
1548         buffer[index++] = (lowBits >> 16) & 0xff;
1549         buffer[index++] = (lowBits >> 24) & 0xff;
1550         // Encode high bits
1551         buffer[index++] = highBits & 0xff;
1552         buffer[index++] = (highBits >> 8) & 0xff;
1553         buffer[index++] = (highBits >> 16) & 0xff;
1554         buffer[index++] = (highBits >> 24) & 0xff;
1555         return index;
1556       } else if(value instanceof Double || value['_bsontype'] == 'Double') {
1557         // Encode as double
1558         buffer[index++] = BSON.BSON_DATA_NUMBER;
1559         // Number of written bytes
1560         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1561         // Encode the name
1562         index = index + numberOfWrittenBytes + 1;
1563         buffer[index - 1] = 0;
1564         // Write float
1565         writeIEEE754(buffer, value, index, 'little', 52, 8);
1566         // Ajust index
1567         index = index + 8;
1568         return index;
1569       } else if(value instanceof Code || value['_bsontype'] == 'Code') {
1570         if(value.scope != null && Object.keys(value.scope).length > 0) {
1571           // Write the type
1572           buffer[index++] = BSON.BSON_DATA_CODE_W_SCOPE;
1573           // Number of written bytes
1574           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1575           // Encode the name
1576           index = index + numberOfWrittenBytes + 1;
1577           buffer[index - 1] = 0;
1578           // Calculate the scope size
1579           var scopeSize = BSON.calculateObjectSize(value.scope, serializeFunctions);
1580           // Function string
1581           var functionString = value.code.toString();
1582           // Function Size
1583           var codeSize = supportsBuffer ? Buffer.byteLength(functionString) + 1 : numberOfBytes(functionString) + 1;
1584
1585           // Calculate full size of the object
1586           var totalSize = 4 + codeSize + scopeSize + 4;
1587
1588           // Write the total size of the object
1589           buffer[index++] = totalSize & 0xff;
1590           buffer[index++] = (totalSize >> 8) & 0xff;
1591           buffer[index++] = (totalSize >> 16) & 0xff;
1592           buffer[index++] = (totalSize >> 24) & 0xff;
1593
1594           // Write the size of the string to buffer
1595           buffer[index++] = codeSize & 0xff;
1596           buffer[index++] = (codeSize >> 8) & 0xff;
1597           buffer[index++] = (codeSize >> 16) & 0xff;
1598           buffer[index++] = (codeSize >> 24) & 0xff;
1599
1600           // Write the string
1601           supportsBuffer ? buffer.write(functionString, index, 'utf8') : writeToTypedArray(buffer, functionString, index);
1602           // Update index
1603           index = index + codeSize - 1;
1604           // Write zero
1605           buffer[index++] = 0;
1606           // Serialize the scope object
1607           var scopeObjectBuffer = supportsBuffer ? new Buffer(scopeSize) : new Uint8Array(new ArrayBuffer(scopeSize));
1608           // Execute the serialization into a seperate buffer
1609           serializeObject(value.scope, checkKeys, scopeObjectBuffer, 0, serializeFunctions);
1610
1611           // Adjusted scope Size (removing the header)
1612           var scopeDocSize = scopeSize;
1613           // Write scope object size
1614           buffer[index++] = scopeDocSize & 0xff;
1615           buffer[index++] = (scopeDocSize >> 8) & 0xff;
1616           buffer[index++] = (scopeDocSize >> 16) & 0xff;
1617           buffer[index++] = (scopeDocSize >> 24) & 0xff;
1618
1619           // Write the scopeObject into the buffer
1620           supportsBuffer ? scopeObjectBuffer.copy(buffer, index, 0, scopeSize) : buffer.set(scopeObjectBuffer, index);
1621           // Adjust index, removing the empty size of the doc (5 bytes 0000000005)
1622           index = index + scopeDocSize - 5;
1623           // Write trailing zero
1624           buffer[index++] = 0;
1625           return index
1626         } else {
1627           buffer[index++] = BSON.BSON_DATA_CODE;
1628           // Number of written bytes
1629           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1630           // Encode the name
1631           index = index + numberOfWrittenBytes + 1;
1632           buffer[index - 1] = 0;
1633           // Function string
1634           var functionString = value.code.toString();
1635           // Function Size
1636           var size = supportsBuffer ? Buffer.byteLength(functionString) + 1 : numberOfBytes(functionString) + 1;
1637           // Write the size of the string to buffer
1638           buffer[index++] = size & 0xff;
1639           buffer[index++] = (size >> 8) & 0xff;
1640           buffer[index++] = (size >> 16) & 0xff;
1641           buffer[index++] = (size >> 24) & 0xff;
1642           // Write the string
1643           supportsBuffer ? buffer.write(functionString, index, 'utf8') : writeToTypedArray(buffer, functionString, index);
1644           // Update index
1645           index = index + size - 1;
1646           // Write zero
1647           buffer[index++] = 0;
1648           return index;
1649         }
1650       } else if(value instanceof Binary || value['_bsontype'] == 'Binary') {
1651         // Write the type
1652         buffer[index++] = BSON.BSON_DATA_BINARY;
1653         // Number of written bytes
1654         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1655         // Encode the name
1656         index = index + numberOfWrittenBytes + 1;
1657         buffer[index - 1] = 0;
1658         // Extract the buffer
1659         var data = value.value(true);
1660         // Calculate size
1661         var size = value.position;
1662         // Write the size of the string to buffer
1663         buffer[index++] = size & 0xff;
1664         buffer[index++] = (size >> 8) & 0xff;
1665         buffer[index++] = (size >> 16) & 0xff;
1666         buffer[index++] = (size >> 24) & 0xff;
1667         // Write the subtype to the buffer
1668         buffer[index++] = value.sub_type;
1669
1670         // If we have binary type 2 the 4 first bytes are the size
1671         if(value.sub_type == Binary.SUBTYPE_BYTE_ARRAY) {
1672           buffer[index++] = size & 0xff;
1673           buffer[index++] = (size >> 8) & 0xff;
1674           buffer[index++] = (size >> 16) & 0xff;
1675           buffer[index++] = (size >> 24) & 0xff;
1676         }
1677
1678         // Write the data to the object
1679         supportsBuffer ? data.copy(buffer, index, 0, value.position) : buffer.set(data, index);
1680         // Ajust index
1681         index = index + value.position;
1682         return index;
1683       } else if(value instanceof Symbol || value['_bsontype'] == 'Symbol') {
1684         // Write the type
1685         buffer[index++] = BSON.BSON_DATA_SYMBOL;
1686         // Number of written bytes
1687         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1688         // Encode the name
1689         index = index + numberOfWrittenBytes + 1;
1690         buffer[index - 1] = 0;
1691         // Calculate size
1692         var size = supportsBuffer ? Buffer.byteLength(value.value) + 1 : numberOfBytes(value.value) + 1;
1693         // Write the size of the string to buffer
1694         buffer[index++] = size & 0xff;
1695         buffer[index++] = (size >> 8) & 0xff;
1696         buffer[index++] = (size >> 16) & 0xff;
1697         buffer[index++] = (size >> 24) & 0xff;
1698         // Write the string
1699         buffer.write(value.value, index, 'utf8');
1700         // Update index
1701         index = index + size - 1;
1702         // Write zero
1703         buffer[index++] = 0x00;
1704         return index;
1705       } else if(value instanceof DBRef || value['_bsontype'] == 'DBRef') {
1706         // Write the type
1707         buffer[index++] = BSON.BSON_DATA_OBJECT;
1708         // Number of written bytes
1709         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1710         // Encode the name
1711         index = index + numberOfWrittenBytes + 1;
1712         buffer[index - 1] = 0;
1713         // Set up correct object for serialization
1714         var ordered_values = {
1715             '$ref': value.namespace
1716           , '$id' : value.oid
1717         };
1718
1719         // Add db reference if it exists
1720         if(null != value.db) {
1721           ordered_values['$db'] = value.db;
1722         }
1723
1724         // Message size
1725         var size = BSON.calculateObjectSize(ordered_values, serializeFunctions);
1726         // Serialize the object
1727         var endIndex = BSON.serializeWithBufferAndIndex(ordered_values, checkKeys, buffer, index, serializeFunctions);
1728         // Write the size of the string to buffer
1729         buffer[index++] = size & 0xff;
1730         buffer[index++] = (size >> 8) & 0xff;
1731         buffer[index++] = (size >> 16) & 0xff;
1732         buffer[index++] = (size >> 24) & 0xff;
1733         // Write zero for object
1734         buffer[endIndex++] = 0x00;
1735         // Return the end index
1736         return endIndex;
1737       } else if(value instanceof RegExp || Object.prototype.toString.call(value) === '[object RegExp]') {
1738         // Write the type
1739         buffer[index++] = BSON.BSON_DATA_REGEXP;
1740         // Number of written bytes
1741         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1742         // Encode the name
1743         index = index + numberOfWrittenBytes + 1;
1744         buffer[index - 1] = 0;
1745
1746         // Write the regular expression string
1747         supportsBuffer ? buffer.write(value.source, index, 'utf8') : writeToTypedArray(buffer, value.source, index);
1748         // Adjust the index
1749         index = index + (supportsBuffer ? Buffer.byteLength(value.source) : numberOfBytes(value.source));
1750         // Write zero
1751         buffer[index++] = 0x00;
1752         // Write the parameters
1753         if(value.global) buffer[index++] = 0x73; // s
1754         if(value.ignoreCase) buffer[index++] = 0x69; // i
1755         if(value.multiline) buffer[index++] = 0x6d; // m
1756         // Add ending zero
1757         buffer[index++] = 0x00;
1758         return index;
1759       } else {
1760         // Write the type
1761         buffer[index++] = Array.isArray(value) ? BSON.BSON_DATA_ARRAY : BSON.BSON_DATA_OBJECT;
1762         // Number of written bytes
1763         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1764         // Adjust the index
1765         index = index + numberOfWrittenBytes + 1;
1766         buffer[index - 1] = 0;
1767               var endIndex = serializeObject(value, checkKeys, buffer, index + 4, serializeFunctions);
1768         // Write size
1769         var size = endIndex - index;
1770         // Write the size of the string to buffer
1771         buffer[index++] = size & 0xff;
1772         buffer[index++] = (size >> 8) & 0xff;
1773         buffer[index++] = (size >> 16) & 0xff;
1774         buffer[index++] = (size >> 24) & 0xff;
1775         return endIndex;
1776       }
1777     case 'function':
1778       // WTF for 0.4.X where typeof /someregexp/ === 'function'
1779       if(value instanceof RegExp || Object.prototype.toString.call(value) === '[object RegExp]' || String.call(value) == '[object RegExp]') {
1780         // Write the type
1781         buffer[index++] = BSON.BSON_DATA_REGEXP;
1782         // Number of written bytes
1783         var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1784         // Encode the name
1785         index = index + numberOfWrittenBytes + 1;
1786         buffer[index - 1] = 0;
1787
1788         // Write the regular expression string
1789         buffer.write(value.source, index, 'utf8');
1790         // Adjust the index
1791         index = index + (supportsBuffer ? Buffer.byteLength(value.source) : numberOfBytes(value.source));
1792         // Write zero
1793         buffer[index++] = 0x00;
1794         // Write the parameters
1795         if(value.global) buffer[index++] = 0x73; // s
1796         if(value.ignoreCase) buffer[index++] = 0x69; // i
1797         if(value.multiline) buffer[index++] = 0x6d; // m
1798         // Add ending zero
1799         buffer[index++] = 0x00;
1800         return index;
1801       } else {
1802         if(serializeFunctions && value.scope != null && Object.keys(value.scope).length > 0) {
1803           // Write the type
1804           buffer[index++] = BSON.BSON_DATA_CODE_W_SCOPE;
1805           // Number of written bytes
1806           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1807           // Encode the name
1808           index = index + numberOfWrittenBytes + 1;
1809           buffer[index - 1] = 0;
1810           // Calculate the scope size
1811           var scopeSize = BSON.calculateObjectSize(value.scope, serializeFunctions);
1812           // Function string
1813           var functionString = value.toString();
1814           // Function Size
1815           var codeSize = supportsBuffer ? Buffer.byteLength(functionString) + 1 : numberOfBytes(functionString) + 1;
1816
1817           // Calculate full size of the object
1818           var totalSize = 4 + codeSize + scopeSize;
1819
1820           // Write the total size of the object
1821           buffer[index++] = totalSize & 0xff;
1822           buffer[index++] = (totalSize >> 8) & 0xff;
1823           buffer[index++] = (totalSize >> 16) & 0xff;
1824           buffer[index++] = (totalSize >> 24) & 0xff;
1825
1826           // Write the size of the string to buffer
1827           buffer[index++] = codeSize & 0xff;
1828           buffer[index++] = (codeSize >> 8) & 0xff;
1829           buffer[index++] = (codeSize >> 16) & 0xff;
1830           buffer[index++] = (codeSize >> 24) & 0xff;
1831
1832           // Write the string
1833           supportsBuffer ? buffer.write(functionString, index, 'utf8') : writeToTypedArray(buffer, functionString, index);
1834           // Update index
1835           index = index + codeSize - 1;
1836           // Write zero
1837           buffer[index++] = 0;
1838           // Serialize the scope object
1839           var scopeObjectBuffer = new Buffer(scopeSize);
1840           // Execute the serialization into a seperate buffer
1841           serializeObject(value.scope, checkKeys, scopeObjectBuffer, 0, serializeFunctions);
1842
1843           // Adjusted scope Size (removing the header)
1844           var scopeDocSize = scopeSize - 4;
1845           // Write scope object size
1846           buffer[index++] = scopeDocSize & 0xff;
1847           buffer[index++] = (scopeDocSize >> 8) & 0xff;
1848           buffer[index++] = (scopeDocSize >> 16) & 0xff;
1849           buffer[index++] = (scopeDocSize >> 24) & 0xff;
1850
1851           // Write the scopeObject into the buffer
1852           scopeObjectBuffer.copy(buffer, index, 0, scopeSize);
1853
1854           // Adjust index, removing the empty size of the doc (5 bytes 0000000005)
1855           index = index + scopeDocSize - 5;
1856           // Write trailing zero
1857           buffer[index++] = 0;
1858           return index
1859         } else if(serializeFunctions) {
1860           buffer[index++] = BSON.BSON_DATA_CODE;
1861           // Number of written bytes
1862           var numberOfWrittenBytes = supportsBuffer ? buffer.write(name, index, 'utf8') : writeToTypedArray(buffer, name, index);
1863           // Encode the name
1864           index = index + numberOfWrittenBytes + 1;
1865           buffer[index - 1] = 0;
1866           // Function string
1867           var functionString = value.toString();
1868           // Function Size
1869           var size = supportsBuffer ? Buffer.byteLength(functionString) + 1 : numberOfBytes(functionString) + 1;
1870           // Write the size of the string to buffer
1871           buffer[index++] = size & 0xff;
1872           buffer[index++] = (size >> 8) & 0xff;
1873           buffer[index++] = (size >> 16) & 0xff;
1874           buffer[index++] = (size >> 24) & 0xff;
1875           // Write the string
1876           supportsBuffer ? buffer.write(functionString, index, 'utf8') : writeToTypedArray(buffer, functionString, index);
1877           // Update index
1878           index = index + size - 1;
1879           // Write zero
1880           buffer[index++] = 0;
1881           return index;
1882         }
1883       }
1884   }
1885
1886   // If no value to serialize
1887   return index;
1888 }
1889
1890 /**
1891  * Serialize a Javascript object.
1892  *
1893  * @param {Object} object the Javascript object to serialize.
1894  * @param {Boolean} checkKeys the serializer will check if keys are valid.
1895  * @param {Boolean} asBuffer return the serialized object as a Buffer object **(ignore)**.
1896  * @param {Boolean} serializeFunctions serialize the javascript functions **(default:false)**.
1897  * @return {Buffer} returns the Buffer object containing the serialized object.
1898  * @api public
1899  */
1900 BSON.serialize = function(object, checkKeys, asBuffer, serializeFunctions) {
1901   // Throw error if we are trying serialize an illegal type
1902   if(object == null || typeof object != 'object' || Array.isArray(object)) 
1903     throw new Error("Only javascript objects supported");
1904   
1905   // Emoty target buffer
1906   var buffer = null;
1907   // Calculate the size of the object
1908   var size = BSON.calculateObjectSize(object, serializeFunctions);
1909   // Fetch the best available type for storing the binary data
1910   if(buffer = typeof Buffer != 'undefined') {
1911     buffer = new Buffer(size);
1912     asBuffer = true;
1913   } else if(typeof Uint8Array != 'undefined') {
1914     buffer = new Uint8Array(new ArrayBuffer(size));
1915   } else {
1916     buffer = new Array(size);
1917   }
1918
1919   // If asBuffer is false use typed arrays
1920   BSON.serializeWithBufferAndIndex(object, checkKeys, buffer, 0, serializeFunctions);
1921   return buffer;
1922 }
1923
1924 /**
1925  * Contains the function cache if we have that enable to allow for avoiding the eval step on each deserialization, comparison is by md5
1926  *
1927  * @ignore
1928  * @api private
1929  */
1930 var functionCache = BSON.functionCache = {};
1931
1932 /**
1933  * Crc state variables shared by function
1934  *
1935  * @ignore
1936  * @api private
1937  */
1938 var table = [0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3, 0x0EDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91, 0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7, 0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5, 0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B, 0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59, 0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F, 0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D, 0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433, 0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01, 0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457, 0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65, 0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB, 0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9, 0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F, 0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD, 0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683, 0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1, 0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7, 0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5, 0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B, 0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79, 0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F, 0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D, 0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713, 0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21, 0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777, 0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45, 0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB, 0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9, 0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF, 0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D];
1939
1940 /**
1941  * CRC32 hash method, Fast and enough versitility for our usage
1942  *
1943  * @ignore
1944  * @api private
1945  */
1946 var crc32 =  function(string, start, end) {
1947   var crc = 0
1948   var x = 0;
1949   var y = 0;
1950   crc = crc ^ (-1);
1951
1952   for(var i = start, iTop = end; i < iTop;i++) {
1953         y = (crc ^ string[i]) & 0xFF;
1954     x = table[y];
1955         crc = (crc >>> 8) ^ x;
1956   }
1957
1958   return crc ^ (-1);
1959 }
1960
1961 /**
1962  * Deserialize stream data as BSON documents.
1963  *
1964  * Options
1965  *  - **evalFunctions** {Boolean, default:false}, evaluate functions in the BSON document scoped to the object deserialized.
1966  *  - **cacheFunctions** {Boolean, default:false}, cache evaluated functions for reuse.
1967  *  - **cacheFunctionsCrc32** {Boolean, default:false}, use a crc32 code for caching, otherwise use the string of the function.
1968  *  - **promoteLongs** {Boolean, default:true}, when deserializing a Long will fit it into a Number if it's smaller than 53 bits
1969  *
1970  * @param {Buffer} data the buffer containing the serialized set of BSON documents.
1971  * @param {Number} startIndex the start index in the data Buffer where the deserialization is to start.
1972  * @param {Number} numberOfDocuments number of documents to deserialize.
1973  * @param {Array} documents an array where to store the deserialized documents.
1974  * @param {Number} docStartIndex the index in the documents array from where to start inserting documents.
1975  * @param {Object} [options] additional options used for the deserialization.
1976  * @return {Number} returns the next index in the buffer after deserialization **x** numbers of documents.
1977  * @api public
1978  */
1979 BSON.deserializeStream = function(data, startIndex, numberOfDocuments, documents, docStartIndex, options) {
1980   // if(numberOfDocuments !== documents.length) throw new Error("Number of expected results back is less than the number of documents");
1981   options = options != null ? options : {};
1982   var index = startIndex;
1983   // Loop over all documents
1984   for(var i = 0; i < numberOfDocuments; i++) {
1985     // Find size of the document
1986     var size = data[index] | data[index + 1] << 8 | data[index + 2] << 16 | data[index + 3] << 24;
1987     // Update options with index
1988     options['index'] = index;
1989     // Parse the document at this point
1990     documents[docStartIndex + i] = BSON.deserialize(data, options);
1991     // Adjust index by the document size
1992     index = index + size;
1993   }
1994
1995   // Return object containing end index of parsing and list of documents
1996   return index;
1997 }
1998
1999 /**
2000  * Ensure eval is isolated.
2001  *
2002  * @ignore
2003  * @api private
2004  */
2005 var isolateEvalWithHash = function(functionCache, hash, functionString, object) {
2006   // Contains the value we are going to set
2007   var value = null;
2008
2009   // Check for cache hit, eval if missing and return cached function
2010   if(functionCache[hash] == null) {
2011     eval("value = " + functionString);
2012     functionCache[hash] = value;
2013   }
2014   // Set the object
2015   return functionCache[hash].bind(object);
2016 }
2017
2018 /**
2019  * Ensure eval is isolated.
2020  *
2021  * @ignore
2022  * @api private
2023  */
2024 var isolateEval = function(functionString) {
2025   // Contains the value we are going to set
2026   var value = null;
2027   // Eval the function
2028   eval("value = " + functionString);
2029   return value;
2030 }
2031
2032 /**
2033  * Convert Uint8Array to String
2034  *
2035  * @ignore
2036  * @api private
2037  */
2038 var convertUint8ArrayToUtf8String = function(byteArray, startIndex, endIndex) {
2039   return BinaryParser.decode_utf8(convertArraytoUtf8BinaryString(byteArray, startIndex, endIndex));
2040 }
2041
2042 var convertArraytoUtf8BinaryString = function(byteArray, startIndex, endIndex) {
2043   var result = "";
2044   for(var i = startIndex; i < endIndex; i++) {
2045     result = result + String.fromCharCode(byteArray[i]);
2046   }
2047
2048   return result;
2049 };
2050
2051 /**
2052  * Deserialize data as BSON.
2053  *
2054  * Options
2055  *  - **evalFunctions** {Boolean, default:false}, evaluate functions in the BSON document scoped to the object deserialized.
2056  *  - **cacheFunctions** {Boolean, default:false}, cache evaluated functions for reuse.
2057  *  - **cacheFunctionsCrc32** {Boolean, default:false}, use a crc32 code for caching, otherwise use the string of the function.
2058  *  - **promoteLongs** {Boolean, default:true}, when deserializing a Long will fit it into a Number if it's smaller than 53 bits
2059  *
2060  * @param {Buffer} buffer the buffer containing the serialized set of BSON documents.
2061  * @param {Object} [options] additional options used for the deserialization.
2062  * @param {Boolean} [isArray] ignore used for recursive parsing.
2063  * @return {Object} returns the deserialized Javascript Object.
2064  * @api public
2065  */
2066 BSON.deserialize = function(buffer, options, isArray) {
2067   // Options
2068   options = options == null ? {} : options;
2069   var evalFunctions = options['evalFunctions'] == null ? false : options['evalFunctions'];
2070   var cacheFunctions = options['cacheFunctions'] == null ? false : options['cacheFunctions'];
2071   var cacheFunctionsCrc32 = options['cacheFunctionsCrc32'] == null ? false : options['cacheFunctionsCrc32'];
2072   var promoteLongs = options['promoteLongs'] || true;
2073
2074   // Validate that we have at least 4 bytes of buffer
2075   if(buffer.length < 5) throw new Error("corrupt bson message < 5 bytes long");
2076
2077   // Set up index
2078   var index = typeof options['index'] == 'number' ? options['index'] : 0;
2079   // Reads in a C style string
2080   var readCStyleString = function() {
2081     // Get the start search index
2082     var i = index;
2083     // Locate the end of the c string
2084     while(buffer[i] !== 0x00) { i++ }
2085     // Grab utf8 encoded string
2086     var string = supportsBuffer && Buffer.isBuffer(buffer) ? buffer.toString('utf8', index, i) : convertUint8ArrayToUtf8String(buffer, index, i);
2087     // Update index position
2088     index = i + 1;
2089     // Return string
2090     return string;
2091   }
2092
2093   // Create holding object
2094   var object = isArray ? [] : {};
2095
2096   // Read the document size
2097   var size = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2098
2099   // Ensure buffer is valid size
2100   if(size < 5 || size > buffer.length) throw new Error("corrupt bson message");
2101
2102   // While we have more left data left keep parsing
2103   while(true) {
2104     // Read the type
2105     var elementType = buffer[index++];
2106     // If we get a zero it's the last byte, exit
2107     if(elementType == 0) break;
2108     // Read the name of the field
2109     var name = readCStyleString();
2110     // Switch on the type
2111     switch(elementType) {
2112       case BSON.BSON_DATA_OID:
2113         var string = supportsBuffer && Buffer.isBuffer(buffer) ? buffer.toString('binary', index, index + 12) : convertArraytoUtf8BinaryString(buffer, index, index + 12);
2114         // Decode the oid
2115         object[name] = new ObjectID(string);
2116         // Update index
2117         index = index + 12;
2118         break;
2119       case BSON.BSON_DATA_STRING:
2120         // Read the content of the field
2121         var stringSize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2122         // Add string to object
2123         object[name] = supportsBuffer && Buffer.isBuffer(buffer) ? buffer.toString('utf8', index, index + stringSize - 1) : convertUint8ArrayToUtf8String(buffer, index, index + stringSize - 1);
2124         // Update parse index position
2125         index = index + stringSize;
2126         break;
2127       case BSON.BSON_DATA_INT:
2128         // Decode the 32bit value
2129         object[name] = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2130         break;
2131       case BSON.BSON_DATA_NUMBER:
2132         // Decode the double value
2133         object[name] = readIEEE754(buffer, index, 'little', 52, 8);
2134         // Update the index
2135         index = index + 8;
2136         break;
2137       case BSON.BSON_DATA_DATE:
2138         // Unpack the low and high bits
2139         var lowBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2140         var highBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2141         // Set date object
2142         object[name] = new Date(new Long(lowBits, highBits).toNumber());
2143         break;
2144       case BSON.BSON_DATA_BOOLEAN:
2145         // Parse the boolean value
2146         object[name] = buffer[index++] == 1;
2147         break;
2148       case BSON.BSON_DATA_NULL:
2149         // Parse the boolean value
2150         object[name] = null;
2151         break;
2152       case BSON.BSON_DATA_BINARY:
2153         // Decode the size of the binary blob
2154         var binarySize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2155         // Decode the subtype
2156         var subType = buffer[index++];
2157         // Decode as raw Buffer object if options specifies it
2158         if(buffer['slice'] != null) {
2159           // If we have subtype 2 skip the 4 bytes for the size
2160           if(subType == Binary.SUBTYPE_BYTE_ARRAY) {
2161             binarySize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2162           }
2163           // Slice the data
2164           object[name] = new Binary(buffer.slice(index, index + binarySize), subType);
2165         } else {
2166           var _buffer = typeof Uint8Array != 'undefined' ? new Uint8Array(new ArrayBuffer(binarySize)) : new Array(binarySize);
2167           // If we have subtype 2 skip the 4 bytes for the size
2168           if(subType == Binary.SUBTYPE_BYTE_ARRAY) {
2169             binarySize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2170           }
2171           // Copy the data
2172           for(var i = 0; i < binarySize; i++) {
2173             _buffer[i] = buffer[index + i];
2174           }
2175           // Create the binary object
2176           object[name] = new Binary(_buffer, subType);
2177         }
2178         // Update the index
2179         index = index + binarySize;
2180         break;
2181       case BSON.BSON_DATA_ARRAY:
2182         options['index'] = index;
2183         // Decode the size of the array document
2184         var objectSize = buffer[index] | buffer[index + 1] << 8 | buffer[index + 2] << 16 | buffer[index + 3] << 24;
2185         // Set the array to the object
2186         object[name] = BSON.deserialize(buffer, options, true);
2187         // Adjust the index
2188         index = index + objectSize;
2189         break;
2190       case BSON.BSON_DATA_OBJECT:
2191         options['index'] = index;
2192         // Decode the size of the object document
2193         var objectSize = buffer[index] | buffer[index + 1] << 8 | buffer[index + 2] << 16 | buffer[index + 3] << 24;
2194         // Set the array to the object
2195         object[name] = BSON.deserialize(buffer, options, false);
2196         // Adjust the index
2197         index = index + objectSize;
2198         break;
2199       case BSON.BSON_DATA_REGEXP:
2200         // Create the regexp
2201         var source = readCStyleString();
2202         var regExpOptions = readCStyleString();
2203         // For each option add the corresponding one for javascript
2204         var optionsArray = new Array(regExpOptions.length);
2205
2206         // Parse options
2207         for(var i = 0; i < regExpOptions.length; i++) {
2208           switch(regExpOptions[i]) {
2209             case 'm':
2210               optionsArray[i] = 'm';
2211               break;
2212             case 's':
2213               optionsArray[i] = 'g';
2214               break;
2215             case 'i':
2216               optionsArray[i] = 'i';
2217               break;
2218           }
2219         }
2220
2221         object[name] = new RegExp(source, optionsArray.join(''));
2222         break;
2223       case BSON.BSON_DATA_LONG:
2224         // Unpack the low and high bits
2225         var lowBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2226         var highBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2227         // Create long object
2228         var long = new Long(lowBits, highBits); 
2229         // Promote the long if possible
2230         if(promoteLongs) {
2231           object[name] = long.lessThanOrEqual(JS_INT_MAX_LONG) && long.greaterThanOrEqual(JS_INT_MIN_LONG) ? long.toNumber() : long;
2232         } else {
2233           object[name] = long;
2234         }
2235         break;
2236       case BSON.BSON_DATA_SYMBOL:
2237         // Read the content of the field
2238         var stringSize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2239         // Add string to object
2240         object[name] = new Symbol(buffer.toString('utf8', index, index + stringSize - 1));
2241         // Update parse index position
2242         index = index + stringSize;
2243         break;
2244       case BSON.BSON_DATA_TIMESTAMP:
2245         // Unpack the low and high bits
2246         var lowBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2247         var highBits = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2248         // Set the object
2249         object[name] = new Timestamp(lowBits, highBits);
2250         break;
2251       case BSON.BSON_DATA_MIN_KEY:
2252         // Parse the object
2253         object[name] = new MinKey();
2254         break;
2255       case BSON.BSON_DATA_MAX_KEY:
2256         // Parse the object
2257         object[name] = new MaxKey();
2258         break;
2259       case BSON.BSON_DATA_CODE:
2260         // Read the content of the field
2261         var stringSize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2262         // Function string
2263         var functionString = supportsBuffer && Buffer.isBuffer(buffer) ? buffer.toString('utf8', index, index + stringSize - 1) : convertUint8ArrayToUtf8String(buffer, index, index + stringSize - 1);
2264
2265         // If we are evaluating the functions
2266         if(evalFunctions) {
2267           // Contains the value we are going to set
2268           var value = null;
2269           // If we have cache enabled let's look for the md5 of the function in the cache
2270           if(cacheFunctions) {
2271             var hash = cacheFunctionsCrc32 ? crc32(functionString) : functionString;
2272             // Got to do this to avoid V8 deoptimizing the call due to finding eval
2273             object[name] = isolateEvalWithHash(functionCache, hash, functionString, object);
2274           } else {
2275             // Set directly
2276             object[name] = isolateEval(functionString);
2277           }
2278         } else {
2279           object[name]  = new Code(functionString, {});
2280         }
2281
2282         // Update parse index position
2283         index = index + stringSize;
2284         break;
2285       case BSON.BSON_DATA_CODE_W_SCOPE:
2286         // Read the content of the field
2287         var totalSize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2288         var stringSize = buffer[index++] | buffer[index++] << 8 | buffer[index++] << 16 | buffer[index++] << 24;
2289         // Javascript function
2290         var functionString = supportsBuffer && Buffer.isBuffer(buffer) ? buffer.toString('utf8', index, index + stringSize - 1) : convertUint8ArrayToUtf8String(buffer, index, index + stringSize - 1);
2291         // Update parse index position
2292         index = index + stringSize;
2293         // Parse the element
2294         options['index'] = index;
2295         // Decode the size of the object document
2296         var objectSize = buffer[index] | buffer[index + 1] << 8 | buffer[index + 2] << 16 | buffer[index + 3] << 24;
2297         // Decode the scope object
2298         var scopeObject = BSON.deserialize(buffer, options, false);
2299         // Adjust the index
2300         index = index + objectSize;
2301
2302         // If we are evaluating the functions
2303         if(evalFunctions) {
2304           // Contains the value we are going to set
2305           var value = null;
2306           // If we have cache enabled let's look for the md5 of the function in the cache
2307           if(cacheFunctions) {
2308             var hash = cacheFunctionsCrc32 ? crc32(functionString) : functionString;
2309             // Got to do this to avoid V8 deoptimizing the call due to finding eval
2310             object[name] = isolateEvalWithHash(functionCache, hash, functionString, object);
2311           } else {
2312             // Set directly
2313             object[name] = isolateEval(functionString);
2314           }
2315
2316           // Set the scope on the object
2317           object[name].scope = scopeObject;
2318         } else {
2319           object[name]  = new Code(functionString, scopeObject);
2320         }
2321
2322         // Add string to object
2323         break;
2324     }
2325   }
2326
2327   // Check if we have a db ref object
2328   if(object['$id'] != null) object = new DBRef(object['$ref'], object['$id'], object['$db']);
2329
2330   // Return the final objects
2331   return object;
2332 }
2333
2334 /**
2335  * Check if key name is valid.
2336  *
2337  * @ignore
2338  * @api private
2339  */
2340 BSON.checkKey = function checkKey (key, dollarsAndDotsOk) {
2341   if (!key.length) return;
2342   // Check if we have a legal key for the object
2343   if (!!~key.indexOf("\x00")) {
2344     // The BSON spec doesn't allow keys with null bytes because keys are
2345     // null-terminated.
2346     throw Error("key " + key + " must not contain null bytes");
2347   }
2348   if (!dollarsAndDotsOk) {
2349     if('$' == key[0]) {
2350       throw Error("key " + key + " must not start with '$'");
2351     } else if (!!~key.indexOf('.')) {
2352       throw Error("key " + key + " must not contain '.'");
2353     }
2354   }
2355 };
2356
2357 /**
2358  * Deserialize data as BSON.
2359  *
2360  * Options
2361  *  - **evalFunctions** {Boolean, default:false}, evaluate functions in the BSON document scoped to the object deserialized.
2362  *  - **cacheFunctions** {Boolean, default:false}, cache evaluated functions for reuse.
2363  *  - **cacheFunctionsCrc32** {Boolean, default:false}, use a crc32 code for caching, otherwise use the string of the function.
2364  *
2365  * @param {Buffer} buffer the buffer containing the serialized set of BSON documents.
2366  * @param {Object} [options] additional options used for the deserialization.
2367  * @param {Boolean} [isArray] ignore used for recursive parsing.
2368  * @return {Object} returns the deserialized Javascript Object.
2369  * @api public
2370  */
2371 BSON.prototype.deserialize = function(data, options) {
2372   return BSON.deserialize(data, options);
2373 }
2374
2375 /**
2376  * Deserialize stream data as BSON documents.
2377  *
2378  * Options
2379  *  - **evalFunctions** {Boolean, default:false}, evaluate functions in the BSON document scoped to the object deserialized.
2380  *  - **cacheFunctions** {Boolean, default:false}, cache evaluated functions for reuse.
2381  *  - **cacheFunctionsCrc32** {Boolean, default:false}, use a crc32 code for caching, otherwise use the string of the function.
2382  *
2383  * @param {Buffer} data the buffer containing the serialized set of BSON documents.
2384  * @param {Number} startIndex the start index in the data Buffer where the deserialization is to start.
2385  * @param {Number} numberOfDocuments number of documents to deserialize.
2386  * @param {Array} documents an array where to store the deserialized documents.
2387  * @param {Number} docStartIndex the index in the documents array from where to start inserting documents.
2388  * @param {Object} [options] additional options used for the deserialization.
2389  * @return {Number} returns the next index in the buffer after deserialization **x** numbers of documents.
2390  * @api public
2391  */
2392 BSON.prototype.deserializeStream = function(data, startIndex, numberOfDocuments, documents, docStartIndex, options) {
2393   return BSON.deserializeStream(data, startIndex, numberOfDocuments, documents, docStartIndex, options);
2394 }
2395
2396 /**
2397  * Serialize a Javascript object.
2398  *
2399  * @param {Object} object the Javascript object to serialize.
2400  * @param {Boolean} checkKeys the serializer will check if keys are valid.
2401  * @param {Boolean} asBuffer return the serialized object as a Buffer object **(ignore)**.
2402  * @param {Boolean} serializeFunctions serialize the javascript functions **(default:false)**.
2403  * @return {Buffer} returns the Buffer object containing the serialized object.
2404  * @api public
2405  */
2406 BSON.prototype.serialize = function(object, checkKeys, asBuffer, serializeFunctions) {
2407   return BSON.serialize(object, checkKeys, asBuffer, serializeFunctions);
2408 }
2409
2410 /**
2411  * Calculate the bson size for a passed in Javascript object.
2412  *
2413  * @param {Object} object the Javascript object to calculate the BSON byte size for.
2414  * @param {Boolean} [serializeFunctions] serialize all functions in the object **(default:false)**.
2415  * @return {Number} returns the number of bytes the BSON object will take up.
2416  * @api public
2417  */
2418 BSON.prototype.calculateObjectSize = function(object, serializeFunctions) {
2419   return BSON.calculateObjectSize(object, serializeFunctions);
2420 }
2421
2422 /**
2423  * Serialize a Javascript object using a predefined Buffer and index into the buffer, useful when pre-allocating the space for serialization.
2424  *
2425  * @param {Object} object the Javascript object to serialize.
2426  * @param {Boolean} checkKeys the serializer will check if keys are valid.
2427  * @param {Buffer} buffer the Buffer you pre-allocated to store the serialized BSON object.
2428  * @param {Number} index the index in the buffer where we wish to start serializing into.
2429  * @param {Boolean} serializeFunctions serialize the javascript functions **(default:false)**.
2430  * @return {Number} returns the new write index in the Buffer.
2431  * @api public
2432  */
2433 BSON.prototype.serializeWithBufferAndIndex = function(object, checkKeys, buffer, startIndex, serializeFunctions) {
2434   return BSON.serializeWithBufferAndIndex(object, checkKeys, buffer, startIndex, serializeFunctions);
2435 }
2436
2437 /**
2438  * @ignore
2439  * @api private
2440  */
2441 exports.Code = Code;
2442 exports.Symbol = Symbol;
2443 exports.BSON = BSON;
2444 exports.DBRef = DBRef;
2445 exports.Binary = Binary;
2446 exports.ObjectID = ObjectID;
2447 exports.Long = Long;
2448 exports.Timestamp = Timestamp;
2449 exports.Double = Double;
2450 exports.MinKey = MinKey;
2451 exports.MaxKey = MaxKey;
2452
2453 }, 
2454
2455
2456
2457 'code': function(module, exports, global, require, undefined){
2458   /**
2459  * A class representation of the BSON Code type.
2460  *
2461  * @class Represents the BSON Code type.
2462  * @param {String|Function} code a string or function.
2463  * @param {Object} [scope] an optional scope for the function.
2464  * @return {Code}
2465  */
2466 function Code(code, scope) {
2467   if(!(this instanceof Code)) return new Code(code, scope);
2468   
2469   this._bsontype = 'Code';
2470   this.code = code;
2471   this.scope = scope == null ? {} : scope;
2472 };
2473
2474 /**
2475  * @ignore
2476  * @api private
2477  */
2478 Code.prototype.toJSON = function() {
2479   return {scope:this.scope, code:this.code};
2480 }
2481
2482 exports.Code = Code;
2483 }, 
2484
2485
2486
2487 'db_ref': function(module, exports, global, require, undefined){
2488   /**
2489  * A class representation of the BSON DBRef type.
2490  *
2491  * @class Represents the BSON DBRef type.
2492  * @param {String} namespace the collection name.
2493  * @param {ObjectID} oid the reference ObjectID.
2494  * @param {String} [db] optional db name, if omitted the reference is local to the current db.
2495  * @return {DBRef}
2496  */
2497 function DBRef(namespace, oid, db) {
2498   if(!(this instanceof DBRef)) return new DBRef(namespace, oid, db);
2499   
2500   this._bsontype = 'DBRef';
2501   this.namespace = namespace;
2502   this.oid = oid;
2503   this.db = db;
2504 };
2505
2506 /**
2507  * @ignore
2508  * @api private
2509  */
2510 DBRef.prototype.toJSON = function() {
2511   return {
2512     '$ref':this.namespace,
2513     '$id':this.oid,
2514     '$db':this.db == null ? '' : this.db
2515   };
2516 }
2517
2518 exports.DBRef = DBRef;
2519 }, 
2520
2521
2522
2523 'double': function(module, exports, global, require, undefined){
2524   /**
2525  * A class representation of the BSON Double type.
2526  *
2527  * @class Represents the BSON Double type.
2528  * @param {Number} value the number we want to represent as a double.
2529  * @return {Double}
2530  */
2531 function Double(value) {
2532   if(!(this instanceof Double)) return new Double(value);
2533   
2534   this._bsontype = 'Double';
2535   this.value = value;
2536 }
2537
2538 /**
2539  * Access the number value.
2540  *
2541  * @return {Number} returns the wrapped double number.
2542  * @api public
2543  */
2544 Double.prototype.valueOf = function() {
2545   return this.value;
2546 };
2547
2548 /**
2549  * @ignore
2550  * @api private
2551  */
2552 Double.prototype.toJSON = function() {
2553   return this.value;
2554 }
2555
2556 exports.Double = Double;
2557 }, 
2558
2559
2560
2561 'float_parser': function(module, exports, global, require, undefined){
2562   // Copyright (c) 2008, Fair Oaks Labs, Inc.
2563 // All rights reserved.
2564 // 
2565 // Redistribution and use in source and binary forms, with or without
2566 // modification, are permitted provided that the following conditions are met:
2567 // 
2568 //  * Redistributions of source code must retain the above copyright notice,
2569 //    this list of conditions and the following disclaimer.
2570 // 
2571 //  * Redistributions in binary form must reproduce the above copyright notice,
2572 //    this list of conditions and the following disclaimer in the documentation
2573 //    and/or other materials provided with the distribution.
2574 // 
2575 //  * Neither the name of Fair Oaks Labs, Inc. nor the names of its contributors
2576 //    may be used to endorse or promote products derived from this software
2577 //    without specific prior written permission.
2578 // 
2579 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
2580 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
2581 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
2582 // ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
2583 // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2584 // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2585 // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2586 // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2587 // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2588 // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
2589 // POSSIBILITY OF SUCH DAMAGE.
2590 //
2591 //
2592 // Modifications to writeIEEE754 to support negative zeroes made by Brian White
2593
2594 var readIEEE754 = function(buffer, offset, endian, mLen, nBytes) {
2595   var e, m,
2596       bBE = (endian === 'big'),
2597       eLen = nBytes * 8 - mLen - 1,
2598       eMax = (1 << eLen) - 1,
2599       eBias = eMax >> 1,
2600       nBits = -7,
2601       i = bBE ? 0 : (nBytes - 1),
2602       d = bBE ? 1 : -1,
2603       s = buffer[offset + i];
2604
2605   i += d;
2606
2607   e = s & ((1 << (-nBits)) - 1);
2608   s >>= (-nBits);
2609   nBits += eLen;
2610   for (; nBits > 0; e = e * 256 + buffer[offset + i], i += d, nBits -= 8);
2611
2612   m = e & ((1 << (-nBits)) - 1);
2613   e >>= (-nBits);
2614   nBits += mLen;
2615   for (; nBits > 0; m = m * 256 + buffer[offset + i], i += d, nBits -= 8);
2616
2617   if (e === 0) {
2618     e = 1 - eBias;
2619   } else if (e === eMax) {
2620     return m ? NaN : ((s ? -1 : 1) * Infinity);
2621   } else {
2622     m = m + Math.pow(2, mLen);
2623     e = e - eBias;
2624   }
2625   return (s ? -1 : 1) * m * Math.pow(2, e - mLen);
2626 };
2627
2628 var writeIEEE754 = function(buffer, value, offset, endian, mLen, nBytes) {
2629   var e, m, c,
2630       bBE = (endian === 'big'),
2631       eLen = nBytes * 8 - mLen - 1,
2632       eMax = (1 << eLen) - 1,
2633       eBias = eMax >> 1,
2634       rt = (mLen === 23 ? Math.pow(2, -24) - Math.pow(2, -77) : 0),
2635       i = bBE ? (nBytes-1) : 0,
2636       d = bBE ? -1 : 1,
2637       s = value < 0 || (value === 0 && 1 / value < 0) ? 1 : 0;
2638
2639   value = Math.abs(value);
2640
2641   if (isNaN(value) || value === Infinity) {
2642     m = isNaN(value) ? 1 : 0;
2643     e = eMax;
2644   } else {
2645     e = Math.floor(Math.log(value) / Math.LN2);
2646     if (value * (c = Math.pow(2, -e)) < 1) {
2647       e--;
2648       c *= 2;
2649     }
2650     if (e+eBias >= 1) {
2651       value += rt / c;
2652     } else {
2653       value += rt * Math.pow(2, 1 - eBias);
2654     }
2655     if (value * c >= 2) {
2656       e++;
2657       c /= 2;
2658     }
2659
2660     if (e + eBias >= eMax) {
2661       m = 0;
2662       e = eMax;
2663     } else if (e + eBias >= 1) {
2664       m = (value * c - 1) * Math.pow(2, mLen);
2665       e = e + eBias;
2666     } else {
2667       m = value * Math.pow(2, eBias - 1) * Math.pow(2, mLen);
2668       e = 0;
2669     }
2670   }
2671
2672   for (; mLen >= 8; buffer[offset + i] = m & 0xff, i += d, m /= 256, mLen -= 8);
2673
2674   e = (e << mLen) | m;
2675   eLen += mLen;
2676   for (; eLen > 0; buffer[offset + i] = e & 0xff, i += d, e /= 256, eLen -= 8);
2677
2678   buffer[offset + i - d] |= s * 128;
2679 };
2680
2681 exports.readIEEE754 = readIEEE754;
2682 exports.writeIEEE754 = writeIEEE754;
2683 }, 
2684
2685
2686
2687 'index': function(module, exports, global, require, undefined){
2688   try {
2689   exports.BSONPure = require('./bson');
2690   exports.BSONNative = require('../../ext');
2691 } catch(err) {
2692   // do nothing
2693 }
2694
2695 [ './binary_parser'
2696   , './binary'
2697   , './code'
2698   , './db_ref'
2699   , './double'
2700   , './max_key'
2701   , './min_key'
2702   , './objectid'
2703   , './symbol'
2704   , './timestamp'
2705   , './long'].forEach(function (path) {
2706         var module = require('./' + path);
2707         for (var i in module) {
2708                 exports[i] = module[i];
2709     }
2710 });
2711
2712 // Exports all the classes for the NATIVE JS BSON Parser
2713 exports.native = function() {
2714   var classes = {};
2715   // Map all the classes
2716   [ './binary_parser'
2717     , './binary'
2718     , './code'
2719     , './db_ref'
2720     , './double'
2721     , './max_key'
2722     , './min_key'
2723     , './objectid'
2724     , './symbol'
2725     , './timestamp'
2726     , './long'
2727     , '../../ext'
2728 ].forEach(function (path) {
2729         var module = require('./' + path);
2730         for (var i in module) {
2731                 classes[i] = module[i];
2732       }
2733   });
2734   // Return classes list
2735   return classes;
2736 }
2737
2738 // Exports all the classes for the PURE JS BSON Parser
2739 exports.pure = function() {
2740   var classes = {};
2741   // Map all the classes
2742   [ './binary_parser'
2743     , './binary'
2744     , './code'
2745     , './db_ref'
2746     , './double'
2747     , './max_key'
2748     , './min_key'
2749     , './objectid'
2750     , './symbol'
2751     , './timestamp'
2752     , './long'
2753     , '././bson'].forEach(function (path) {
2754         var module = require('./' + path);
2755         for (var i in module) {
2756                 classes[i] = module[i];
2757       }
2758   });
2759   // Return classes list
2760   return classes;
2761 }
2762
2763 }, 
2764
2765
2766
2767 'long': function(module, exports, global, require, undefined){
2768   // Licensed under the Apache License, Version 2.0 (the "License");
2769 // you may not use this file except in compliance with the License.
2770 // You may obtain a copy of the License at
2771 //
2772 //     http://www.apache.org/licenses/LICENSE-2.0
2773 //
2774 // Unless required by applicable law or agreed to in writing, software
2775 // distributed under the License is distributed on an "AS IS" BASIS,
2776 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
2777 // See the License for the specific language governing permissions and
2778 // limitations under the License.
2779 //
2780 // Copyright 2009 Google Inc. All Rights Reserved
2781
2782 /**
2783  * Defines a Long class for representing a 64-bit two's-complement
2784  * integer value, which faithfully simulates the behavior of a Java "Long". This
2785  * implementation is derived from LongLib in GWT.
2786  *
2787  * Constructs a 64-bit two's-complement integer, given its low and high 32-bit
2788  * values as *signed* integers.  See the from* functions below for more
2789  * convenient ways of constructing Longs.
2790  *
2791  * The internal representation of a Long is the two given signed, 32-bit values.
2792  * We use 32-bit pieces because these are the size of integers on which
2793  * Javascript performs bit-operations.  For operations like addition and
2794  * multiplication, we split each number into 16-bit pieces, which can easily be
2795  * multiplied within Javascript's floating-point representation without overflow
2796  * or change in sign.
2797  *
2798  * In the algorithms below, we frequently reduce the negative case to the
2799  * positive case by negating the input(s) and then post-processing the result.
2800  * Note that we must ALWAYS check specially whether those values are MIN_VALUE
2801  * (-2^63) because -MIN_VALUE == MIN_VALUE (since 2^63 cannot be represented as
2802  * a positive number, it overflows back into a negative).  Not handling this
2803  * case would often result in infinite recursion.
2804  *
2805  * @class Represents the BSON Long type.
2806  * @param {Number} low  the low (signed) 32 bits of the Long.
2807  * @param {Number} high the high (signed) 32 bits of the Long.
2808  */
2809 function Long(low, high) {
2810   if(!(this instanceof Long)) return new Long(low, high);
2811   
2812   this._bsontype = 'Long';
2813   /**
2814    * @type {number}
2815    * @api private
2816    */
2817   this.low_ = low | 0;  // force into 32 signed bits.
2818
2819   /**
2820    * @type {number}
2821    * @api private
2822    */
2823   this.high_ = high | 0;  // force into 32 signed bits.
2824 };
2825
2826 /**
2827  * Return the int value.
2828  *
2829  * @return {Number} the value, assuming it is a 32-bit integer.
2830  * @api public
2831  */
2832 Long.prototype.toInt = function() {
2833   return this.low_;
2834 };
2835
2836 /**
2837  * Return the Number value.
2838  *
2839  * @return {Number} the closest floating-point representation to this value.
2840  * @api public
2841  */
2842 Long.prototype.toNumber = function() {
2843   return this.high_ * Long.TWO_PWR_32_DBL_ +
2844          this.getLowBitsUnsigned();
2845 };
2846
2847 /**
2848  * Return the JSON value.
2849  *
2850  * @return {String} the JSON representation.
2851  * @api public
2852  */
2853 Long.prototype.toJSON = function() {
2854   return this.toString();
2855 }
2856
2857 /**
2858  * Return the String value.
2859  *
2860  * @param {Number} [opt_radix] the radix in which the text should be written.
2861  * @return {String} the textual representation of this value.
2862  * @api public
2863  */
2864 Long.prototype.toString = function(opt_radix) {
2865   var radix = opt_radix || 10;
2866   if (radix < 2 || 36 < radix) {
2867     throw Error('radix out of range: ' + radix);
2868   }
2869
2870   if (this.isZero()) {
2871     return '0';
2872   }
2873
2874   if (this.isNegative()) {
2875     if (this.equals(Long.MIN_VALUE)) {
2876       // We need to change the Long value before it can be negated, so we remove
2877       // the bottom-most digit in this base and then recurse to do the rest.
2878       var radixLong = Long.fromNumber(radix);
2879       var div = this.div(radixLong);
2880       var rem = div.multiply(radixLong).subtract(this);
2881       return div.toString(radix) + rem.toInt().toString(radix);
2882     } else {
2883       return '-' + this.negate().toString(radix);
2884     }
2885   }
2886
2887   // Do several (6) digits each time through the loop, so as to
2888   // minimize the calls to the very expensive emulated div.
2889   var radixToPower = Long.fromNumber(Math.pow(radix, 6));
2890
2891   var rem = this;
2892   var result = '';
2893   while (true) {
2894     var remDiv = rem.div(radixToPower);
2895     var intval = rem.subtract(remDiv.multiply(radixToPower)).toInt();
2896     var digits = intval.toString(radix);
2897
2898     rem = remDiv;
2899     if (rem.isZero()) {
2900       return digits + result;
2901     } else {
2902       while (digits.length < 6) {
2903         digits = '0' + digits;
2904       }
2905       result = '' + digits + result;
2906     }
2907   }
2908 };
2909
2910 /**
2911  * Return the high 32-bits value.
2912  *
2913  * @return {Number} the high 32-bits as a signed value.
2914  * @api public
2915  */
2916 Long.prototype.getHighBits = function() {
2917   return this.high_;
2918 };
2919
2920 /**
2921  * Return the low 32-bits value.
2922  *
2923  * @return {Number} the low 32-bits as a signed value.
2924  * @api public
2925  */
2926 Long.prototype.getLowBits = function() {
2927   return this.low_;
2928 };
2929
2930 /**
2931  * Return the low unsigned 32-bits value.
2932  *
2933  * @return {Number} the low 32-bits as an unsigned value.
2934  * @api public
2935  */
2936 Long.prototype.getLowBitsUnsigned = function() {
2937   return (this.low_ >= 0) ?
2938       this.low_ : Long.TWO_PWR_32_DBL_ + this.low_;
2939 };
2940
2941 /**
2942  * Returns the number of bits needed to represent the absolute value of this Long.
2943  *
2944  * @return {Number} Returns the number of bits needed to represent the absolute value of this Long.
2945  * @api public
2946  */
2947 Long.prototype.getNumBitsAbs = function() {
2948   if (this.isNegative()) {
2949     if (this.equals(Long.MIN_VALUE)) {
2950       return 64;
2951     } else {
2952       return this.negate().getNumBitsAbs();
2953     }
2954   } else {
2955     var val = this.high_ != 0 ? this.high_ : this.low_;
2956     for (var bit = 31; bit > 0; bit--) {
2957       if ((val & (1 << bit)) != 0) {
2958         break;
2959       }
2960     }
2961     return this.high_ != 0 ? bit + 33 : bit + 1;
2962   }
2963 };
2964
2965 /**
2966  * Return whether this value is zero.
2967  *
2968  * @return {Boolean} whether this value is zero.
2969  * @api public
2970  */
2971 Long.prototype.isZero = function() {
2972   return this.high_ == 0 && this.low_ == 0;
2973 };
2974
2975 /**
2976  * Return whether this value is negative.
2977  *
2978  * @return {Boolean} whether this value is negative.
2979  * @api public
2980  */
2981 Long.prototype.isNegative = function() {
2982   return this.high_ < 0;
2983 };
2984
2985 /**
2986  * Return whether this value is odd.
2987  *
2988  * @return {Boolean} whether this value is odd.
2989  * @api public
2990  */
2991 Long.prototype.isOdd = function() {
2992   return (this.low_ & 1) == 1;
2993 };
2994
2995 /**
2996  * Return whether this Long equals the other
2997  *
2998  * @param {Long} other Long to compare against.
2999  * @return {Boolean} whether this Long equals the other
3000  * @api public
3001  */
3002 Long.prototype.equals = function(other) {
3003   return (this.high_ == other.high_) && (this.low_ == other.low_);
3004 };
3005
3006 /**
3007  * Return whether this Long does not equal the other.
3008  *
3009  * @param {Long} other Long to compare against.
3010  * @return {Boolean} whether this Long does not equal the other.
3011  * @api public
3012  */
3013 Long.prototype.notEquals = function(other) {
3014   return (this.high_ != other.high_) || (this.low_ != other.low_);
3015 };
3016
3017 /**
3018  * Return whether this Long is less than the other.
3019  *
3020  * @param {Long} other Long to compare against.
3021  * @return {Boolean} whether this Long is less than the other.
3022  * @api public
3023  */
3024 Long.prototype.lessThan = function(other) {
3025   return this.compare(other) < 0;
3026 };
3027
3028 /**
3029  * Return whether this Long is less than or equal to the other.
3030  *
3031  * @param {Long} other Long to compare against.
3032  * @return {Boolean} whether this Long is less than or equal to the other.
3033  * @api public
3034  */
3035 Long.prototype.lessThanOrEqual = function(other) {
3036   return this.compare(other) <= 0;
3037 };
3038
3039 /**
3040  * Return whether this Long is greater than the other.
3041  *
3042  * @param {Long} other Long to compare against.
3043  * @return {Boolean} whether this Long is greater than the other.
3044  * @api public
3045  */
3046 Long.prototype.greaterThan = function(other) {
3047   return this.compare(other) > 0;
3048 };
3049
3050 /**
3051  * Return whether this Long is greater than or equal to the other.
3052  *
3053  * @param {Long} other Long to compare against.
3054  * @return {Boolean} whether this Long is greater than or equal to the other.
3055  * @api public
3056  */
3057 Long.prototype.greaterThanOrEqual = function(other) {
3058   return this.compare(other) >= 0;
3059 };
3060
3061 /**
3062  * Compares this Long with the given one.
3063  *
3064  * @param {Long} other Long to compare against.
3065  * @return {Boolean} 0 if they are the same, 1 if the this is greater, and -1 if the given one is greater.
3066  * @api public
3067  */
3068 Long.prototype.compare = function(other) {
3069   if (this.equals(other)) {
3070     return 0;
3071   }
3072
3073   var thisNeg = this.isNegative();
3074   var otherNeg = other.isNegative();
3075   if (thisNeg && !otherNeg) {
3076     return -1;
3077   }
3078   if (!thisNeg && otherNeg) {
3079     return 1;
3080   }
3081
3082   // at this point, the signs are the same, so subtraction will not overflow
3083   if (this.subtract(other).isNegative()) {
3084     return -1;
3085   } else {
3086     return 1;
3087   }
3088 };
3089
3090 /**
3091  * The negation of this value.
3092  *
3093  * @return {Long} the negation of this value.
3094  * @api public
3095  */
3096 Long.prototype.negate = function() {
3097   if (this.equals(Long.MIN_VALUE)) {
3098     return Long.MIN_VALUE;
3099   } else {
3100     return this.not().add(Long.ONE);
3101   }
3102 };
3103
3104 /**
3105  * Returns the sum of this and the given Long.
3106  *
3107  * @param {Long} other Long to add to this one.
3108  * @return {Long} the sum of this and the given Long.
3109  * @api public
3110  */
3111 Long.prototype.add = function(other) {
3112   // Divide each number into 4 chunks of 16 bits, and then sum the chunks.
3113
3114   var a48 = this.high_ >>> 16;
3115   var a32 = this.high_ & 0xFFFF;
3116   var a16 = this.low_ >>> 16;
3117   var a00 = this.low_ & 0xFFFF;
3118
3119   var b48 = other.high_ >>> 16;
3120   var b32 = other.high_ & 0xFFFF;
3121   var b16 = other.low_ >>> 16;
3122   var b00 = other.low_ & 0xFFFF;
3123
3124   var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
3125   c00 += a00 + b00;
3126   c16 += c00 >>> 16;
3127   c00 &= 0xFFFF;
3128   c16 += a16 + b16;
3129   c32 += c16 >>> 16;
3130   c16 &= 0xFFFF;
3131   c32 += a32 + b32;
3132   c48 += c32 >>> 16;
3133   c32 &= 0xFFFF;
3134   c48 += a48 + b48;
3135   c48 &= 0xFFFF;
3136   return Long.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
3137 };
3138
3139 /**
3140  * Returns the difference of this and the given Long.
3141  *
3142  * @param {Long} other Long to subtract from this.
3143  * @return {Long} the difference of this and the given Long.
3144  * @api public
3145  */
3146 Long.prototype.subtract = function(other) {
3147   return this.add(other.negate());
3148 };
3149
3150 /**
3151  * Returns the product of this and the given Long.
3152  *
3153  * @param {Long} other Long to multiply with this.
3154  * @return {Long} the product of this and the other.
3155  * @api public
3156  */
3157 Long.prototype.multiply = function(other) {
3158   if (this.isZero()) {
3159     return Long.ZERO;
3160   } else if (other.isZero()) {
3161     return Long.ZERO;
3162   }
3163
3164   if (this.equals(Long.MIN_VALUE)) {
3165     return other.isOdd() ? Long.MIN_VALUE : Long.ZERO;
3166   } else if (other.equals(Long.MIN_VALUE)) {
3167     return this.isOdd() ? Long.MIN_VALUE : Long.ZERO;
3168   }
3169
3170   if (this.isNegative()) {
3171     if (other.isNegative()) {
3172       return this.negate().multiply(other.negate());
3173     } else {
3174       return this.negate().multiply(other).negate();
3175     }
3176   } else if (other.isNegative()) {
3177     return this.multiply(other.negate()).negate();
3178   }
3179
3180   // If both Longs are small, use float multiplication
3181   if (this.lessThan(Long.TWO_PWR_24_) &&
3182       other.lessThan(Long.TWO_PWR_24_)) {
3183     return Long.fromNumber(this.toNumber() * other.toNumber());
3184   }
3185
3186   // Divide each Long into 4 chunks of 16 bits, and then add up 4x4 products.
3187   // We can skip products that would overflow.
3188
3189   var a48 = this.high_ >>> 16;
3190   var a32 = this.high_ & 0xFFFF;
3191   var a16 = this.low_ >>> 16;
3192   var a00 = this.low_ & 0xFFFF;
3193
3194   var b48 = other.high_ >>> 16;
3195   var b32 = other.high_ & 0xFFFF;
3196   var b16 = other.low_ >>> 16;
3197   var b00 = other.low_ & 0xFFFF;
3198
3199   var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
3200   c00 += a00 * b00;
3201   c16 += c00 >>> 16;
3202   c00 &= 0xFFFF;
3203   c16 += a16 * b00;
3204   c32 += c16 >>> 16;
3205   c16 &= 0xFFFF;
3206   c16 += a00 * b16;
3207   c32 += c16 >>> 16;
3208   c16 &= 0xFFFF;
3209   c32 += a32 * b00;
3210   c48 += c32 >>> 16;
3211   c32 &= 0xFFFF;
3212   c32 += a16 * b16;
3213   c48 += c32 >>> 16;
3214   c32 &= 0xFFFF;
3215   c32 += a00 * b32;
3216   c48 += c32 >>> 16;
3217   c32 &= 0xFFFF;
3218   c48 += a48 * b00 + a32 * b16 + a16 * b32 + a00 * b48;
3219   c48 &= 0xFFFF;
3220   return Long.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
3221 };
3222
3223 /**
3224  * Returns this Long divided by the given one.
3225  *
3226  * @param {Long} other Long by which to divide.
3227  * @return {Long} this Long divided by the given one.
3228  * @api public
3229  */
3230 Long.prototype.div = function(other) {
3231   if (other.isZero()) {
3232     throw Error('division by zero');
3233   } else if (this.isZero()) {
3234     return Long.ZERO;
3235   }
3236
3237   if (this.equals(Long.MIN_VALUE)) {
3238     if (other.equals(Long.ONE) ||
3239         other.equals(Long.NEG_ONE)) {
3240       return Long.MIN_VALUE;  // recall that -MIN_VALUE == MIN_VALUE
3241     } else if (other.equals(Long.MIN_VALUE)) {
3242       return Long.ONE;
3243     } else {
3244       // At this point, we have |other| >= 2, so |this/other| < |MIN_VALUE|.
3245       var halfThis = this.shiftRight(1);
3246       var approx = halfThis.div(other).shiftLeft(1);
3247       if (approx.equals(Long.ZERO)) {
3248         return other.isNegative() ? Long.ONE : Long.NEG_ONE;
3249       } else {
3250         var rem = this.subtract(other.multiply(approx));
3251         var result = approx.add(rem.div(other));
3252         return result;
3253       }
3254     }
3255   } else if (other.equals(Long.MIN_VALUE)) {
3256     return Long.ZERO;
3257   }
3258
3259   if (this.isNegative()) {
3260     if (other.isNegative()) {
3261       return this.negate().div(other.negate());
3262     } else {
3263       return this.negate().div(other).negate();
3264     }
3265   } else if (other.isNegative()) {
3266     return this.div(other.negate()).negate();
3267   }
3268
3269   // Repeat the following until the remainder is less than other:  find a
3270   // floating-point that approximates remainder / other *from below*, add this
3271   // into the result, and subtract it from the remainder.  It is critical that
3272   // the approximate value is less than or equal to the real value so that the
3273   // remainder never becomes negative.
3274   var res = Long.ZERO;
3275   var rem = this;
3276   while (rem.greaterThanOrEqual(other)) {
3277     // Approximate the result of division. This may be a little greater or
3278     // smaller than the actual value.
3279     var approx = Math.max(1, Math.floor(rem.toNumber() / other.toNumber()));
3280
3281     // We will tweak the approximate result by changing it in the 48-th digit or
3282     // the smallest non-fractional digit, whichever is larger.
3283     var log2 = Math.ceil(Math.log(approx) / Math.LN2);
3284     var delta = (log2 <= 48) ? 1 : Math.pow(2, log2 - 48);
3285
3286     // Decrease the approximation until it is smaller than the remainder.  Note
3287     // that if it is too large, the product overflows and is negative.
3288     var approxRes = Long.fromNumber(approx);
3289     var approxRem = approxRes.multiply(other);
3290     while (approxRem.isNegative() || approxRem.greaterThan(rem)) {
3291       approx -= delta;
3292       approxRes = Long.fromNumber(approx);
3293       approxRem = approxRes.multiply(other);
3294     }
3295
3296     // We know the answer can't be zero... and actually, zero would cause
3297     // infinite recursion since we would make no progress.
3298     if (approxRes.isZero()) {
3299       approxRes = Long.ONE;
3300     }
3301
3302     res = res.add(approxRes);
3303     rem = rem.subtract(approxRem);
3304   }
3305   return res;
3306 };
3307
3308 /**
3309  * Returns this Long modulo the given one.
3310  *
3311  * @param {Long} other Long by which to mod.
3312  * @return {Long} this Long modulo the given one.
3313  * @api public
3314  */
3315 Long.prototype.modulo = function(other) {
3316   return this.subtract(this.div(other).multiply(other));
3317 };
3318
3319 /**
3320  * The bitwise-NOT of this value.
3321  *
3322  * @return {Long} the bitwise-NOT of this value.
3323  * @api public
3324  */
3325 Long.prototype.not = function() {
3326   return Long.fromBits(~this.low_, ~this.high_);
3327 };
3328
3329 /**
3330  * Returns the bitwise-AND of this Long and the given one.
3331  *
3332  * @param {Long} other the Long with which to AND.
3333  * @return {Long} the bitwise-AND of this and the other.
3334  * @api public
3335  */
3336 Long.prototype.and = function(other) {
3337   return Long.fromBits(this.low_ & other.low_, this.high_ & other.high_);
3338 };
3339
3340 /**
3341  * Returns the bitwise-OR of this Long and the given one.
3342  *
3343  * @param {Long} other the Long with which to OR.
3344  * @return {Long} the bitwise-OR of this and the other.
3345  * @api public
3346  */
3347 Long.prototype.or = function(other) {
3348   return Long.fromBits(this.low_ | other.low_, this.high_ | other.high_);
3349 };
3350
3351 /**
3352  * Returns the bitwise-XOR of this Long and the given one.
3353  *
3354  * @param {Long} other the Long with which to XOR.
3355  * @return {Long} the bitwise-XOR of this and the other.
3356  * @api public
3357  */
3358 Long.prototype.xor = function(other) {
3359   return Long.fromBits(this.low_ ^ other.low_, this.high_ ^ other.high_);
3360 };
3361
3362 /**
3363  * Returns this Long with bits shifted to the left by the given amount.
3364  *
3365  * @param {Number} numBits the number of bits by which to shift.
3366  * @return {Long} this shifted to the left by the given amount.
3367  * @api public
3368  */
3369 Long.prototype.shiftLeft = function(numBits) {
3370   numBits &= 63;
3371   if (numBits == 0) {
3372     return this;
3373   } else {
3374     var low = this.low_;
3375     if (numBits < 32) {
3376       var high = this.high_;
3377       return Long.fromBits(
3378                  low << numBits,
3379                  (high << numBits) | (low >>> (32 - numBits)));
3380     } else {
3381       return Long.fromBits(0, low << (numBits - 32));
3382     }
3383   }
3384 };
3385
3386 /**
3387  * Returns this Long with bits shifted to the right by the given amount.
3388  *
3389  * @param {Number} numBits the number of bits by which to shift.
3390  * @return {Long} this shifted to the right by the given amount.
3391  * @api public
3392  */
3393 Long.prototype.shiftRight = function(numBits) {
3394   numBits &= 63;
3395   if (numBits == 0) {
3396     return this;
3397   } else {
3398     var high = this.high_;
3399     if (numBits < 32) {
3400       var low = this.low_;
3401       return Long.fromBits(
3402                  (low >>> numBits) | (high << (32 - numBits)),
3403                  high >> numBits);
3404     } else {
3405       return Long.fromBits(
3406                  high >> (numBits - 32),
3407                  high >= 0 ? 0 : -1);
3408     }
3409   }
3410 };
3411
3412 /**
3413  * Returns this Long with bits shifted to the right by the given amount, with the new top bits matching the current sign bit.
3414  *
3415  * @param {Number} numBits the number of bits by which to shift.
3416  * @return {Long} this shifted to the right by the given amount, with zeros placed into the new leading bits.
3417  * @api public
3418  */
3419 Long.prototype.shiftRightUnsigned = function(numBits) {
3420   numBits &= 63;
3421   if (numBits == 0) {
3422     return this;
3423   } else {
3424     var high = this.high_;
3425     if (numBits < 32) {
3426       var low = this.low_;
3427       return Long.fromBits(
3428                  (low >>> numBits) | (high << (32 - numBits)),
3429                  high >>> numBits);
3430     } else if (numBits == 32) {
3431       return Long.fromBits(high, 0);
3432     } else {
3433       return Long.fromBits(high >>> (numBits - 32), 0);
3434     }
3435   }
3436 };
3437
3438 /**
3439  * Returns a Long representing the given (32-bit) integer value.
3440  *
3441  * @param {Number} value the 32-bit integer in question.
3442  * @return {Long} the corresponding Long value.
3443  * @api public
3444  */
3445 Long.fromInt = function(value) {
3446   if (-128 <= value && value < 128) {
3447     var cachedObj = Long.INT_CACHE_[value];
3448     if (cachedObj) {
3449       return cachedObj;
3450     }
3451   }
3452
3453   var obj = new Long(value | 0, value < 0 ? -1 : 0);
3454   if (-128 <= value && value < 128) {
3455     Long.INT_CACHE_[value] = obj;
3456   }
3457   return obj;
3458 };
3459
3460 /**
3461  * Returns a Long representing the given value, provided that it is a finite number. Otherwise, zero is returned.
3462  *
3463  * @param {Number} value the number in question.
3464  * @return {Long} the corresponding Long value.
3465  * @api public
3466  */
3467 Long.fromNumber = function(value) {
3468   if (isNaN(value) || !isFinite(value)) {
3469     return Long.ZERO;
3470   } else if (value <= -Long.TWO_PWR_63_DBL_) {
3471     return Long.MIN_VALUE;
3472   } else if (value + 1 >= Long.TWO_PWR_63_DBL_) {
3473     return Long.MAX_VALUE;
3474   } else if (value < 0) {
3475     return Long.fromNumber(-value).negate();
3476   } else {
3477     return new Long(
3478                (value % Long.TWO_PWR_32_DBL_) | 0,
3479                (value / Long.TWO_PWR_32_DBL_) | 0);
3480   }
3481 };
3482
3483 /**
3484  * Returns a Long representing the 64-bit integer that comes by concatenating the given high and low bits. Each is assumed to use 32 bits.
3485  *
3486  * @param {Number} lowBits the low 32-bits.
3487  * @param {Number} highBits the high 32-bits.
3488  * @return {Long} the corresponding Long value.
3489  * @api public
3490  */
3491 Long.fromBits = function(lowBits, highBits) {
3492   return new Long(lowBits, highBits);
3493 };
3494
3495 /**
3496  * Returns a Long representation of the given string, written using the given radix.
3497  *
3498  * @param {String} str the textual representation of the Long.
3499  * @param {Number} opt_radix the radix in which the text is written.
3500  * @return {Long} the corresponding Long value.
3501  * @api public
3502  */
3503 Long.fromString = function(str, opt_radix) {
3504   if (str.length == 0) {
3505     throw Error('number format error: empty string');
3506   }
3507
3508   var radix = opt_radix || 10;
3509   if (radix < 2 || 36 < radix) {
3510     throw Error('radix out of range: ' + radix);
3511   }
3512
3513   if (str.charAt(0) == '-') {
3514     return Long.fromString(str.substring(1), radix).negate();
3515   } else if (str.indexOf('-') >= 0) {
3516     throw Error('number format error: interior "-" character: ' + str);
3517   }
3518
3519   // Do several (8) digits each time through the loop, so as to
3520   // minimize the calls to the very expensive emulated div.
3521   var radixToPower = Long.fromNumber(Math.pow(radix, 8));
3522
3523   var result = Long.ZERO;
3524   for (var i = 0; i < str.length; i += 8) {
3525     var size = Math.min(8, str.length - i);
3526     var value = parseInt(str.substring(i, i + size), radix);
3527     if (size < 8) {
3528       var power = Long.fromNumber(Math.pow(radix, size));
3529       result = result.multiply(power).add(Long.fromNumber(value));
3530     } else {
3531       result = result.multiply(radixToPower);
3532       result = result.add(Long.fromNumber(value));
3533     }
3534   }
3535   return result;
3536 };
3537
3538 // NOTE: Common constant values ZERO, ONE, NEG_ONE, etc. are defined below the
3539 // from* methods on which they depend.
3540
3541
3542 /**
3543  * A cache of the Long representations of small integer values.
3544  * @type {Object}
3545  * @api private
3546  */
3547 Long.INT_CACHE_ = {};
3548
3549 // NOTE: the compiler should inline these constant values below and then remove
3550 // these variables, so there should be no runtime penalty for these.
3551
3552 /**
3553  * Number used repeated below in calculations.  This must appear before the
3554  * first call to any from* function below.
3555  * @type {number}
3556  * @api private
3557  */
3558 Long.TWO_PWR_16_DBL_ = 1 << 16;
3559
3560 /**
3561  * @type {number}
3562  * @api private
3563  */
3564 Long.TWO_PWR_24_DBL_ = 1 << 24;
3565
3566 /**
3567  * @type {number}
3568  * @api private
3569  */
3570 Long.TWO_PWR_32_DBL_ = Long.TWO_PWR_16_DBL_ * Long.TWO_PWR_16_DBL_;
3571
3572 /**
3573  * @type {number}
3574  * @api private
3575  */
3576 Long.TWO_PWR_31_DBL_ = Long.TWO_PWR_32_DBL_ / 2;
3577
3578 /**
3579  * @type {number}
3580  * @api private
3581  */
3582 Long.TWO_PWR_48_DBL_ = Long.TWO_PWR_32_DBL_ * Long.TWO_PWR_16_DBL_;
3583
3584 /**
3585  * @type {number}
3586  * @api private
3587  */
3588 Long.TWO_PWR_64_DBL_ = Long.TWO_PWR_32_DBL_ * Long.TWO_PWR_32_DBL_;
3589
3590 /**
3591  * @type {number}
3592  * @api private
3593  */
3594 Long.TWO_PWR_63_DBL_ = Long.TWO_PWR_64_DBL_ / 2;
3595
3596 /** @type {Long} */
3597 Long.ZERO = Long.fromInt(0);
3598
3599 /** @type {Long} */
3600 Long.ONE = Long.fromInt(1);
3601
3602 /** @type {Long} */
3603 Long.NEG_ONE = Long.fromInt(-1);
3604
3605 /** @type {Long} */
3606 Long.MAX_VALUE =
3607     Long.fromBits(0xFFFFFFFF | 0, 0x7FFFFFFF | 0);
3608
3609 /** @type {Long} */
3610 Long.MIN_VALUE = Long.fromBits(0, 0x80000000 | 0);
3611
3612 /**
3613  * @type {Long}
3614  * @api private
3615  */
3616 Long.TWO_PWR_24_ = Long.fromInt(1 << 24);
3617
3618 /**
3619  * Expose.
3620  */
3621 exports.Long = Long;
3622 }, 
3623
3624
3625
3626 'max_key': function(module, exports, global, require, undefined){
3627   /**
3628  * A class representation of the BSON MaxKey type.
3629  *
3630  * @class Represents the BSON MaxKey type.
3631  * @return {MaxKey}
3632  */
3633 function MaxKey() {
3634   if(!(this instanceof MaxKey)) return new MaxKey();
3635   
3636   this._bsontype = 'MaxKey';  
3637 }
3638
3639 exports.MaxKey = MaxKey;
3640 }, 
3641
3642
3643
3644 'min_key': function(module, exports, global, require, undefined){
3645   /**
3646  * A class representation of the BSON MinKey type.
3647  *
3648  * @class Represents the BSON MinKey type.
3649  * @return {MinKey}
3650  */
3651 function MinKey() {
3652   if(!(this instanceof MinKey)) return new MinKey();
3653   
3654   this._bsontype = 'MinKey';
3655 }
3656
3657 exports.MinKey = MinKey;
3658 }, 
3659
3660
3661
3662 'objectid': function(module, exports, global, require, undefined){
3663   /**
3664  * Module dependencies.
3665  */
3666 var BinaryParser = require('./binary_parser').BinaryParser;
3667
3668 /**
3669  * Machine id.
3670  *
3671  * Create a random 3-byte value (i.e. unique for this
3672  * process). Other drivers use a md5 of the machine id here, but
3673  * that would mean an asyc call to gethostname, so we don't bother.
3674  */
3675 var MACHINE_ID = parseInt(Math.random() * 0xFFFFFF, 10);
3676
3677 // Regular expression that checks for hex value
3678 var checkForHexRegExp = new RegExp("^[0-9a-fA-F]{24}$");
3679
3680 /**
3681 * Create a new ObjectID instance
3682 *
3683 * @class Represents the BSON ObjectID type
3684 * @param {String|Number} id Can be a 24 byte hex string, 12 byte binary string or a Number.
3685 * @return {Object} instance of ObjectID.
3686 */
3687 var ObjectID = function ObjectID(id, _hex) {
3688   if(!(this instanceof ObjectID)) return new ObjectID(id, _hex);
3689
3690   this._bsontype = 'ObjectID';
3691   var __id = null;
3692
3693   // Throw an error if it's not a valid setup
3694   if(id != null && 'number' != typeof id && (id.length != 12 && id.length != 24))
3695     throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
3696
3697   // Generate id based on the input
3698   if(id == null || typeof id == 'number') {
3699     // convert to 12 byte binary string
3700     this.id = this.generate(id);
3701   } else if(id != null && id.length === 12) {
3702     // assume 12 byte string
3703     this.id = id;
3704   } else if(checkForHexRegExp.test(id)) {
3705     return ObjectID.createFromHexString(id);
3706   } else {
3707     throw new Error("Value passed in is not a valid 24 character hex string");
3708   }
3709
3710   if(ObjectID.cacheHexString) this.__id = this.toHexString();
3711 };
3712
3713 // Allow usage of ObjectId as well as ObjectID
3714 var ObjectId = ObjectID;
3715
3716 // Precomputed hex table enables speedy hex string conversion
3717 var hexTable = [];
3718 for (var i = 0; i < 256; i++) {
3719   hexTable[i] = (i <= 15 ? '0' : '') + i.toString(16);
3720 }
3721
3722 /**
3723 * Return the ObjectID id as a 24 byte hex string representation
3724 *
3725 * @return {String} return the 24 byte hex string representation.
3726 * @api public
3727 */
3728 ObjectID.prototype.toHexString = function() {
3729   if(ObjectID.cacheHexString && this.__id) return this.__id;
3730
3731   var hexString = '';
3732
3733   for (var i = 0; i < this.id.length; i++) {
3734     hexString += hexTable[this.id.charCodeAt(i)];
3735   }
3736
3737   if(ObjectID.cacheHexString) this.__id = hexString;
3738   return hexString;
3739 };
3740
3741 /**
3742 * Update the ObjectID index used in generating new ObjectID's on the driver
3743 *
3744 * @return {Number} returns next index value.
3745 * @api private
3746 */
3747 ObjectID.prototype.get_inc = function() {
3748   return ObjectID.index = (ObjectID.index + 1) % 0xFFFFFF;
3749 };
3750
3751 /**
3752 * Update the ObjectID index used in generating new ObjectID's on the driver
3753 *
3754 * @return {Number} returns next index value.
3755 * @api private
3756 */
3757 ObjectID.prototype.getInc = function() {
3758   return this.get_inc();
3759 };
3760
3761 /**
3762 * Generate a 12 byte id string used in ObjectID's
3763 *
3764 * @param {Number} [time] optional parameter allowing to pass in a second based timestamp.
3765 * @return {String} return the 12 byte id binary string.
3766 * @api private
3767 */
3768 ObjectID.prototype.generate = function(time) {
3769   if ('number' == typeof time) {
3770     var time4Bytes = BinaryParser.encodeInt(time, 32, true, true);
3771     /* for time-based ObjectID the bytes following the time will be zeroed */
3772     var machine3Bytes = BinaryParser.encodeInt(MACHINE_ID, 24, false);
3773     var pid2Bytes = BinaryParser.fromShort(typeof process === 'undefined' ? Math.floor(Math.random() * 100000) : process.pid);
3774     var index3Bytes = BinaryParser.encodeInt(this.get_inc(), 24, false, true);
3775   } else {
3776         var unixTime = parseInt(Date.now()/1000,10);
3777     var time4Bytes = BinaryParser.encodeInt(unixTime, 32, true, true);
3778     var machine3Bytes = BinaryParser.encodeInt(MACHINE_ID, 24, false);
3779     var pid2Bytes = BinaryParser.fromShort(typeof process === 'undefined' ? Math.floor(Math.random() * 100000) : process.pid);
3780     var index3Bytes = BinaryParser.encodeInt(this.get_inc(), 24, false, true);
3781   }
3782
3783   return time4Bytes + machine3Bytes + pid2Bytes + index3Bytes;
3784 };
3785
3786 /**
3787 * Converts the id into a 24 byte hex string for printing
3788 *
3789 * @return {String} return the 24 byte hex string representation.
3790 * @api private
3791 */
3792 ObjectID.prototype.toString = function() {
3793   return this.toHexString();
3794 };
3795
3796 /**
3797 * Converts to a string representation of this Id.
3798 *
3799 * @return {String} return the 24 byte hex string representation.
3800 * @api private
3801 */
3802 ObjectID.prototype.inspect = ObjectID.prototype.toString;
3803
3804 /**
3805 * Converts to its JSON representation.
3806 *
3807 * @return {String} return the 24 byte hex string representation.
3808 * @api private
3809 */
3810 ObjectID.prototype.toJSON = function() {
3811   return this.toHexString();
3812 };
3813
3814 /**
3815 * Compares the equality of this ObjectID with `otherID`.
3816 *
3817 * @param {Object} otherID ObjectID instance to compare against.
3818 * @return {Bool} the result of comparing two ObjectID's
3819 * @api public
3820 */
3821 ObjectID.prototype.equals = function equals (otherID) {
3822   var id = (otherID instanceof ObjectID || otherID.toHexString)
3823     ? otherID.id
3824     : ObjectID.createFromHexString(otherID).id;
3825
3826   return this.id === id;
3827 }
3828
3829 /**
3830 * Returns the generation date (accurate up to the second) that this ID was generated.
3831 *
3832 * @return {Date} the generation date
3833 * @api public
3834 */
3835 ObjectID.prototype.getTimestamp = function() {
3836   var timestamp = new Date();
3837   timestamp.setTime(Math.floor(BinaryParser.decodeInt(this.id.substring(0,4), 32, true, true)) * 1000);
3838   return timestamp;
3839 }
3840
3841 /**
3842 * @ignore
3843 * @api private
3844 */
3845 ObjectID.index = parseInt(Math.random() * 0xFFFFFF, 10);
3846
3847 ObjectID.createPk = function createPk () {
3848   return new ObjectID();
3849 };
3850
3851 /**
3852 * Creates an ObjectID from a second based number, with the rest of the ObjectID zeroed out. Used for comparisons or sorting the ObjectID.
3853 *
3854 * @param {Number} time an integer number representing a number of seconds.
3855 * @return {ObjectID} return the created ObjectID
3856 * @api public
3857 */
3858 ObjectID.createFromTime = function createFromTime (time) {
3859   var id = BinaryParser.encodeInt(time, 32, true, true) +
3860            BinaryParser.encodeInt(0, 64, true, true);
3861   return new ObjectID(id);
3862 };
3863
3864 /**
3865 * Creates an ObjectID from a hex string representation of an ObjectID.
3866 *
3867 * @param {String} hexString create a ObjectID from a passed in 24 byte hexstring.
3868 * @return {ObjectID} return the created ObjectID
3869 * @api public
3870 */
3871 ObjectID.createFromHexString = function createFromHexString (hexString) {
3872   // Throw an error if it's not a valid setup
3873   if(typeof hexString === 'undefined' || hexString != null && hexString.length != 24)
3874     throw new Error("Argument passed in must be a single String of 12 bytes or a string of 24 hex characters");
3875
3876   var len = hexString.length;
3877
3878   if(len > 12*2) {
3879     throw new Error('Id cannot be longer than 12 bytes');
3880   }
3881
3882   var result = ''
3883     , string
3884     , number;
3885
3886   for (var index = 0; index < len; index += 2) {
3887     string = hexString.substr(index, 2);
3888     number = parseInt(string, 16);
3889     result += BinaryParser.fromByte(number);
3890   }
3891
3892   return new ObjectID(result, hexString);
3893 };
3894
3895 /**
3896 * @ignore
3897 */
3898 Object.defineProperty(ObjectID.prototype, "generationTime", {
3899    enumerable: true
3900  , get: function () {
3901      return Math.floor(BinaryParser.decodeInt(this.id.substring(0,4), 32, true, true));
3902    }
3903  , set: function (value) {
3904      var value = BinaryParser.encodeInt(value, 32, true, true);
3905      this.id = value + this.id.substr(4);
3906      // delete this.__id;
3907      this.toHexString();
3908    }
3909 });
3910
3911 /**
3912  * Expose.
3913  */
3914 exports.ObjectID = ObjectID;
3915 exports.ObjectId = ObjectID;
3916
3917 }, 
3918
3919
3920
3921 'symbol': function(module, exports, global, require, undefined){
3922   /**
3923  * A class representation of the BSON Symbol type.
3924  *
3925  * @class Represents the BSON Symbol type.
3926  * @param {String} value the string representing the symbol.
3927  * @return {Symbol}
3928  */
3929 function Symbol(value) {
3930   if(!(this instanceof Symbol)) return new Symbol(value);
3931   this._bsontype = 'Symbol';
3932   this.value = value;
3933 }
3934
3935 /**
3936  * Access the wrapped string value.
3937  *
3938  * @return {String} returns the wrapped string.
3939  * @api public
3940  */
3941 Symbol.prototype.valueOf = function() {
3942   return this.value;
3943 };
3944
3945 /**
3946  * @ignore
3947  * @api private
3948  */
3949 Symbol.prototype.toString = function() {
3950   return this.value;
3951 }
3952
3953 /**
3954  * @ignore
3955  * @api private
3956  */
3957 Symbol.prototype.inspect = function() {
3958   return this.value;
3959 }
3960
3961 /**
3962  * @ignore
3963  * @api private
3964  */
3965 Symbol.prototype.toJSON = function() {
3966   return this.value;
3967 }
3968
3969 exports.Symbol = Symbol;
3970 }, 
3971
3972
3973
3974 'timestamp': function(module, exports, global, require, undefined){
3975   // Licensed under the Apache License, Version 2.0 (the "License");
3976 // you may not use this file except in compliance with the License.
3977 // You may obtain a copy of the License at
3978 //
3979 //     http://www.apache.org/licenses/LICENSE-2.0
3980 //
3981 // Unless required by applicable law or agreed to in writing, software
3982 // distributed under the License is distributed on an "AS IS" BASIS,
3983 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
3984 // See the License for the specific language governing permissions and
3985 // limitations under the License.
3986 //
3987 // Copyright 2009 Google Inc. All Rights Reserved
3988
3989 /**
3990  * Defines a Timestamp class for representing a 64-bit two's-complement
3991  * integer value, which faithfully simulates the behavior of a Java "Timestamp". This
3992  * implementation is derived from TimestampLib in GWT.
3993  *
3994  * Constructs a 64-bit two's-complement integer, given its low and high 32-bit
3995  * values as *signed* integers.  See the from* functions below for more
3996  * convenient ways of constructing Timestamps.
3997  *
3998  * The internal representation of a Timestamp is the two given signed, 32-bit values.
3999  * We use 32-bit pieces because these are the size of integers on which
4000  * Javascript performs bit-operations.  For operations like addition and
4001  * multiplication, we split each number into 16-bit pieces, which can easily be
4002  * multiplied within Javascript's floating-point representation without overflow
4003  * or change in sign.
4004  *
4005  * In the algorithms below, we frequently reduce the negative case to the
4006  * positive case by negating the input(s) and then post-processing the result.
4007  * Note that we must ALWAYS check specially whether those values are MIN_VALUE
4008  * (-2^63) because -MIN_VALUE == MIN_VALUE (since 2^63 cannot be represented as
4009  * a positive number, it overflows back into a negative).  Not handling this
4010  * case would often result in infinite recursion.
4011  *
4012  * @class Represents the BSON Timestamp type.
4013  * @param {Number} low  the low (signed) 32 bits of the Timestamp.
4014  * @param {Number} high the high (signed) 32 bits of the Timestamp.
4015  */
4016 function Timestamp(low, high) {
4017   if(!(this instanceof Timestamp)) return new Timestamp(low, high);
4018   this._bsontype = 'Timestamp';
4019   /**
4020    * @type {number}
4021    * @api private
4022    */
4023   this.low_ = low | 0;  // force into 32 signed bits.
4024
4025   /**
4026    * @type {number}
4027    * @api private
4028    */
4029   this.high_ = high | 0;  // force into 32 signed bits.
4030 };
4031
4032 /**
4033  * Return the int value.
4034  *
4035  * @return {Number} the value, assuming it is a 32-bit integer.
4036  * @api public
4037  */
4038 Timestamp.prototype.toInt = function() {
4039   return this.low_;
4040 };
4041
4042 /**
4043  * Return the Number value.
4044  *
4045  * @return {Number} the closest floating-point representation to this value.
4046  * @api public
4047  */
4048 Timestamp.prototype.toNumber = function() {
4049   return this.high_ * Timestamp.TWO_PWR_32_DBL_ +
4050          this.getLowBitsUnsigned();
4051 };
4052
4053 /**
4054  * Return the JSON value.
4055  *
4056  * @return {String} the JSON representation.
4057  * @api public
4058  */
4059 Timestamp.prototype.toJSON = function() {
4060   return this.toString();
4061 }
4062
4063 /**
4064  * Return the String value.
4065  *
4066  * @param {Number} [opt_radix] the radix in which the text should be written.
4067  * @return {String} the textual representation of this value.
4068  * @api public
4069  */
4070 Timestamp.prototype.toString = function(opt_radix) {
4071   var radix = opt_radix || 10;
4072   if (radix < 2 || 36 < radix) {
4073     throw Error('radix out of range: ' + radix);
4074   }
4075
4076   if (this.isZero()) {
4077     return '0';
4078   }
4079
4080   if (this.isNegative()) {
4081     if (this.equals(Timestamp.MIN_VALUE)) {
4082       // We need to change the Timestamp value before it can be negated, so we remove
4083       // the bottom-most digit in this base and then recurse to do the rest.
4084       var radixTimestamp = Timestamp.fromNumber(radix);
4085       var div = this.div(radixTimestamp);
4086       var rem = div.multiply(radixTimestamp).subtract(this);
4087       return div.toString(radix) + rem.toInt().toString(radix);
4088     } else {
4089       return '-' + this.negate().toString(radix);
4090     }
4091   }
4092
4093   // Do several (6) digits each time through the loop, so as to
4094   // minimize the calls to the very expensive emulated div.
4095   var radixToPower = Timestamp.fromNumber(Math.pow(radix, 6));
4096
4097   var rem = this;
4098   var result = '';
4099   while (true) {
4100     var remDiv = rem.div(radixToPower);
4101     var intval = rem.subtract(remDiv.multiply(radixToPower)).toInt();
4102     var digits = intval.toString(radix);
4103
4104     rem = remDiv;
4105     if (rem.isZero()) {
4106       return digits + result;
4107     } else {
4108       while (digits.length < 6) {
4109         digits = '0' + digits;
4110       }
4111       result = '' + digits + result;
4112     }
4113   }
4114 };
4115
4116 /**
4117  * Return the high 32-bits value.
4118  *
4119  * @return {Number} the high 32-bits as a signed value.
4120  * @api public
4121  */
4122 Timestamp.prototype.getHighBits = function() {
4123   return this.high_;
4124 };
4125
4126 /**
4127  * Return the low 32-bits value.
4128  *
4129  * @return {Number} the low 32-bits as a signed value.
4130  * @api public
4131  */
4132 Timestamp.prototype.getLowBits = function() {
4133   return this.low_;
4134 };
4135
4136 /**
4137  * Return the low unsigned 32-bits value.
4138  *
4139  * @return {Number} the low 32-bits as an unsigned value.
4140  * @api public
4141  */
4142 Timestamp.prototype.getLowBitsUnsigned = function() {
4143   return (this.low_ >= 0) ?
4144       this.low_ : Timestamp.TWO_PWR_32_DBL_ + this.low_;
4145 };
4146
4147 /**
4148  * Returns the number of bits needed to represent the absolute value of this Timestamp.
4149  *
4150  * @return {Number} Returns the number of bits needed to represent the absolute value of this Timestamp.
4151  * @api public
4152  */
4153 Timestamp.prototype.getNumBitsAbs = function() {
4154   if (this.isNegative()) {
4155     if (this.equals(Timestamp.MIN_VALUE)) {
4156       return 64;
4157     } else {
4158       return this.negate().getNumBitsAbs();
4159     }
4160   } else {
4161     var val = this.high_ != 0 ? this.high_ : this.low_;
4162     for (var bit = 31; bit > 0; bit--) {
4163       if ((val & (1 << bit)) != 0) {
4164         break;
4165       }
4166     }
4167     return this.high_ != 0 ? bit + 33 : bit + 1;
4168   }
4169 };
4170
4171 /**
4172  * Return whether this value is zero.
4173  *
4174  * @return {Boolean} whether this value is zero.
4175  * @api public
4176  */
4177 Timestamp.prototype.isZero = function() {
4178   return this.high_ == 0 && this.low_ == 0;
4179 };
4180
4181 /**
4182  * Return whether this value is negative.
4183  *
4184  * @return {Boolean} whether this value is negative.
4185  * @api public
4186  */
4187 Timestamp.prototype.isNegative = function() {
4188   return this.high_ < 0;
4189 };
4190
4191 /**
4192  * Return whether this value is odd.
4193  *
4194  * @return {Boolean} whether this value is odd.
4195  * @api public
4196  */
4197 Timestamp.prototype.isOdd = function() {
4198   return (this.low_ & 1) == 1;
4199 };
4200
4201 /**
4202  * Return whether this Timestamp equals the other
4203  *
4204  * @param {Timestamp} other Timestamp to compare against.
4205  * @return {Boolean} whether this Timestamp equals the other
4206  * @api public
4207  */
4208 Timestamp.prototype.equals = function(other) {
4209   return (this.high_ == other.high_) && (this.low_ == other.low_);
4210 };
4211
4212 /**
4213  * Return whether this Timestamp does not equal the other.
4214  *
4215  * @param {Timestamp} other Timestamp to compare against.
4216  * @return {Boolean} whether this Timestamp does not equal the other.
4217  * @api public
4218  */
4219 Timestamp.prototype.notEquals = function(other) {
4220   return (this.high_ != other.high_) || (this.low_ != other.low_);
4221 };
4222
4223 /**
4224  * Return whether this Timestamp is less than the other.
4225  *
4226  * @param {Timestamp} other Timestamp to compare against.
4227  * @return {Boolean} whether this Timestamp is less than the other.
4228  * @api public
4229  */
4230 Timestamp.prototype.lessThan = function(other) {
4231   return this.compare(other) < 0;
4232 };
4233
4234 /**
4235  * Return whether this Timestamp is less than or equal to the other.
4236  *
4237  * @param {Timestamp} other Timestamp to compare against.
4238  * @return {Boolean} whether this Timestamp is less than or equal to the other.
4239  * @api public
4240  */
4241 Timestamp.prototype.lessThanOrEqual = function(other) {
4242   return this.compare(other) <= 0;
4243 };
4244
4245 /**
4246  * Return whether this Timestamp is greater than the other.
4247  *
4248  * @param {Timestamp} other Timestamp to compare against.
4249  * @return {Boolean} whether this Timestamp is greater than the other.
4250  * @api public
4251  */
4252 Timestamp.prototype.greaterThan = function(other) {
4253   return this.compare(other) > 0;
4254 };
4255
4256 /**
4257  * Return whether this Timestamp is greater than or equal to the other.
4258  *
4259  * @param {Timestamp} other Timestamp to compare against.
4260  * @return {Boolean} whether this Timestamp is greater than or equal to the other.
4261  * @api public
4262  */
4263 Timestamp.prototype.greaterThanOrEqual = function(other) {
4264   return this.compare(other) >= 0;
4265 };
4266
4267 /**
4268  * Compares this Timestamp with the given one.
4269  *
4270  * @param {Timestamp} other Timestamp to compare against.
4271  * @return {Boolean} 0 if they are the same, 1 if the this is greater, and -1 if the given one is greater.
4272  * @api public
4273  */
4274 Timestamp.prototype.compare = function(other) {
4275   if (this.equals(other)) {
4276     return 0;
4277   }
4278
4279   var thisNeg = this.isNegative();
4280   var otherNeg = other.isNegative();
4281   if (thisNeg && !otherNeg) {
4282     return -1;
4283   }
4284   if (!thisNeg && otherNeg) {
4285     return 1;
4286   }
4287
4288   // at this point, the signs are the same, so subtraction will not overflow
4289   if (this.subtract(other).isNegative()) {
4290     return -1;
4291   } else {
4292     return 1;
4293   }
4294 };
4295
4296 /**
4297  * The negation of this value.
4298  *
4299  * @return {Timestamp} the negation of this value.
4300  * @api public
4301  */
4302 Timestamp.prototype.negate = function() {
4303   if (this.equals(Timestamp.MIN_VALUE)) {
4304     return Timestamp.MIN_VALUE;
4305   } else {
4306     return this.not().add(Timestamp.ONE);
4307   }
4308 };
4309
4310 /**
4311  * Returns the sum of this and the given Timestamp.
4312  *
4313  * @param {Timestamp} other Timestamp to add to this one.
4314  * @return {Timestamp} the sum of this and the given Timestamp.
4315  * @api public
4316  */
4317 Timestamp.prototype.add = function(other) {
4318   // Divide each number into 4 chunks of 16 bits, and then sum the chunks.
4319
4320   var a48 = this.high_ >>> 16;
4321   var a32 = this.high_ & 0xFFFF;
4322   var a16 = this.low_ >>> 16;
4323   var a00 = this.low_ & 0xFFFF;
4324
4325   var b48 = other.high_ >>> 16;
4326   var b32 = other.high_ & 0xFFFF;
4327   var b16 = other.low_ >>> 16;
4328   var b00 = other.low_ & 0xFFFF;
4329
4330   var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
4331   c00 += a00 + b00;
4332   c16 += c00 >>> 16;
4333   c00 &= 0xFFFF;
4334   c16 += a16 + b16;
4335   c32 += c16 >>> 16;
4336   c16 &= 0xFFFF;
4337   c32 += a32 + b32;
4338   c48 += c32 >>> 16;
4339   c32 &= 0xFFFF;
4340   c48 += a48 + b48;
4341   c48 &= 0xFFFF;
4342   return Timestamp.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
4343 };
4344
4345 /**
4346  * Returns the difference of this and the given Timestamp.
4347  *
4348  * @param {Timestamp} other Timestamp to subtract from this.
4349  * @return {Timestamp} the difference of this and the given Timestamp.
4350  * @api public
4351  */
4352 Timestamp.prototype.subtract = function(other) {
4353   return this.add(other.negate());
4354 };
4355
4356 /**
4357  * Returns the product of this and the given Timestamp.
4358  *
4359  * @param {Timestamp} other Timestamp to multiply with this.
4360  * @return {Timestamp} the product of this and the other.
4361  * @api public
4362  */
4363 Timestamp.prototype.multiply = function(other) {
4364   if (this.isZero()) {
4365     return Timestamp.ZERO;
4366   } else if (other.isZero()) {
4367     return Timestamp.ZERO;
4368   }
4369
4370   if (this.equals(Timestamp.MIN_VALUE)) {
4371     return other.isOdd() ? Timestamp.MIN_VALUE : Timestamp.ZERO;
4372   } else if (other.equals(Timestamp.MIN_VALUE)) {
4373     return this.isOdd() ? Timestamp.MIN_VALUE : Timestamp.ZERO;
4374   }
4375
4376   if (this.isNegative()) {
4377     if (other.isNegative()) {
4378       return this.negate().multiply(other.negate());
4379     } else {
4380       return this.negate().multiply(other).negate();
4381     }
4382   } else if (other.isNegative()) {
4383     return this.multiply(other.negate()).negate();
4384   }
4385
4386   // If both Timestamps are small, use float multiplication
4387   if (this.lessThan(Timestamp.TWO_PWR_24_) &&
4388       other.lessThan(Timestamp.TWO_PWR_24_)) {
4389     return Timestamp.fromNumber(this.toNumber() * other.toNumber());
4390   }
4391
4392   // Divide each Timestamp into 4 chunks of 16 bits, and then add up 4x4 products.
4393   // We can skip products that would overflow.
4394
4395   var a48 = this.high_ >>> 16;
4396   var a32 = this.high_ & 0xFFFF;
4397   var a16 = this.low_ >>> 16;
4398   var a00 = this.low_ & 0xFFFF;
4399
4400   var b48 = other.high_ >>> 16;
4401   var b32 = other.high_ & 0xFFFF;
4402   var b16 = other.low_ >>> 16;
4403   var b00 = other.low_ & 0xFFFF;
4404
4405   var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
4406   c00 += a00 * b00;
4407   c16 += c00 >>> 16;
4408   c00 &= 0xFFFF;
4409   c16 += a16 * b00;
4410   c32 += c16 >>> 16;
4411   c16 &= 0xFFFF;
4412   c16 += a00 * b16;
4413   c32 += c16 >>> 16;
4414   c16 &= 0xFFFF;
4415   c32 += a32 * b00;
4416   c48 += c32 >>> 16;
4417   c32 &= 0xFFFF;
4418   c32 += a16 * b16;
4419   c48 += c32 >>> 16;
4420   c32 &= 0xFFFF;
4421   c32 += a00 * b32;
4422   c48 += c32 >>> 16;
4423   c32 &= 0xFFFF;
4424   c48 += a48 * b00 + a32 * b16 + a16 * b32 + a00 * b48;
4425   c48 &= 0xFFFF;
4426   return Timestamp.fromBits((c16 << 16) | c00, (c48 << 16) | c32);
4427 };
4428
4429 /**
4430  * Returns this Timestamp divided by the given one.
4431  *
4432  * @param {Timestamp} other Timestamp by which to divide.
4433  * @return {Timestamp} this Timestamp divided by the given one.
4434  * @api public
4435  */
4436 Timestamp.prototype.div = function(other) {
4437   if (other.isZero()) {
4438     throw Error('division by zero');
4439   } else if (this.isZero()) {
4440     return Timestamp.ZERO;
4441   }
4442
4443   if (this.equals(Timestamp.MIN_VALUE)) {
4444     if (other.equals(Timestamp.ONE) ||
4445         other.equals(Timestamp.NEG_ONE)) {
4446       return Timestamp.MIN_VALUE;  // recall that -MIN_VALUE == MIN_VALUE
4447     } else if (other.equals(Timestamp.MIN_VALUE)) {
4448       return Timestamp.ONE;
4449     } else {
4450       // At this point, we have |other| >= 2, so |this/other| < |MIN_VALUE|.
4451       var halfThis = this.shiftRight(1);
4452       var approx = halfThis.div(other).shiftLeft(1);
4453       if (approx.equals(Timestamp.ZERO)) {
4454         return other.isNegative() ? Timestamp.ONE : Timestamp.NEG_ONE;
4455       } else {
4456         var rem = this.subtract(other.multiply(approx));
4457         var result = approx.add(rem.div(other));
4458         return result;
4459       }
4460     }
4461   } else if (other.equals(Timestamp.MIN_VALUE)) {
4462     return Timestamp.ZERO;
4463   }
4464
4465   if (this.isNegative()) {
4466     if (other.isNegative()) {
4467       return this.negate().div(other.negate());
4468     } else {
4469       return this.negate().div(other).negate();
4470     }
4471   } else if (other.isNegative()) {
4472     return this.div(other.negate()).negate();
4473   }
4474
4475   // Repeat the following until the remainder is less than other:  find a
4476   // floating-point that approximates remainder / other *from below*, add this
4477   // into the result, and subtract it from the remainder.  It is critical that
4478   // the approximate value is less than or equal to the real value so that the
4479   // remainder never becomes negative.
4480   var res = Timestamp.ZERO;
4481   var rem = this;
4482   while (rem.greaterThanOrEqual(other)) {
4483     // Approximate the result of division. This may be a little greater or
4484     // smaller than the actual value.
4485     var approx = Math.max(1, Math.floor(rem.toNumber() / other.toNumber()));
4486
4487     // We will tweak the approximate result by changing it in the 48-th digit or
4488     // the smallest non-fractional digit, whichever is larger.
4489     var log2 = Math.ceil(Math.log(approx) / Math.LN2);
4490     var delta = (log2 <= 48) ? 1 : Math.pow(2, log2 - 48);
4491
4492     // Decrease the approximation until it is smaller than the remainder.  Note
4493     // that if it is too large, the product overflows and is negative.
4494     var approxRes = Timestamp.fromNumber(approx);
4495     var approxRem = approxRes.multiply(other);
4496     while (approxRem.isNegative() || approxRem.greaterThan(rem)) {
4497       approx -= delta;
4498       approxRes = Timestamp.fromNumber(approx);
4499       approxRem = approxRes.multiply(other);
4500     }
4501
4502     // We know the answer can't be zero... and actually, zero would cause
4503     // infinite recursion since we would make no progress.
4504     if (approxRes.isZero()) {
4505       approxRes = Timestamp.ONE;
4506     }
4507
4508     res = res.add(approxRes);
4509     rem = rem.subtract(approxRem);
4510   }
4511   return res;
4512 };
4513
4514 /**
4515  * Returns this Timestamp modulo the given one.
4516  *
4517  * @param {Timestamp} other Timestamp by which to mod.
4518  * @return {Timestamp} this Timestamp modulo the given one.
4519  * @api public
4520  */
4521 Timestamp.prototype.modulo = function(other) {
4522   return this.subtract(this.div(other).multiply(other));
4523 };
4524
4525 /**
4526  * The bitwise-NOT of this value.
4527  *
4528  * @return {Timestamp} the bitwise-NOT of this value.
4529  * @api public
4530  */
4531 Timestamp.prototype.not = function() {
4532   return Timestamp.fromBits(~this.low_, ~this.high_);
4533 };
4534
4535 /**
4536  * Returns the bitwise-AND of this Timestamp and the given one.
4537  *
4538  * @param {Timestamp} other the Timestamp with which to AND.
4539  * @return {Timestamp} the bitwise-AND of this and the other.
4540  * @api public
4541  */
4542 Timestamp.prototype.and = function(other) {
4543   return Timestamp.fromBits(this.low_ & other.low_, this.high_ & other.high_);
4544 };
4545
4546 /**
4547  * Returns the bitwise-OR of this Timestamp and the given one.
4548  *
4549  * @param {Timestamp} other the Timestamp with which to OR.
4550  * @return {Timestamp} the bitwise-OR of this and the other.
4551  * @api public
4552  */
4553 Timestamp.prototype.or = function(other) {
4554   return Timestamp.fromBits(this.low_ | other.low_, this.high_ | other.high_);
4555 };
4556
4557 /**
4558  * Returns the bitwise-XOR of this Timestamp and the given one.
4559  *
4560  * @param {Timestamp} other the Timestamp with which to XOR.
4561  * @return {Timestamp} the bitwise-XOR of this and the other.
4562  * @api public
4563  */
4564 Timestamp.prototype.xor = function(other) {
4565   return Timestamp.fromBits(this.low_ ^ other.low_, this.high_ ^ other.high_);
4566 };
4567
4568 /**
4569  * Returns this Timestamp with bits shifted to the left by the given amount.
4570  *
4571  * @param {Number} numBits the number of bits by which to shift.
4572  * @return {Timestamp} this shifted to the left by the given amount.
4573  * @api public
4574  */
4575 Timestamp.prototype.shiftLeft = function(numBits) {
4576   numBits &= 63;
4577   if (numBits == 0) {
4578     return this;
4579   } else {
4580     var low = this.low_;
4581     if (numBits < 32) {
4582       var high = this.high_;
4583       return Timestamp.fromBits(
4584                  low << numBits,
4585                  (high << numBits) | (low >>> (32 - numBits)));
4586     } else {
4587       return Timestamp.fromBits(0, low << (numBits - 32));
4588     }
4589   }
4590 };
4591
4592 /**
4593  * Returns this Timestamp with bits shifted to the right by the given amount.
4594  *
4595  * @param {Number} numBits the number of bits by which to shift.
4596  * @return {Timestamp} this shifted to the right by the given amount.
4597  * @api public
4598  */
4599 Timestamp.prototype.shiftRight = function(numBits) {
4600   numBits &= 63;
4601   if (numBits == 0) {
4602     return this;
4603   } else {
4604     var high = this.high_;
4605     if (numBits < 32) {
4606       var low = this.low_;
4607       return Timestamp.fromBits(
4608                  (low >>> numBits) | (high << (32 - numBits)),
4609                  high >> numBits);
4610     } else {
4611       return Timestamp.fromBits(
4612                  high >> (numBits - 32),
4613                  high >= 0 ? 0 : -1);
4614     }
4615   }
4616 };
4617
4618 /**
4619  * Returns this Timestamp with bits shifted to the right by the given amount, with the new top bits matching the current sign bit.
4620  *
4621  * @param {Number} numBits the number of bits by which to shift.
4622  * @return {Timestamp} this shifted to the right by the given amount, with zeros placed into the new leading bits.
4623  * @api public
4624  */
4625 Timestamp.prototype.shiftRightUnsigned = function(numBits) {
4626   numBits &= 63;
4627   if (numBits == 0) {
4628     return this;
4629   } else {
4630     var high = this.high_;
4631     if (numBits < 32) {
4632       var low = this.low_;
4633       return Timestamp.fromBits(
4634                  (low >>> numBits) | (high << (32 - numBits)),
4635                  high >>> numBits);
4636     } else if (numBits == 32) {
4637       return Timestamp.fromBits(high, 0);
4638     } else {
4639       return Timestamp.fromBits(high >>> (numBits - 32), 0);
4640     }
4641   }
4642 };
4643
4644 /**
4645  * Returns a Timestamp representing the given (32-bit) integer value.
4646  *
4647  * @param {Number} value the 32-bit integer in question.
4648  * @return {Timestamp} the corresponding Timestamp value.
4649  * @api public
4650  */
4651 Timestamp.fromInt = function(value) {
4652   if (-128 <= value && value < 128) {
4653     var cachedObj = Timestamp.INT_CACHE_[value];
4654     if (cachedObj) {
4655       return cachedObj;
4656     }
4657   }
4658
4659   var obj = new Timestamp(value | 0, value < 0 ? -1 : 0);
4660   if (-128 <= value && value < 128) {
4661     Timestamp.INT_CACHE_[value] = obj;
4662   }
4663   return obj;
4664 };
4665
4666 /**
4667  * Returns a Timestamp representing the given value, provided that it is a finite number. Otherwise, zero is returned.
4668  *
4669  * @param {Number} value the number in question.
4670  * @return {Timestamp} the corresponding Timestamp value.
4671  * @api public
4672  */
4673 Timestamp.fromNumber = function(value) {
4674   if (isNaN(value) || !isFinite(value)) {
4675     return Timestamp.ZERO;
4676   } else if (value <= -Timestamp.TWO_PWR_63_DBL_) {
4677     return Timestamp.MIN_VALUE;
4678   } else if (value + 1 >= Timestamp.TWO_PWR_63_DBL_) {
4679     return Timestamp.MAX_VALUE;
4680   } else if (value < 0) {
4681     return Timestamp.fromNumber(-value).negate();
4682   } else {
4683     return new Timestamp(
4684                (value % Timestamp.TWO_PWR_32_DBL_) | 0,
4685                (value / Timestamp.TWO_PWR_32_DBL_) | 0);
4686   }
4687 };
4688
4689 /**
4690  * Returns a Timestamp representing the 64-bit integer that comes by concatenating the given high and low bits. Each is assumed to use 32 bits.
4691  *
4692  * @param {Number} lowBits the low 32-bits.
4693  * @param {Number} highBits the high 32-bits.
4694  * @return {Timestamp} the corresponding Timestamp value.
4695  * @api public
4696  */
4697 Timestamp.fromBits = function(lowBits, highBits) {
4698   return new Timestamp(lowBits, highBits);
4699 };
4700
4701 /**
4702  * Returns a Timestamp representation of the given string, written using the given radix.
4703  *
4704  * @param {String} str the textual representation of the Timestamp.
4705  * @param {Number} opt_radix the radix in which the text is written.
4706  * @return {Timestamp} the corresponding Timestamp value.
4707  * @api public
4708  */
4709 Timestamp.fromString = function(str, opt_radix) {
4710   if (str.length == 0) {
4711     throw Error('number format error: empty string');
4712   }
4713
4714   var radix = opt_radix || 10;
4715   if (radix < 2 || 36 < radix) {
4716     throw Error('radix out of range: ' + radix);
4717   }
4718
4719   if (str.charAt(0) == '-') {
4720     return Timestamp.fromString(str.substring(1), radix).negate();
4721   } else if (str.indexOf('-') >= 0) {
4722     throw Error('number format error: interior "-" character: ' + str);
4723   }
4724
4725   // Do several (8) digits each time through the loop, so as to
4726   // minimize the calls to the very expensive emulated div.
4727   var radixToPower = Timestamp.fromNumber(Math.pow(radix, 8));
4728
4729   var result = Timestamp.ZERO;
4730   for (var i = 0; i < str.length; i += 8) {
4731     var size = Math.min(8, str.length - i);
4732     var value = parseInt(str.substring(i, i + size), radix);
4733     if (size < 8) {
4734       var power = Timestamp.fromNumber(Math.pow(radix, size));
4735       result = result.multiply(power).add(Timestamp.fromNumber(value));
4736     } else {
4737       result = result.multiply(radixToPower);
4738       result = result.add(Timestamp.fromNumber(value));
4739     }
4740   }
4741   return result;
4742 };
4743
4744 // NOTE: Common constant values ZERO, ONE, NEG_ONE, etc. are defined below the
4745 // from* methods on which they depend.
4746
4747
4748 /**
4749  * A cache of the Timestamp representations of small integer values.
4750  * @type {Object}
4751  * @api private
4752  */
4753 Timestamp.INT_CACHE_ = {};
4754
4755 // NOTE: the compiler should inline these constant values below and then remove
4756 // these variables, so there should be no runtime penalty for these.
4757
4758 /**
4759  * Number used repeated below in calculations.  This must appear before the
4760  * first call to any from* function below.
4761  * @type {number}
4762  * @api private
4763  */
4764 Timestamp.TWO_PWR_16_DBL_ = 1 << 16;
4765
4766 /**
4767  * @type {number}
4768  * @api private
4769  */
4770 Timestamp.TWO_PWR_24_DBL_ = 1 << 24;
4771
4772 /**
4773  * @type {number}
4774  * @api private
4775  */
4776 Timestamp.TWO_PWR_32_DBL_ = Timestamp.TWO_PWR_16_DBL_ * Timestamp.TWO_PWR_16_DBL_;
4777
4778 /**
4779  * @type {number}
4780  * @api private
4781  */
4782 Timestamp.TWO_PWR_31_DBL_ = Timestamp.TWO_PWR_32_DBL_ / 2;
4783
4784 /**
4785  * @type {number}
4786  * @api private
4787  */
4788 Timestamp.TWO_PWR_48_DBL_ = Timestamp.TWO_PWR_32_DBL_ * Timestamp.TWO_PWR_16_DBL_;
4789
4790 /**
4791  * @type {number}
4792  * @api private
4793  */
4794 Timestamp.TWO_PWR_64_DBL_ = Timestamp.TWO_PWR_32_DBL_ * Timestamp.TWO_PWR_32_DBL_;
4795
4796 /**
4797  * @type {number}
4798  * @api private
4799  */
4800 Timestamp.TWO_PWR_63_DBL_ = Timestamp.TWO_PWR_64_DBL_ / 2;
4801
4802 /** @type {Timestamp} */
4803 Timestamp.ZERO = Timestamp.fromInt(0);
4804
4805 /** @type {Timestamp} */
4806 Timestamp.ONE = Timestamp.fromInt(1);
4807
4808 /** @type {Timestamp} */
4809 Timestamp.NEG_ONE = Timestamp.fromInt(-1);
4810
4811 /** @type {Timestamp} */
4812 Timestamp.MAX_VALUE =
4813     Timestamp.fromBits(0xFFFFFFFF | 0, 0x7FFFFFFF | 0);
4814
4815 /** @type {Timestamp} */
4816 Timestamp.MIN_VALUE = Timestamp.fromBits(0, 0x80000000 | 0);
4817
4818 /**
4819  * @type {Timestamp}
4820  * @api private
4821  */
4822 Timestamp.TWO_PWR_24_ = Timestamp.fromInt(1 << 24);
4823
4824 /**
4825  * Expose.
4826  */
4827 exports.Timestamp = Timestamp;
4828 }, 
4829
4830  });
4831
4832
4833 if(typeof module != 'undefined' && module.exports ){
4834   module.exports = bson;
4835
4836   if( !module.parent ){
4837     bson();
4838   }
4839 }
4840
4841 if(typeof window != 'undefined' && typeof require == 'undefined'){
4842   window.require = bson.require;
4843 }