From a6321e7201125243edac8b47b103193a0723db3b Mon Sep 17 00:00:00 2001 From: Jonas Jenwald Date: Sun, 31 May 2026 18:52:59 +0200 Subject: [PATCH] Improve the `BaseStream.prototype.clone` implementations - The `dict` field is optional, hence avoid an Error if trying to clone a non-existent dictionary. - Use the `length` getter in the `Stream` class, to avoid duplication. - Fix the `DecodeStream` implementation, since it has a couple of bugs: - The `clone` method currently uses `start`/`end` fields, despite these only existing on `Stream` instances. - Given the previous point, we ended up creating the cloned `Stream` instance using the *entire* underlying `buffer`. This is problematic since the length of a `DecodeStream` cannot be accurately estimated before decoding, and the `buffer`-length is simply a multiple of two. Unless the size of the decoded-data just happens to also be a multiple of two, this causes the cloned `Stream` instance to be "padded" with zeros at the end. --- src/core/base_stream.js | 4 ++++ src/core/decode_stream.js | 15 +++++---------- src/core/stream.js | 4 ++-- 3 files changed, 11 insertions(+), 12 deletions(-) diff --git a/src/core/base_stream.js b/src/core/base_stream.js index bf252b24e..d26d9acd8 100644 --- a/src/core/base_stream.js +++ b/src/core/base_stream.js @@ -135,6 +135,10 @@ class BaseStream { unreachable("Abstract method `makeSubStream` called"); } + clone() { + unreachable("Abstract method `clone` called"); + } + /** * @returns {Array | null} */ diff --git a/src/core/decode_stream.js b/src/core/decode_stream.js index c8edbff22..619d6efc0 100644 --- a/src/core/decode_stream.js +++ b/src/core/decode_stream.js @@ -178,21 +178,16 @@ class DecodeStream extends BaseStream { return new Stream(this.buffer, start, length, dict); } - getBaseStreams() { - return this.stream ? this.stream.getBaseStreams() : null; - } - clone() { // Make sure it has been fully read. while (!this.eof) { this.readBlock(); } - return new Stream( - this.buffer, - this.start, - this.end - this.start, - this.dict.clone() - ); + return new Stream(this.buffer, 0, this.bufferLength, this.dict?.clone()); + } + + getBaseStreams() { + return this.stream ? this.stream.getBaseStreams() : null; } } diff --git a/src/core/stream.js b/src/core/stream.js index 41581f37f..ddb269772 100644 --- a/src/core/stream.js +++ b/src/core/stream.js @@ -88,8 +88,8 @@ class Stream extends BaseStream { return new Stream( this.bytes.buffer, this.start, - this.end - this.start, - this.dict.clone() + this.length, + this.dict?.clone() ); } }