Files
node/test/parallel/test-buffer-bytelength-gc.js
Robert Nagy bf246cf4b5 buffer: limit UTF-8 fast calls to safe one-byte strings
Replace the allocating UTF-8 fast call with a fast binding for
sequential one-byte strings. Its slow fallback only returns a Smi
sentinel. JavaScript sends rejected strings to a separate regular
binding that can flatten strings and handle lazy deoptimization.

Both native callbacks used by the fast API avoid JS-heap allocation.
Add GC regression and string-representation coverage, including
optimized fast acceptance and rejection checks.

Fixes: https://github.com/nodejs/node/issues/66870
Refs: https://github.com/nodejs/node/pull/67134
Assisted-by: Codex
Signed-off-by: Robert Nagy <ronagy@icloud.com>
PR-URL: https://github.com/nodejs/node/pull/67136
Refs: https://github.com/nodejs/node/issues/66870
Reviewed-By: Matteo Collina <matteo.collina@gmail.com>
Reviewed-By: Yagiz Nizipli <yagiz@nizipli.com>
Reviewed-By: Anna Henningsen <anna@addaleax.net>
Reviewed-By: Ulises Gascón <ulisesgascongonzalez@gmail.com>
2026-11-01 08:22:55 +00:00

36 lines
1.0 KiB
JavaScript

// Flags: --allow-natives-syntax --gc-global --gc-interval=500
'use strict';
require('../common');
const assert = require('assert');
function byteLength(object, string) {
return object.x + Buffer.byteLength(string);
}
function makeDying() {
const object = { x: 1 };
object.dying = 1;
return object;
}
const keep = { x: 2, keep: 1 };
// The optimized caller holds the dying objects' map weakly. A full GC while
// flattening a cons string can invalidate that map and lazily deoptimize it.
// A value-returning fast API call, including its slow fallback, cannot handle
// that deoptimization and aborts instead.
eval('%PrepareFunctionForOptimization(byteLength)');
for (let i = 0; i < 10; i++) {
byteLength(makeDying(), 'ab');
byteLength(keep, 'ab');
}
eval('%OptimizeFunctionOnNextCall(byteLength)');
assert.strictEqual(byteLength(keep, 'ab'), 4);
const big = 'a'.repeat(1 << 20);
for (let i = 0; i < 50; i++) {
const cons = big + String(i) + big;
assert.strictEqual(byteLength(keep, cons), 2 + cons.length);
}