Skip to content

Commit

Permalink
lib: add TypedArray to the primordials
Browse files Browse the repository at this point in the history
This also makes it possible to use Symbol methods and getters.
  • Loading branch information
targos committed May 16, 2020
1 parent c1ee70e commit 95b07ea
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 58 deletions.
18 changes: 5 additions & 13 deletions lib/buffer.js
Expand Up @@ -34,12 +34,11 @@ const {
ObjectCreate,
ObjectDefineProperties,
ObjectDefineProperty,
ObjectGetOwnPropertyDescriptor,
ObjectGetPrototypeOf,
ObjectSetPrototypeOf,
SymbolSpecies,
SymbolToPrimitive,
Uint8ArrayPrototype,
TypedArrayPrototypeByteLength,
TypedArrayPrototypeFill,
} = primordials;

const {
Expand Down Expand Up @@ -107,13 +106,6 @@ const {
addBufferPrototypeMethods
} = require('internal/buffer');

const TypedArrayPrototype = ObjectGetPrototypeOf(Uint8ArrayPrototype);

const TypedArrayProto_byteLength =
ObjectGetOwnPropertyDescriptor(TypedArrayPrototype,
'byteLength').get;
const TypedArrayFill = TypedArrayPrototype.fill;

FastBuffer.prototype.constructor = Buffer;
Buffer.prototype = FastBuffer.prototype;
addBufferPrototypeMethods(Buffer.prototype);
Expand Down Expand Up @@ -581,7 +573,7 @@ Buffer.concat = function concat(list, length) {
// Zero-fill the remaining bytes if the specified `length` was more than
// the actual total length, i.e. if we have some remaining allocated bytes
// there were not initialized.
TypedArrayFill.call(buffer, 0, pos, length);
TypedArrayPrototypeFill(buffer, 0, pos, length);
}

return buffer;
Expand Down Expand Up @@ -1020,12 +1012,12 @@ function _fill(buf, value, offset, end, encoding) {

if (typeof value === 'number') {
// OOB check
const byteLen = TypedArrayProto_byteLength.call(buf);
const byteLen = TypedArrayPrototypeByteLength(buf);
const fillLength = end - offset;
if (offset > end || fillLength + offset > byteLen)
throw new ERR_BUFFER_OUT_OF_BOUNDS();

TypedArrayFill.call(buf, value, offset, end);
TypedArrayPrototypeFill(buf, value, offset, end);
} else {
const res = bindingFill(buf, value, offset, end, encoding);
if (res < 0) {
Expand Down
33 changes: 24 additions & 9 deletions lib/internal/per_context/primordials.js
Expand Up @@ -65,16 +65,22 @@ function copyPropsRenamedBound(src, dest, prefix) {

function copyPrototype(src, dest, prefix) {
for (const key of Reflect.ownKeys(src)) {
if (typeof key === 'string') {
const desc = Reflect.getOwnPropertyDescriptor(src, key);
if (typeof desc.value === 'function') {
desc.value = uncurryThis(desc.value);
}
Reflect.defineProperty(
dest,
`${prefix}${key[0].toUpperCase()}${key.slice(1)}`,
desc);
let newKey;
if (typeof key === 'symbol') {
const name = key.description.slice(7);
newKey = `${prefix}Symbol${name[0].toUpperCase()}${name.slice(1)}`;
} else {
newKey = `${prefix}${key[0].toUpperCase()}${key.slice(1)}`;
}
const desc = Reflect.getOwnPropertyDescriptor(src, key);
if (typeof desc.value === 'function') {
desc.value = uncurryThis(desc.value);
} else if (typeof desc.get === 'function') {
desc.value = uncurryThis(desc.get);
delete desc.get;
delete desc.set;
}
Reflect.defineProperty(dest, newKey, desc);
}
}

Expand Down Expand Up @@ -163,5 +169,14 @@ primordials.SafePromise = makeSafe(
copyPrototype(original.prototype, primordials, `${name}Prototype`);
});

// Create copies of objects that are not immediately available on `globalThis`.
[
['TypedArray', Object.getPrototypeOf(Uint8Array)]
].forEach(([name, original]) => {
primordials[name] = original;
copyPropsRenamed(original, primordials, name);
copyPrototype(original.prototype, primordials, `${name}Prototype`);
});

Object.setPrototypeOf(primordials, null);
Object.freeze(primordials);
19 changes: 6 additions & 13 deletions lib/internal/util/inspect.js
Expand Up @@ -14,8 +14,8 @@ const {
Float32Array,
JSONStringify,
Map,
MapPrototype,
MapPrototypeEntries,
MapPrototypeSize,
MathFloor,
MathMax,
MathMin,
Expand All @@ -39,13 +39,14 @@ const {
RegExp,
RegExpPrototypeToString,
Set,
SetPrototype,
SetPrototypeSize,
SetPrototypeValues,
StringPrototypeValueOf,
SymbolPrototypeToString,
SymbolPrototypeValueOf,
SymbolIterator,
SymbolToStringTag,
TypedArrayPrototypeLength,
Uint16Array,
uncurryThis,
} = primordials;
Expand Down Expand Up @@ -120,14 +121,6 @@ const assert = require('internal/assert');

const { NativeModule } = require('internal/bootstrap/loaders');

const setSizeGetter = uncurryThis(
ObjectGetOwnPropertyDescriptor(SetPrototype, 'size').get);
const mapSizeGetter = uncurryThis(
ObjectGetOwnPropertyDescriptor(MapPrototype, 'size').get);
const typedArraySizeGetter = uncurryThis(
ObjectGetOwnPropertyDescriptor(
ObjectGetPrototypeOf(Uint8Array.prototype), 'length').get);

let hexSlice;

const builtInObjects = new Set(
Expand Down Expand Up @@ -802,7 +795,7 @@ function formatRaw(ctx, value, recurseTimes, typedArray) {
extrasType = kArrayExtrasType;
formatter = formatArray;
} else if (isSet(value)) {
const size = setSizeGetter(value);
const size = SetPrototypeSize(value);
const prefix = getPrefix(constructor, tag, 'Set', `(${size})`);
keys = getKeys(value, ctx.showHidden);
formatter = constructor !== null ?
Expand All @@ -812,7 +805,7 @@ function formatRaw(ctx, value, recurseTimes, typedArray) {
return `${prefix}{}`;
braces = [`${prefix}{`, '}'];
} else if (isMap(value)) {
const size = mapSizeGetter(value);
const size = MapPrototypeSize(value);
const prefix = getPrefix(constructor, tag, 'Map', `(${size})`);
keys = getKeys(value, ctx.showHidden);
formatter = constructor !== null ?
Expand All @@ -831,7 +824,7 @@ function formatRaw(ctx, value, recurseTimes, typedArray) {
// Reconstruct the array information.
bound = new constr(value);
}
const size = typedArraySizeGetter(value);
const size = TypedArrayPrototypeLength(value);
const prefix = getPrefix(constructor, tag, fallback, `(${size})`);
braces = [`${prefix}[`, ']'];
if (value.length === 0 && keys.length === 0 && !ctx.showHidden)
Expand Down
36 changes: 13 additions & 23 deletions lib/internal/util/types.js
Expand Up @@ -2,65 +2,55 @@

const {
ArrayBufferIsView,
ObjectGetOwnPropertyDescriptor,
ObjectGetPrototypeOf,
SymbolToStringTag,
uncurryThis,
TypedArrayPrototypeSymbolToStringTag,
} = primordials;

const TypedArrayPrototype = ObjectGetPrototypeOf(Uint8Array.prototype);

const TypedArrayProto_toStringTag =
uncurryThis(
ObjectGetOwnPropertyDescriptor(TypedArrayPrototype,
SymbolToStringTag).get);

function isTypedArray(value) {
return TypedArrayProto_toStringTag(value) !== undefined;
return TypedArrayPrototypeSymbolToStringTag(value) !== undefined;
}

function isUint8Array(value) {
return TypedArrayProto_toStringTag(value) === 'Uint8Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Uint8Array';
}

function isUint8ClampedArray(value) {
return TypedArrayProto_toStringTag(value) === 'Uint8ClampedArray';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Uint8ClampedArray';
}

function isUint16Array(value) {
return TypedArrayProto_toStringTag(value) === 'Uint16Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Uint16Array';
}

function isUint32Array(value) {
return TypedArrayProto_toStringTag(value) === 'Uint32Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Uint32Array';
}

function isInt8Array(value) {
return TypedArrayProto_toStringTag(value) === 'Int8Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Int8Array';
}

function isInt16Array(value) {
return TypedArrayProto_toStringTag(value) === 'Int16Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Int16Array';
}

function isInt32Array(value) {
return TypedArrayProto_toStringTag(value) === 'Int32Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Int32Array';
}

function isFloat32Array(value) {
return TypedArrayProto_toStringTag(value) === 'Float32Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Float32Array';
}

function isFloat64Array(value) {
return TypedArrayProto_toStringTag(value) === 'Float64Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'Float64Array';
}

function isBigInt64Array(value) {
return TypedArrayProto_toStringTag(value) === 'BigInt64Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'BigInt64Array';
}

function isBigUint64Array(value) {
return TypedArrayProto_toStringTag(value) === 'BigUint64Array';
return TypedArrayPrototypeSymbolToStringTag(value) === 'BigUint64Array';
}

module.exports = {
Expand Down

0 comments on commit 95b07ea

Please sign in to comment.