| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780 | 'use strict';var Long = require('../long').Long,  Double = require('../double').Double,  Timestamp = require('../timestamp').Timestamp,  ObjectID = require('../objectid').ObjectID,  Symbol = require('../symbol').Symbol,  Code = require('../code').Code,  MinKey = require('../min_key').MinKey,  MaxKey = require('../max_key').MaxKey,  Decimal128 = require('../decimal128'),  Int32 = require('../int_32'),  DBRef = require('../db_ref').DBRef,  BSONRegExp = require('../regexp').BSONRegExp,  Binary = require('../binary').Binary;var deserialize = function(buffer, options, isArray) {  options = options == null ? {} : options;  var index = options && options.index ? options.index : 0;  // Read the document size  var size =    buffer[index] |    (buffer[index + 1] << 8) |    (buffer[index + 2] << 16) |    (buffer[index + 3] << 24);  // Ensure buffer is valid size  if (size < 5 || buffer.length < size || size + index > buffer.length) {    throw new Error('corrupt bson message');  }  // Illegal end value  if (buffer[index + size - 1] !== 0) {    throw new Error("One object, sized correctly, with a spot for an EOO, but the EOO isn't 0x00");  }  // Start deserializtion  return deserializeObject(buffer, index, options, isArray);};var deserializeObject = function(buffer, index, options, isArray) {  var evalFunctions = options['evalFunctions'] == null ? false : options['evalFunctions'];  var cacheFunctions = options['cacheFunctions'] == null ? false : options['cacheFunctions'];  var cacheFunctionsCrc32 =    options['cacheFunctionsCrc32'] == null ? false : options['cacheFunctionsCrc32'];  if (!cacheFunctionsCrc32) var crc32 = null;  var fieldsAsRaw = options['fieldsAsRaw'] == null ? null : options['fieldsAsRaw'];  // Return raw bson buffer instead of parsing it  var raw = options['raw'] == null ? false : options['raw'];  // Return BSONRegExp objects instead of native regular expressions  var bsonRegExp = typeof options['bsonRegExp'] === 'boolean' ? options['bsonRegExp'] : false;  // Controls the promotion of values vs wrapper classes  var promoteBuffers = options['promoteBuffers'] == null ? false : options['promoteBuffers'];  var promoteLongs = options['promoteLongs'] == null ? true : options['promoteLongs'];  var promoteValues = options['promoteValues'] == null ? true : options['promoteValues'];  // Set the start index  var startIndex = index;  // Validate that we have at least 4 bytes of buffer  if (buffer.length < 5) throw new Error('corrupt bson message < 5 bytes long');  // Read the document size  var size =    buffer[index++] | (buffer[index++] << 8) | (buffer[index++] << 16) | (buffer[index++] << 24);  // Ensure buffer is valid size  if (size < 5 || size > buffer.length) throw new Error('corrupt bson message');  // Create holding object  var object = isArray ? [] : {};  // Used for arrays to skip having to perform utf8 decoding  var arrayIndex = 0;  var done = false;  // While we have more left data left keep parsing  // while (buffer[index + 1] !== 0) {  while (!done) {    // Read the type    var elementType = buffer[index++];    // If we get a zero it's the last byte, exit    if (elementType === 0) break;    // Get the start search index    var i = index;    // Locate the end of the c string    while (buffer[i] !== 0x00 && i < buffer.length) {      i++;    }    // If are at the end of the buffer there is a problem with the document    if (i >= buffer.length) throw new Error('Bad BSON Document: illegal CString');    var name = isArray ? arrayIndex++ : buffer.toString('utf8', index, i);    index = i + 1;    if (elementType === BSON.BSON_DATA_STRING) {      var stringSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      if (        stringSize <= 0 ||        stringSize > buffer.length - index ||        buffer[index + stringSize - 1] !== 0      )        throw new Error('bad string length in bson');      object[name] = buffer.toString('utf8', index, index + stringSize - 1);      index = index + stringSize;    } else if (elementType === BSON.BSON_DATA_OID) {      var oid = new Buffer(12);      buffer.copy(oid, 0, index, index + 12);      object[name] = new ObjectID(oid);      index = index + 12;    } else if (elementType === BSON.BSON_DATA_INT && promoteValues === false) {      object[name] = new Int32(        buffer[index++] | (buffer[index++] << 8) | (buffer[index++] << 16) | (buffer[index++] << 24)      );    } else if (elementType === BSON.BSON_DATA_INT) {      object[name] =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);    } else if (elementType === BSON.BSON_DATA_NUMBER && promoteValues === false) {      object[name] = new Double(buffer.readDoubleLE(index));      index = index + 8;    } else if (elementType === BSON.BSON_DATA_NUMBER) {      object[name] = buffer.readDoubleLE(index);      index = index + 8;    } else if (elementType === BSON.BSON_DATA_DATE) {      var lowBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      var highBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      object[name] = new Date(new Long(lowBits, highBits).toNumber());    } else if (elementType === BSON.BSON_DATA_BOOLEAN) {      if (buffer[index] !== 0 && buffer[index] !== 1) throw new Error('illegal boolean type value');      object[name] = buffer[index++] === 1;    } else if (elementType === BSON.BSON_DATA_OBJECT) {      var _index = index;      var objectSize =        buffer[index] |        (buffer[index + 1] << 8) |        (buffer[index + 2] << 16) |        (buffer[index + 3] << 24);      if (objectSize <= 0 || objectSize > buffer.length - index)        throw new Error('bad embedded document length in bson');      // We have a raw value      if (raw) {        object[name] = buffer.slice(index, index + objectSize);      } else {        object[name] = deserializeObject(buffer, _index, options, false);      }      index = index + objectSize;    } else if (elementType === BSON.BSON_DATA_ARRAY) {      _index = index;      objectSize =        buffer[index] |        (buffer[index + 1] << 8) |        (buffer[index + 2] << 16) |        (buffer[index + 3] << 24);      var arrayOptions = options;      // Stop index      var stopIndex = index + objectSize;      // All elements of array to be returned as raw bson      if (fieldsAsRaw && fieldsAsRaw[name]) {        arrayOptions = {};        for (var n in options) arrayOptions[n] = options[n];        arrayOptions['raw'] = true;      }      object[name] = deserializeObject(buffer, _index, arrayOptions, true);      index = index + objectSize;      if (buffer[index - 1] !== 0) throw new Error('invalid array terminator byte');      if (index !== stopIndex) throw new Error('corrupted array bson');    } else if (elementType === BSON.BSON_DATA_UNDEFINED) {      object[name] = undefined;    } else if (elementType === BSON.BSON_DATA_NULL) {      object[name] = null;    } else if (elementType === BSON.BSON_DATA_LONG) {      // Unpack the low and high bits      lowBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      highBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      var long = new Long(lowBits, highBits);      // Promote the long if possible      if (promoteLongs && promoteValues === true) {        object[name] =          long.lessThanOrEqual(JS_INT_MAX_LONG) && long.greaterThanOrEqual(JS_INT_MIN_LONG)            ? long.toNumber()            : long;      } else {        object[name] = long;      }    } else if (elementType === BSON.BSON_DATA_DECIMAL128) {      // Buffer to contain the decimal bytes      var bytes = new Buffer(16);      // Copy the next 16 bytes into the bytes buffer      buffer.copy(bytes, 0, index, index + 16);      // Update index      index = index + 16;      // Assign the new Decimal128 value      var decimal128 = new Decimal128(bytes);      // If we have an alternative mapper use that      object[name] = decimal128.toObject ? decimal128.toObject() : decimal128;    } else if (elementType === BSON.BSON_DATA_BINARY) {      var binarySize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      var totalBinarySize = binarySize;      var subType = buffer[index++];      // Did we have a negative binary size, throw      if (binarySize < 0) throw new Error('Negative binary type element size found');      // Is the length longer than the document      if (binarySize > buffer.length) throw new Error('Binary type size larger than document size');      // Decode as raw Buffer object if options specifies it      if (buffer['slice'] != null) {        // If we have subtype 2 skip the 4 bytes for the size        if (subType === Binary.SUBTYPE_BYTE_ARRAY) {          binarySize =            buffer[index++] |            (buffer[index++] << 8) |            (buffer[index++] << 16) |            (buffer[index++] << 24);          if (binarySize < 0)            throw new Error('Negative binary type element size found for subtype 0x02');          if (binarySize > totalBinarySize - 4)            throw new Error('Binary type with subtype 0x02 contains to long binary size');          if (binarySize < totalBinarySize - 4)            throw new Error('Binary type with subtype 0x02 contains to short binary size');        }        if (promoteBuffers && promoteValues) {          object[name] = buffer.slice(index, index + binarySize);        } else {          object[name] = new Binary(buffer.slice(index, index + binarySize), subType);        }      } else {        var _buffer =          typeof Uint8Array !== 'undefined'            ? new Uint8Array(new ArrayBuffer(binarySize))            : new Array(binarySize);        // If we have subtype 2 skip the 4 bytes for the size        if (subType === Binary.SUBTYPE_BYTE_ARRAY) {          binarySize =            buffer[index++] |            (buffer[index++] << 8) |            (buffer[index++] << 16) |            (buffer[index++] << 24);          if (binarySize < 0)            throw new Error('Negative binary type element size found for subtype 0x02');          if (binarySize > totalBinarySize - 4)            throw new Error('Binary type with subtype 0x02 contains to long binary size');          if (binarySize < totalBinarySize - 4)            throw new Error('Binary type with subtype 0x02 contains to short binary size');        }        // Copy the data        for (i = 0; i < binarySize; i++) {          _buffer[i] = buffer[index + i];        }        if (promoteBuffers && promoteValues) {          object[name] = _buffer;        } else {          object[name] = new Binary(_buffer, subType);        }      }      // Update the index      index = index + binarySize;    } else if (elementType === BSON.BSON_DATA_REGEXP && bsonRegExp === false) {      // Get the start search index      i = index;      // Locate the end of the c string      while (buffer[i] !== 0x00 && i < buffer.length) {        i++;      }      // If are at the end of the buffer there is a problem with the document      if (i >= buffer.length) throw new Error('Bad BSON Document: illegal CString');      // Return the C string      var source = buffer.toString('utf8', index, i);      // Create the regexp      index = i + 1;      // Get the start search index      i = index;      // Locate the end of the c string      while (buffer[i] !== 0x00 && i < buffer.length) {        i++;      }      // If are at the end of the buffer there is a problem with the document      if (i >= buffer.length) throw new Error('Bad BSON Document: illegal CString');      // Return the C string      var regExpOptions = buffer.toString('utf8', index, i);      index = i + 1;      // For each option add the corresponding one for javascript      var optionsArray = new Array(regExpOptions.length);      // Parse options      for (i = 0; i < regExpOptions.length; i++) {        switch (regExpOptions[i]) {          case 'm':            optionsArray[i] = 'm';            break;          case 's':            optionsArray[i] = 'g';            break;          case 'i':            optionsArray[i] = 'i';            break;        }      }      object[name] = new RegExp(source, optionsArray.join(''));    } else if (elementType === BSON.BSON_DATA_REGEXP && bsonRegExp === true) {      // Get the start search index      i = index;      // Locate the end of the c string      while (buffer[i] !== 0x00 && i < buffer.length) {        i++;      }      // If are at the end of the buffer there is a problem with the document      if (i >= buffer.length) throw new Error('Bad BSON Document: illegal CString');      // Return the C string      source = buffer.toString('utf8', index, i);      index = i + 1;      // Get the start search index      i = index;      // Locate the end of the c string      while (buffer[i] !== 0x00 && i < buffer.length) {        i++;      }      // If are at the end of the buffer there is a problem with the document      if (i >= buffer.length) throw new Error('Bad BSON Document: illegal CString');      // Return the C string      regExpOptions = buffer.toString('utf8', index, i);      index = i + 1;      // Set the object      object[name] = new BSONRegExp(source, regExpOptions);    } else if (elementType === BSON.BSON_DATA_SYMBOL) {      stringSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      if (        stringSize <= 0 ||        stringSize > buffer.length - index ||        buffer[index + stringSize - 1] !== 0      )        throw new Error('bad string length in bson');      object[name] = new Symbol(buffer.toString('utf8', index, index + stringSize - 1));      index = index + stringSize;    } else if (elementType === BSON.BSON_DATA_TIMESTAMP) {      lowBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      highBits =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      object[name] = new Timestamp(lowBits, highBits);    } else if (elementType === BSON.BSON_DATA_MIN_KEY) {      object[name] = new MinKey();    } else if (elementType === BSON.BSON_DATA_MAX_KEY) {      object[name] = new MaxKey();    } else if (elementType === BSON.BSON_DATA_CODE) {      stringSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      if (        stringSize <= 0 ||        stringSize > buffer.length - index ||        buffer[index + stringSize - 1] !== 0      )        throw new Error('bad string length in bson');      var functionString = buffer.toString('utf8', index, index + stringSize - 1);      // If we are evaluating the functions      if (evalFunctions) {        // If we have cache enabled let's look for the md5 of the function in the cache        if (cacheFunctions) {          var hash = cacheFunctionsCrc32 ? crc32(functionString) : functionString;          // Got to do this to avoid V8 deoptimizing the call due to finding eval          object[name] = isolateEvalWithHash(functionCache, hash, functionString, object);        } else {          object[name] = isolateEval(functionString);        }      } else {        object[name] = new Code(functionString);      }      // Update parse index position      index = index + stringSize;    } else if (elementType === BSON.BSON_DATA_CODE_W_SCOPE) {      var totalSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      // Element cannot be shorter than totalSize + stringSize + documentSize + terminator      if (totalSize < 4 + 4 + 4 + 1) {        throw new Error('code_w_scope total size shorter minimum expected length');      }      // Get the code string size      stringSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      // Check if we have a valid string      if (        stringSize <= 0 ||        stringSize > buffer.length - index ||        buffer[index + stringSize - 1] !== 0      )        throw new Error('bad string length in bson');      // Javascript function      functionString = buffer.toString('utf8', index, index + stringSize - 1);      // Update parse index position      index = index + stringSize;      // Parse the element      _index = index;      // Decode the size of the object document      objectSize =        buffer[index] |        (buffer[index + 1] << 8) |        (buffer[index + 2] << 16) |        (buffer[index + 3] << 24);      // Decode the scope object      var scopeObject = deserializeObject(buffer, _index, options, false);      // Adjust the index      index = index + objectSize;      // Check if field length is to short      if (totalSize < 4 + 4 + objectSize + stringSize) {        throw new Error('code_w_scope total size is to short, truncating scope');      }      // Check if totalSize field is to long      if (totalSize > 4 + 4 + objectSize + stringSize) {        throw new Error('code_w_scope total size is to long, clips outer document');      }      // If we are evaluating the functions      if (evalFunctions) {        // If we have cache enabled let's look for the md5 of the function in the cache        if (cacheFunctions) {          hash = cacheFunctionsCrc32 ? crc32(functionString) : functionString;          // Got to do this to avoid V8 deoptimizing the call due to finding eval          object[name] = isolateEvalWithHash(functionCache, hash, functionString, object);        } else {          object[name] = isolateEval(functionString);        }        object[name].scope = scopeObject;      } else {        object[name] = new Code(functionString, scopeObject);      }    } else if (elementType === BSON.BSON_DATA_DBPOINTER) {      // Get the code string size      stringSize =        buffer[index++] |        (buffer[index++] << 8) |        (buffer[index++] << 16) |        (buffer[index++] << 24);      // Check if we have a valid string      if (        stringSize <= 0 ||        stringSize > buffer.length - index ||        buffer[index + stringSize - 1] !== 0      )        throw new Error('bad string length in bson');      // Namespace      var namespace = buffer.toString('utf8', index, index + stringSize - 1);      // Update parse index position      index = index + stringSize;      // Read the oid      var oidBuffer = new Buffer(12);      buffer.copy(oidBuffer, 0, index, index + 12);      oid = new ObjectID(oidBuffer);      // Update the index      index = index + 12;      // Split the namespace      var parts = namespace.split('.');      var db = parts.shift();      var collection = parts.join('.');      // Upgrade to DBRef type      object[name] = new DBRef(collection, oid, db);    } else {      throw new Error(        'Detected unknown BSON type ' +          elementType.toString(16) +          ' for fieldname "' +          name +          '", are you using the latest BSON parser'      );    }  }  // Check if the deserialization was against a valid array/object  if (size !== index - startIndex) {    if (isArray) throw new Error('corrupt array bson');    throw new Error('corrupt object bson');  }  // Check if we have a db ref object  if (object['$id'] != null) object = new DBRef(object['$ref'], object['$id'], object['$db']);  return object;};/** * Ensure eval is isolated. * * @ignore * @api private */var isolateEvalWithHash = function(functionCache, hash, functionString, object) {  // Contains the value we are going to set  var value = null;  // Check for cache hit, eval if missing and return cached function  if (functionCache[hash] == null) {    eval('value = ' + functionString);    functionCache[hash] = value;  }  // Set the object  return functionCache[hash].bind(object);};/** * Ensure eval is isolated. * * @ignore * @api private */var isolateEval = function(functionString) {  // Contains the value we are going to set  var value = null;  // Eval the function  eval('value = ' + functionString);  return value;};var BSON = {};/** * Contains the function cache if we have that enable to allow for avoiding the eval step on each deserialization, comparison is by md5 * * @ignore * @api private */var functionCache = (BSON.functionCache = {});/** * Number BSON Type * * @classconstant BSON_DATA_NUMBER **/BSON.BSON_DATA_NUMBER = 1;/** * String BSON Type * * @classconstant BSON_DATA_STRING **/BSON.BSON_DATA_STRING = 2;/** * Object BSON Type * * @classconstant BSON_DATA_OBJECT **/BSON.BSON_DATA_OBJECT = 3;/** * Array BSON Type * * @classconstant BSON_DATA_ARRAY **/BSON.BSON_DATA_ARRAY = 4;/** * Binary BSON Type * * @classconstant BSON_DATA_BINARY **/BSON.BSON_DATA_BINARY = 5;/** * Binary BSON Type * * @classconstant BSON_DATA_UNDEFINED **/BSON.BSON_DATA_UNDEFINED = 6;/** * ObjectID BSON Type * * @classconstant BSON_DATA_OID **/BSON.BSON_DATA_OID = 7;/** * Boolean BSON Type * * @classconstant BSON_DATA_BOOLEAN **/BSON.BSON_DATA_BOOLEAN = 8;/** * Date BSON Type * * @classconstant BSON_DATA_DATE **/BSON.BSON_DATA_DATE = 9;/** * null BSON Type * * @classconstant BSON_DATA_NULL **/BSON.BSON_DATA_NULL = 10;/** * RegExp BSON Type * * @classconstant BSON_DATA_REGEXP **/BSON.BSON_DATA_REGEXP = 11;/** * Code BSON Type * * @classconstant BSON_DATA_DBPOINTER **/BSON.BSON_DATA_DBPOINTER = 12;/** * Code BSON Type * * @classconstant BSON_DATA_CODE **/BSON.BSON_DATA_CODE = 13;/** * Symbol BSON Type * * @classconstant BSON_DATA_SYMBOL **/BSON.BSON_DATA_SYMBOL = 14;/** * Code with Scope BSON Type * * @classconstant BSON_DATA_CODE_W_SCOPE **/BSON.BSON_DATA_CODE_W_SCOPE = 15;/** * 32 bit Integer BSON Type * * @classconstant BSON_DATA_INT **/BSON.BSON_DATA_INT = 16;/** * Timestamp BSON Type * * @classconstant BSON_DATA_TIMESTAMP **/BSON.BSON_DATA_TIMESTAMP = 17;/** * Long BSON Type * * @classconstant BSON_DATA_LONG **/BSON.BSON_DATA_LONG = 18;/** * Long BSON Type * * @classconstant BSON_DATA_DECIMAL128 **/BSON.BSON_DATA_DECIMAL128 = 19;/** * MinKey BSON Type * * @classconstant BSON_DATA_MIN_KEY **/BSON.BSON_DATA_MIN_KEY = 0xff;/** * MaxKey BSON Type * * @classconstant BSON_DATA_MAX_KEY **/BSON.BSON_DATA_MAX_KEY = 0x7f;/** * Binary Default Type * * @classconstant BSON_BINARY_SUBTYPE_DEFAULT **/BSON.BSON_BINARY_SUBTYPE_DEFAULT = 0;/** * Binary Function Type * * @classconstant BSON_BINARY_SUBTYPE_FUNCTION **/BSON.BSON_BINARY_SUBTYPE_FUNCTION = 1;/** * Binary Byte Array Type * * @classconstant BSON_BINARY_SUBTYPE_BYTE_ARRAY **/BSON.BSON_BINARY_SUBTYPE_BYTE_ARRAY = 2;/** * Binary UUID Type * * @classconstant BSON_BINARY_SUBTYPE_UUID **/BSON.BSON_BINARY_SUBTYPE_UUID = 3;/** * Binary MD5 Type * * @classconstant BSON_BINARY_SUBTYPE_MD5 **/BSON.BSON_BINARY_SUBTYPE_MD5 = 4;/** * Binary User Defined Type * * @classconstant BSON_BINARY_SUBTYPE_USER_DEFINED **/BSON.BSON_BINARY_SUBTYPE_USER_DEFINED = 128;// BSON MAX VALUESBSON.BSON_INT32_MAX = 0x7fffffff;BSON.BSON_INT32_MIN = -0x80000000;BSON.BSON_INT64_MAX = Math.pow(2, 63) - 1;BSON.BSON_INT64_MIN = -Math.pow(2, 63);// JS MAX PRECISE VALUESBSON.JS_INT_MAX = 0x20000000000000; // Any integer up to 2^53 can be precisely represented by a double.BSON.JS_INT_MIN = -0x20000000000000; // Any integer down to -2^53 can be precisely represented by a double.// Internal long versionsvar JS_INT_MAX_LONG = Long.fromNumber(0x20000000000000); // Any integer up to 2^53 can be precisely represented by a double.var JS_INT_MIN_LONG = Long.fromNumber(-0x20000000000000); // Any integer down to -2^53 can be precisely represented by a double.module.exports = deserialize;
 |