@@ -57,7 +57,6 @@ const { |
57 | 57 | byteLengthUtf8, |
58 | 58 | compare: _compare, |
59 | 59 | compareOffset, |
60 | | - createFromString, |
61 | 60 | fill: bindingFill, |
62 | 61 | isAscii: bindingIsAscii, |
63 | 62 | isUtf8: bindingIsUtf8, |
@@ -148,11 +147,12 @@ const constants = ObjectDefineProperties({}, { |
148 | 147 | }); |
149 | 148 |
|
150 | 149 | Buffer.poolSize = 8 * 1024; |
151 | | -let poolSize, poolOffset, allocPool; |
| 150 | +let poolSize, poolOffset, allocPool, allocBuffer; |
152 | 151 |
|
153 | 152 | function createPool() { |
154 | 153 | poolSize = Buffer.poolSize; |
155 | | - allocPool = createUnsafeBuffer(poolSize).buffer; |
| 154 | + allocBuffer = createUnsafeBuffer(poolSize); |
| 155 | + allocPool = allocBuffer.buffer; |
156 | 156 | markAsUntransferable(allocPool); |
157 | 157 | poolOffset = 0; |
158 | 158 | } |
@@ -440,38 +440,49 @@ function allocate(size) { |
440 | 440 | } |
441 | 441 |
|
442 | 442 | function fromStringFast(string, ops) { |
443 | | - const length = ops.byteLength(string); |
| 443 | + const maxLength = Buffer.poolSize >>> 1; |
444 | 444 |
|
445 | | - if (length >= (Buffer.poolSize >>> 1)) |
446 | | - return createFromString(string, ops.encodingVal); |
| 445 | + let length = string.length; // Min length |
| 446 | + |
| 447 | + if (length >= maxLength) |
| 448 | + return createFromString(string, ops); |
| 449 | + |
| 450 | + length *= 4; // Max length (4 bytes per character) |
| 451 | + |
| 452 | + if (length >= maxLength) |
| 453 | + length = ops.byteLength(string); // Actual length |
| 454 | + |
| 455 | + if (length >= maxLength) |
| 456 | + return createFromString(string, ops, length); |
447 | 457 |
|
448 | 458 | if (length > (poolSize - poolOffset)) |
449 | 459 | createPool(); |
450 | | - let b = new FastBuffer(allocPool, poolOffset, length); |
451 | | - const actual = ops.write(b, string, 0, length); |
452 | | - if (actual !== length) { |
453 | | - // byteLength() may overestimate. That's a rare case, though. |
454 | | - b = new FastBuffer(allocPool, poolOffset, actual); |
455 | | - } |
| 460 | + |
| 461 | + const actual = ops.write(allocBuffer, string, poolOffset, length); |
| 462 | + const b = new FastBuffer(allocPool, poolOffset, actual); |
| 463 | + |
456 | 464 | poolOffset += actual; |
457 | 465 | alignPool(); |
458 | 466 | return b; |
459 | 467 | } |
460 | 468 |
|
| 469 | +function createFromString(string, ops, length = ops.byteLength(string)) { |
| 470 | + const buf = Buffer.allocUnsafeSlow(length); |
| 471 | + const actual = ops.write(buf, string, 0, length); |
| 472 | + return actual < length ? new FastBuffer(buf.buffer, 0, actual) : buf; |
| 473 | +} |
| 474 | + |
461 | 475 | function fromString(string, encoding) { |
462 | 476 | let ops; |
463 | | - if (typeof encoding !== 'string' || encoding.length === 0) { |
464 | | - if (string.length === 0) |
465 | | - return new FastBuffer(); |
| 477 | + if (!encoding || encoding === 'utf8') { |
466 | 478 | ops = encodingOps.utf8; |
467 | 479 | } else { |
468 | 480 | ops = getEncodingOps(encoding); |
469 | 481 | if (ops === undefined) |
470 | 482 | throw new ERR_UNKNOWN_ENCODING(encoding); |
471 | | - if (string.length === 0) |
472 | | - return new FastBuffer(); |
473 | 483 | } |
474 | | - return fromStringFast(string, ops); |
| 484 | + |
| 485 | + return string.length === 0 ? new FastBuffer() : fromStringFast(string, ops); |
475 | 486 | } |
476 | 487 |
|
477 | 488 | function fromArrayBuffer(obj, byteOffset, length) { |
|