@@ -9,8 +9,15 @@ import Base64Decoder from 'xterm-wasm-parts/lib/base64/Base64Decoder.wasm';
99import { HeaderParser , IHeaderFields , HeaderState } from './IIPHeaderParser' ;
1010import { imageType , UNSUPPORTED_TYPE } from './IIPMetrics' ;
1111
12- // limit hold memory in base64 decoder
13- const KEEP_DATA = 4194304 ;
12+ // Local const enum mirror - esbuild can't inline const enums from external packages
13+ const enum DecoderConst {
14+ // Limit held memory in base64 decoder (encoded bytes).
15+ KEEP_DATA = 4194304 ,
16+ // Initial buffer allocation for the decoder.
17+ INITIAL_DATA = 1048576 ,
18+ // Local mirror of const enum (esbuild can't inline const enums from external packages)
19+ OK = 0
20+ }
1421
1522// default IIP header values
1623const DEFAULT_HEADER : IHeaderFields = {
@@ -27,15 +34,19 @@ export class IIPHandler implements IOscHandler, IResetHandler {
2734 private _aborted = false ;
2835 private _hp = new HeaderParser ( ) ;
2936 private _header : IHeaderFields = DEFAULT_HEADER ;
30- private _dec = new Base64Decoder ( KEEP_DATA ) ;
37+ private _dec : Base64Decoder ;
3138 private _metrics = UNSUPPORTED_TYPE ;
3239
3340 constructor (
3441 private readonly _opts : IImageAddonOptions ,
3542 private readonly _renderer : ImageRenderer ,
3643 private readonly _storage : ImageStorage ,
3744 private readonly _coreTerminal : ITerminalExt
38- ) { }
45+ ) {
46+ const maxEncodedBytes = Math . ceil ( this . _opts . iipSizeLimit * 4 / 3 ) ;
47+ const initialBytes = Math . min ( DecoderConst . INITIAL_DATA , maxEncodedBytes ) ;
48+ this . _dec = new Base64Decoder ( DecoderConst . KEEP_DATA , maxEncodedBytes , initialBytes ) ;
49+ }
3950
4051 public reset ( ) : void { }
4152
@@ -50,7 +61,7 @@ export class IIPHandler implements IOscHandler, IResetHandler {
5061 if ( this . _aborted ) return ;
5162
5263 if ( this . _hp . state === HeaderState . END ) {
53- if ( this . _dec . put ( data , start , end ) ) {
64+ if ( ( this . _dec . put ( data . subarray ( start , end ) ) as number ) !== DecoderConst . OK ) {
5465 this . _dec . release ( ) ;
5566 this . _aborted = true ;
5667 }
@@ -66,8 +77,8 @@ export class IIPHandler implements IOscHandler, IResetHandler {
6677 this . _aborted = true ;
6778 return ;
6879 }
69- this . _dec . init ( this . _header . size ) ;
70- if ( this . _dec . put ( data , dataPos , end ) ) {
80+ this . _dec . init ( ) ;
81+ if ( ( this . _dec . put ( data . subarray ( dataPos , end ) ) as number ) !== DecoderConst . OK ) {
7182 this . _dec . release ( ) ;
7283 this . _aborted = true ;
7384 }
@@ -85,13 +96,15 @@ export class IIPHandler implements IOscHandler, IResetHandler {
8596 let cond : number | boolean = true ;
8697 if ( cond = success ) {
8798 if ( cond = ! this . _dec . end ( ) ) {
88- this . _metrics = imageType ( this . _dec . data8 ) ;
89- if ( cond = this . _metrics . mime !== 'unsupported' ) {
90- w = this . _metrics . width ;
91- h = this . _metrics . height ;
92- if ( cond = w && h && w * h < this . _opts . pixelLimit ) {
93- [ w , h ] = this . _resize ( w , h ) . map ( Math . floor ) ;
94- cond = w && h && w * h < this . _opts . pixelLimit ;
99+ if ( cond = this . _dec . data8 . length === this . _header . size ) {
100+ this . _metrics = imageType ( this . _dec . data8 ) ;
101+ if ( cond = this . _metrics . mime !== 'unsupported' ) {
102+ w = this . _metrics . width ;
103+ h = this . _metrics . height ;
104+ if ( cond = w && h && w * h < this . _opts . pixelLimit ) {
105+ [ w , h ] = this . _resize ( w , h ) . map ( Math . floor ) ;
106+ cond = w && h && w * h < this . _opts . pixelLimit ;
107+ }
95108 }
96109 }
97110 }
0 commit comments