From c717cd919224ef3554d1c2a7bf3b65779943186e Mon Sep 17 00:00:00 2001 From: haad Date: Fri, 22 Jul 2016 19:44:19 +0100 Subject: [PATCH 1/4] :bug: Add support for TypedArrays in IPC. Fixes https://github.com/electron/electron/issues/2104. --- lib/browser/rpc-server.js | 6 +++++- lib/common/api/is-typed-array.js | 16 ++++++++++++++++ lib/renderer/api/remote.js | 9 ++++++++- 3 files changed, 29 insertions(+), 2 deletions(-) create mode 100644 lib/common/api/is-typed-array.js diff --git a/lib/browser/rpc-server.js b/lib/browser/rpc-server.js index 083c5e4d03..2ee14a6659 100644 --- a/lib/browser/rpc-server.js +++ b/lib/browser/rpc-server.js @@ -2,7 +2,7 @@ const electron = require('electron') const v8Util = process.atomBinding('v8_util') -const {ipcMain, isPromise, webContents} = electron +const {ipcMain, isPromise, isTypedArray, webContents} = electron const objectsRegistry = require('./objects-registry') @@ -63,6 +63,8 @@ let valueToMeta = function (sender, value, optimizeSimpleObject = false) { meta.type = 'buffer' } else if (Array.isArray(value)) { meta.type = 'array' + } else if (isTypedArray(value.buffer)) { + meta.type = 'typed-array' } else if (value instanceof Error) { meta.type = 'error' } else if (value instanceof Date) { @@ -149,6 +151,8 @@ const unwrapArgs = function (sender, args) { return unwrapArgs(sender, meta.value) case 'buffer': return new Buffer(meta.value) + case 'typed-array': + return Buffer.from(meta.value) case 'date': return new Date(meta.value) case 'promise': diff --git a/lib/common/api/is-typed-array.js b/lib/common/api/is-typed-array.js new file mode 100644 index 0000000000..85432debb9 --- /dev/null +++ b/lib/common/api/is-typed-array.js @@ -0,0 +1,16 @@ +'use strict' + +module.exports = function isTypedArray(val) { + return ( + val && + (val instanceof Int8Array + || val instanceof Int16Array + || val instanceof Int32Array + || val instanceof Uint8Array + || val instanceof Uint8ClampedArray + || val instanceof Uint16Array + || val instanceof Uint32Array + || val instanceof Float32Array + || val instanceof Float64Array) + ) +} \ No newline at end of file diff --git a/lib/renderer/api/remote.js b/lib/renderer/api/remote.js index 40f067f340..30b94e9884 100644 --- a/lib/renderer/api/remote.js +++ b/lib/renderer/api/remote.js @@ -1,7 +1,7 @@ 'use strict' const v8Util = process.atomBinding('v8_util') -const {ipcRenderer, isPromise, CallbacksRegistry} = require('electron') +const {ipcRenderer, isPromise, isTypedArray, CallbacksRegistry} = require('electron') const callbacksRegistry = new CallbacksRegistry() @@ -35,6 +35,11 @@ const wrapArgs = function (args, visited) { type: 'buffer', value: Array.prototype.slice.call(value, 0) } + } else if (isTypedArray(value.buffer)) { + return { + type: 'typed-array', + value: Array.prototype.slice.call(value) + } } else if (value instanceof Date) { return { type: 'date', @@ -164,6 +169,8 @@ const metaToValue = function (meta) { return results case 'buffer': return new Buffer(meta.value) + case 'typed-array': + return Buffer.from(meta.value) case 'promise': return Promise.resolve({ then: metaToValue(meta.then) From e6c8900a18261da517df08c9e0e1e76386ed629f Mon Sep 17 00:00:00 2001 From: haad Date: Fri, 22 Jul 2016 20:20:24 +0100 Subject: [PATCH 2/4] Fix linting --- lib/common/api/is-typed-array.js | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/lib/common/api/is-typed-array.js b/lib/common/api/is-typed-array.js index 85432debb9..41ca2d9f4b 100644 --- a/lib/common/api/is-typed-array.js +++ b/lib/common/api/is-typed-array.js @@ -1,16 +1,16 @@ 'use strict' -module.exports = function isTypedArray(val) { +module.exports = function isTypedArray (val) { return ( val && - (val instanceof Int8Array - || val instanceof Int16Array - || val instanceof Int32Array - || val instanceof Uint8Array - || val instanceof Uint8ClampedArray - || val instanceof Uint16Array - || val instanceof Uint32Array - || val instanceof Float32Array - || val instanceof Float64Array) + (val instanceof Int8Array || + val instanceof Int16Array || + val instanceof Int32Array || + val instanceof Uint8Array || + val instanceof Uint8ClampedArray || + val instanceof Uint16Array || + val instanceof Uint32Array || + val instanceof Float32Array || + val instanceof Float64Array) ) -} \ No newline at end of file +} From 2757046e7170946b22bff7ed3e2c9a3c5ed36f57 Mon Sep 17 00:00:00 2001 From: haad Date: Sat, 23 Jul 2016 11:22:30 +0100 Subject: [PATCH 3/4] Add isTypedArray to Electron exports --- filenames.gypi | 1 + lib/common/api/exports/electron.js | 5 +++++ 2 files changed, 6 insertions(+) diff --git a/filenames.gypi b/filenames.gypi index a3a4b6c808..d5381e15b3 100644 --- a/filenames.gypi +++ b/filenames.gypi @@ -44,6 +44,7 @@ 'lib/common/api/deprecate.js', 'lib/common/api/deprecations.js', 'lib/common/api/is-promise.js', + 'lib/common/api/is-typed-array.js', 'lib/common/api/exports/electron.js', 'lib/common/api/native-image.js', 'lib/common/api/shell.js', diff --git a/lib/common/api/exports/electron.js b/lib/common/api/exports/electron.js index efa44d452c..4539649c7f 100644 --- a/lib/common/api/exports/electron.js +++ b/lib/common/api/exports/electron.js @@ -48,6 +48,11 @@ exports.defineProperties = function (exports) { get: function () { return require('../is-promise') } + }, + isTypedArray: { + get: function () { + return require('../is-typed-array') + } } }) } From fac330fb50d1ac9ebc61a1cebfc105a96796195d Mon Sep 17 00:00:00 2001 From: haad Date: Sat, 23 Jul 2016 12:43:49 +0100 Subject: [PATCH 4/4] Fix TypedArray check, add check when instanceof doesn't work for TypedArrays. --- lib/browser/rpc-server.js | 2 +- lib/common/api/is-typed-array.js | 3 ++- lib/renderer/api/remote.js | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/lib/browser/rpc-server.js b/lib/browser/rpc-server.js index 2ee14a6659..6e9d80ed21 100644 --- a/lib/browser/rpc-server.js +++ b/lib/browser/rpc-server.js @@ -63,7 +63,7 @@ let valueToMeta = function (sender, value, optimizeSimpleObject = false) { meta.type = 'buffer' } else if (Array.isArray(value)) { meta.type = 'array' - } else if (isTypedArray(value.buffer)) { + } else if (isTypedArray(value)) { meta.type = 'typed-array' } else if (value instanceof Error) { meta.type = 'error' diff --git a/lib/common/api/is-typed-array.js b/lib/common/api/is-typed-array.js index 41ca2d9f4b..8b63a0cb1b 100644 --- a/lib/common/api/is-typed-array.js +++ b/lib/common/api/is-typed-array.js @@ -11,6 +11,7 @@ module.exports = function isTypedArray (val) { val instanceof Uint16Array || val instanceof Uint32Array || val instanceof Float32Array || - val instanceof Float64Array) + val instanceof Float64Array) || + (Object.prototype.toString.call(val).substr(-6, 5) === 'Array') ) } diff --git a/lib/renderer/api/remote.js b/lib/renderer/api/remote.js index 30b94e9884..ae6564fe0f 100644 --- a/lib/renderer/api/remote.js +++ b/lib/renderer/api/remote.js @@ -35,7 +35,7 @@ const wrapArgs = function (args, visited) { type: 'buffer', value: Array.prototype.slice.call(value, 0) } - } else if (isTypedArray(value.buffer)) { + } else if (isTypedArray(value)) { return { type: 'typed-array', value: Array.prototype.slice.call(value)