diff options
author | Ben Noordhuis <info@bnoordhuis.nl> | 2022-07-15 09:56:04 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-07-15 08:56:04 +0100 |
commit | 1643b9ed1943d2854e3d5c10a3e07eafbe75f051 (patch) | |
tree | d5ca5fd6d3e8a167d0920329cb24c450de8fe40f /lib/v8.js | |
parent | 38f1e2793c1a3ba0e8cec897769ec76ad2f58cf5 (diff) | |
download | node-new-1643b9ed1943d2854e3d5c10a3e07eafbe75f051.tar.gz |
v8: serialize BigInt64Array and BigUint64Array
Teach the serializer about BigInt64Array and BigUint64Array.
I open-coded the type-to-index mapper to stay compatible with the
current wire format without undue code gymnastics.
PR-URL: https://github.com/nodejs/node/pull/43571
Reviewed-By: Ruben Bridgewater <ruben@bridgewater.de>
Reviewed-By: Colin Ihrig <cjihrig@gmail.com>
Reviewed-By: James M Snell <jasnell@gmail.com>
Diffstat (limited to 'lib/v8.js')
-rw-r--r-- | lib/v8.js | 80 |
1 files changed, 46 insertions, 34 deletions
@@ -16,9 +16,8 @@ const { Array, - ArrayBuffer, - ArrayPrototypeForEach, - ArrayPrototypePush, + BigInt64Array, + BigUint64Array, DataView, Error, Float32Array, @@ -27,7 +26,6 @@ const { Int32Array, Int8Array, ObjectPrototypeToString, - SafeMap, Uint16Array, Uint32Array, Uint8Array, @@ -247,29 +245,40 @@ Deserializer.prototype.readRawBytes = function readRawBytes(length) { length); }; -/* Keep track of how to handle different ArrayBufferViews. - * The default Serializer for Node does not use the V8 methods for serializing - * those objects because Node's `Buffer` objects use pooled allocation in many - * cases, and their underlying `ArrayBuffer`s would show up in the - * serialization. Because a) those may contain sensitive data and the user - * may not be aware of that and b) they are often much larger than the `Buffer` - * itself, custom serialization is applied. */ -const arrayBufferViewTypes = [Int8Array, Uint8Array, Uint8ClampedArray, - Int16Array, Uint16Array, Int32Array, Uint32Array, - Float32Array, Float64Array, DataView]; - -const arrayBufferViewTypeToIndex = new SafeMap(); - -{ - const dummy = new ArrayBuffer(); - ArrayPrototypeForEach(arrayBufferViewTypes, (ctor, i) => { - const tag = ObjectPrototypeToString(new ctor(dummy)); - arrayBufferViewTypeToIndex.set(tag, i); - }); +function arrayBufferViewTypeToIndex(abView) { + const type = ObjectPrototypeToString(abView); + if (type === '[object Int8Array]') return 0; + if (type === '[object Uint8Array]') return 1; + if (type === '[object Uint8ClampedArray]') return 2; + if (type === '[object Int16Array]') return 3; + if (type === '[object Uint16Array]') return 4; + if (type === '[object Int32Array]') return 5; + if (type === '[object Uint32Array]') return 6; + if (type === '[object Float32Array]') return 7; + if (type === '[object Float64Array]') return 8; + if (type === '[object DataView]') return 9; + // Index 10 is FastBuffer. + if (type === '[object BigInt64Array]') return 11; + if (type === '[object BigUint64Array]') return 12; + return -1; } -const bufferConstructorIndex = - ArrayPrototypePush(arrayBufferViewTypes, FastBuffer) - 1; +function arrayBufferViewIndexToType(index) { + if (index === 0) return Int8Array; + if (index === 1) return Uint8Array; + if (index === 2) return Uint8ClampedArray; + if (index === 3) return Int16Array; + if (index === 4) return Uint16Array; + if (index === 5) return Int32Array; + if (index === 6) return Uint32Array; + if (index === 7) return Float32Array; + if (index === 8) return Float64Array; + if (index === 9) return DataView; + if (index === 10) return FastBuffer; + if (index === 11) return BigInt64Array; + if (index === 12) return BigUint64Array; + return undefined; +} class DefaultSerializer extends Serializer { constructor() { @@ -285,14 +294,17 @@ class DefaultSerializer extends Serializer { * @returns {void} */ _writeHostObject(abView) { - let i = 0; - if (abView.constructor === Buffer) { - i = bufferConstructorIndex; - } else { - const tag = ObjectPrototypeToString(abView); - i = arrayBufferViewTypeToIndex.get(tag); - - if (i === undefined) { + // Keep track of how to handle different ArrayBufferViews. The default + // Serializer for Node does not use the V8 methods for serializing those + // objects because Node's `Buffer` objects use pooled allocation in many + // cases, and their underlying `ArrayBuffer`s would show up in the + // serialization. Because a) those may contain sensitive data and the user + // may not be aware of that and b) they are often much larger than the + // `Buffer` itself, custom serialization is applied. + let i = 10; // FastBuffer + if (abView.constructor !== Buffer) { + i = arrayBufferViewTypeToIndex(abView); + if (i === -1) { throw new this._getDataCloneError( `Unserializable host object: ${inspect(abView)}`); } @@ -313,7 +325,7 @@ class DefaultDeserializer extends Deserializer { */ _readHostObject() { const typeIndex = this.readUint32(); - const ctor = arrayBufferViewTypes[typeIndex]; + const ctor = arrayBufferViewIndexToType(typeIndex); const byteLength = this.readUint32(); const byteOffset = this._readRawBytes(byteLength); const BYTES_PER_ELEMENT = ctor.BYTES_PER_ELEMENT || 1; |