Skip to content

Commit 2c9a86f

Browse files
committed
buffer: directly use ArrayBuffer as the pool
Make the buffer pool an `ArrayBuffer` which is used directly, speeding up allocation noticeably in some cases. The only drawback happens when creating pool-based `Buffer` instances from strings whose byte lengths got overestimated by `Buffer.byteLength`, e.g. for base64-encoded strings containing whitespace, where two `Buffer` instances are being created. This may also be useful when providing Buffer classes in the future. Benchmark results for `benchmark/buffers/buffer-creation.js`: ``` improvement significant p.value len=1024 type="buffer()" 47.11 % *** 5.202555e-12 len=1024 type="fast-alloc" -3.41 % 3.823226e-01 len=1024 type="fast-alloc-fill" 1.11 % 7.985624e-01 len=1024 type="fast-allocUnsafe" 24.37 % *** 4.264084e-05 len=1024 type="slow" 4.81 % 2.634609e-01 len=1024 type="slow-allocUnsafe" 1.28 % 7.864850e-01 len=10 type="buffer()" 59.42 % *** 9.953552e-13 len=10 type="fast-alloc" -6.43 % 1.450524e-01 len=10 type="fast-alloc-fill" -2.96 % 4.873766e-01 len=10 type="fast-allocUnsafe" 33.89 % *** 6.517268e-07 len=10 type="slow" -1.48 % 7.357711e-01 len=10 type="slow-allocUnsafe" 0.04 % 9.939576e-01 len=2048 type="buffer()" 36.34 % *** 3.201045e-10 len=2048 type="fast-alloc" -4.67 % 2.172900e-01 len=2048 type="fast-alloc-fill" -0.15 % 9.732945e-01 len=2048 type="fast-allocUnsafe" 20.13 % *** 2.372115e-04 len=2048 type="slow" 4.35 % 2.831340e-01 len=2048 type="slow-allocUnsafe" 1.13 % 8.055388e-01 len=4096 type="buffer()" 4.90 % 2.495340e-01 len=4096 type="fast-alloc" -2.11 % 5.417520e-01 len=4096 type="fast-alloc-fill" -0.29 % 9.460378e-01 len=4096 type="fast-allocUnsafe" 3.11 % 5.001959e-01 len=4096 type="slow" 0.95 % 8.145888e-01 len=4096 type="slow-allocUnsafe" 3.74 % 4.227627e-01 len=8192 type="buffer()" 5.08 % 2.263029e-01 len=8192 type="fast-alloc" -1.16 % 7.300235e-01 len=8192 type="fast-alloc-fill" 0.40 % 9.179919e-01 len=8192 type="fast-allocUnsafe" 5.16 % 2.591544e-01 len=8192 type="slow" 2.57 % 5.212449e-01 len=8192 type="slow-allocUnsafe" -3.19 % 4.699138e-01 ``` PR-URL: #8302 Reviewed-By: Trevor Norris <[email protected]> Reviewed-By: James M Snell <[email protected]>
1 parent 3504a98 commit 2c9a86f

File tree

1 file changed

+13
-5
lines changed

1 file changed

+13
-5
lines changed

lib/buffer.js

+13-5
Original file line numberDiff line numberDiff line change
@@ -30,17 +30,21 @@ binding.setupBufferJS(Buffer.prototype, bindingObj);
3030
const zeroFill = bindingObj.zeroFill || [0];
3131

3232
function createUnsafeBuffer(size) {
33+
return new FastBuffer(createUnsafeArrayBuffer(size));
34+
}
35+
36+
function createUnsafeArrayBuffer(size) {
3337
zeroFill[0] = 0;
3438
try {
35-
return new FastBuffer(size);
39+
return new ArrayBuffer(size);
3640
} finally {
3741
zeroFill[0] = 1;
3842
}
3943
}
4044

4145
function createPool() {
4246
poolSize = Buffer.poolSize;
43-
allocPool = createUnsafeBuffer(poolSize);
47+
allocPool = createUnsafeArrayBuffer(poolSize);
4448
poolOffset = 0;
4549
}
4650
createPool();
@@ -183,7 +187,7 @@ function allocate(size) {
183187
if (size < (Buffer.poolSize >>> 1)) {
184188
if (size > (poolSize - poolOffset))
185189
createPool();
186-
var b = allocPool.slice(poolOffset, poolOffset + size);
190+
var b = new FastBuffer(allocPool, poolOffset, size);
187191
poolOffset += size;
188192
alignPool();
189193
return b;
@@ -210,8 +214,12 @@ function fromString(string, encoding) {
210214

211215
if (length > (poolSize - poolOffset))
212216
createPool();
213-
var actual = allocPool.write(string, poolOffset, encoding);
214-
var b = allocPool.slice(poolOffset, poolOffset + actual);
217+
var b = new FastBuffer(allocPool, poolOffset, length);
218+
var actual = b.write(string, encoding);
219+
if (actual !== length) {
220+
// byteLength() may overestimate. That’s a rare case, though.
221+
b = new FastBuffer(allocPool, poolOffset, actual);
222+
}
215223
poolOffset += actual;
216224
alignPool();
217225
return b;

0 commit comments

Comments
 (0)