fixed some fuzz test failure · fusiyuan2010/CSC@3f0b586 (original) (raw)
`@@ -11,7 +11,7 @@
`
11
11
` coder->rc_range_<<=8;\
`
12
12
` coder->rc_code_=(coder->rc_code_<<8)+*coder->prc_++;\
`
13
13
` coder->rc_size_++;\
`
14
``
`-
if (coder->rc_size_==coder->rc_bufsize_) {\
`
``
14
`+
if (coder->rc_size_>=coder->rc_bufsize_) {\
`
15
15
` coder->outsize_+=coder->rc_size_;\
`
16
16
`if (coder->io_->ReadRCData(coder->rc_buf_,coder->rc_bufsize_) < 0)\
`
17
17
`throw (int)READ_ERROR;\
`
`@@ -63,7 +63,7 @@ class CSCDecoder
`
63
63
`{
`
64
64
`uint32_t coder_decode_direct(uint32_t len) {
`
65
65
``
66
``
`-
#define BCRCheckBound() do{if (bc_size_ == bc_bufsize_) \
`
``
66
`+
#define BCRCheckBound() do{if (bc_size_ >= bc_bufsize_) \
`
67
67
` {\
`
68
68
` outsize_ += bc_size_;\
`
69
69
`if (io_->ReadBCData(bc_buf_, bc_bufsize_) < 0)\
`
`@@ -94,13 +94,19 @@ class CSCDecoder
`
94
94
`return num;
`
95
95
` }
`
96
96
``
97
``
`-
void decode_bad(uint8_t *dst, uint32_t *size) {
`
``
97
`+
int decode_bad(uint8_t *dst, uint32_t *size, uint32_t max_bsize) {
`
98
98
` *size = decode_int();
`
99
``
`-
for(uint32_t i = 0; i < *size; i++)
`
``
99
`+
if (*size > max_bsize) {
`
``
100
`+
return -1;
`
``
101
`+
}
`
``
102
+
``
103
`+
for(uint32_t i = 0; i < *size; i++) {
`
100
104
` dst[i] = coder_decode_direct(8);
`
``
105
`+
}
`
``
106
`+
return 0;
`
101
107
` }
`
102
108
``
103
``
`-
void decode_rle(uint8_t *dst, uint32_t *size) {
`
``
109
`+
int decode_rle(uint8_t *dst, uint32_t *size, uint32_t max_bsize) {
`
104
110
`uint32_t c, flag, len, i;
`
105
111
`uint32_t sCtx = 0;
`
106
112
`uint32_t *p=NULL;
`
`@@ -112,6 +118,10 @@ class CSCDecoder
`
112
118
` }
`
113
119
``
114
120
` *size = decode_int();
`
``
121
`+
if (*size > max_bsize) {
`
``
122
`+
return -1;
`
``
123
`+
}
`
``
124
+
115
125
`for (i = 0; i < *size; ) {
`
116
126
` flag=0;
`
117
127
`DecodeBit(this, flag, p_rle_flag_);
`
`@@ -126,13 +136,19 @@ class CSCDecoder
`
126
136
` i++;
`
127
137
` } else {
`
128
138
` len = decode_matchlen_2() + 11;
`
``
139
`+
if (i == 0) {
`
``
140
`+
// invalid compression stream
`
``
141
`+
return -1;
`
``
142
`+
}
`
``
143
+
129
144
`while(len-- > 0) {
`
130
145
` dst[i] = dst[i-1];
`
131
146
` i++;
`
132
147
` }
`
133
148
`sCtx = dst[i-1];
`
134
149
` }
`
135
150
` }
`
``
151
`+
return 0;
`
136
152
` }
`
137
153
``
138
154
`uint32_t decode_literal() {
`
`@@ -149,8 +165,12 @@ class CSCDecoder
`
149
165
`return ctx_;
`
150
166
` }
`
151
167
``
152
``
`-
void decode_literals(uint8_t *dst, uint32_t *size) {
`
``
168
`+
int decode_literals(uint8_t *dst, uint32_t *size, uint32_t max_bsize) {
`
153
169
` *size = decode_int();
`
``
170
`+
if (*size > max_bsize) {
`
``
171
`+
return -1;
`
``
172
`+
}
`
``
173
+
154
174
`for(uint32_t i = 0; i < *size; i++) {
`
155
175
`uint32_t c = 1, *p;
`
156
176
` p = &p_lit_[ctx_ * 256];
`
`@@ -160,6 +180,7 @@ class CSCDecoder
`
160
180
` ctx_ = c & 0xFF;
`
161
181
` dst[i] = ctx_;
`
162
182
` }
`
``
183
`+
return 0;
`
163
184
` }
`
164
185
``
165
186
`uint32_t decode_matchlen_1() {
`
`@@ -309,8 +330,9 @@ class CSCDecoder
`
309
330
`if (!prc_ || !pbc_)
`
310
331
`goto FREE_ON_ERROR;
`
311
332
``
312
``
`-
io_->ReadRCData(rc_buf_, rc_bufsize_);
`
313
``
`-
io_->ReadBCData(bc_buf_, bc_bufsize_);
`
``
333
`+
if (io_->ReadRCData(rc_buf_, rc_bufsize_) < 0 ||
`
``
334
`+
io_->ReadBCData(bc_buf_, bc_bufsize_) < 0)
`
``
335
`+
goto FREE_ON_ERROR;
`
314
336
``
315
337
` rc_code_ = ((uint32_t)prc_[1] << 24)
`
316
338
` | ((uint32_t)prc_[2] << 16)
`
`@@ -375,6 +397,10 @@ class CSCDecoder
`
375
397
` filters_->Destroy();
`
376
398
`delete filters_;
`
377
399
` }
`
``
400
`+
p_lit_ = p_delta_ = NULL;
`
``
401
`+
wnd_ = NULL;
`
``
402
`+
rc_buf_ = bc_buf_ = NULL;
`
``
403
`+
filters_ = NULL;
`
378
404
` }
`
379
405
``
380
406
`int Decompress(uint8_t *dst, uint32_t *size, uint32_t max_bsize);
`
`@@ -450,22 +476,23 @@ int CSCDecoder::lz_decode(uint8_t *dst, uint32_t *size, uint32_t limit)
`
450
476
`uint32_t i;
`
451
477
``
452
478
`for(i = 0; i <= limit; ) {
`
453
``
`-
uint32_t v=0;
`
``
479
`+
uint32_t v = 0;
`
454
480
`DecodeBit(this, v, p_state_[state_ *3 + 0]);
`
455
``
`-
if (v==0) {
`
``
481
`+
if (v == 0) {
`
456
482
` wnd_[wnd_curpos_++] = decode_literal();
`
457
483
` i++;
`
458
484
` } else {
`
459
``
`-
v=0;
`
``
485
`+
v = 0;
`
460
486
`DecodeBit(this ,v, p_state_[state_ * 3 + 1]);
`
461
487
``
462
488
`uint32_t dist, len, cpy_pos;
`
463
489
`uint8_t *cpy_src ,*cpy_dst;
`
464
490
`if (v == 1) {
`
465
491
`decode_match(dist, len);
`
466
``
`-
if (len == 0 && dist == 64)
`
``
492
`+
if (len == 0 && dist == 64) {
`
467
493
`// End of a block
`
468
494
`break;
`
``
495
`+
}
`
469
496
` dist++;
`
470
497
` len += 2;
`
471
498
` rep_dist_[3] = rep_dist_[2];
`
`@@ -474,20 +501,22 @@ int CSCDecoder::lz_decode(uint8_t *dst, uint32_t *size, uint32_t limit)
`
474
501
` rep_dist_[0] = dist;
`
475
502
` cpy_pos = wnd_curpos_ >= dist?
`
476
503
` wnd_curpos_ - dist : wnd_curpos_ + wnd_size_ - dist;
`
477
``
`-
if (cpy_pos > wnd_size_ || cpy_pos + len >wnd_size_ || len + i > limit)
`
``
504
`+
if (cpy_pos >= wnd_size_ || cpy_pos + len > wnd_size_ ||
`
``
505
`+
len + i > limit || wnd_curpos_ + len > wnd_size_)
`
478
506
`throw (int)DECODE_ERROR;
`
479
507
``
480
508
` cpy_dst = wnd_ + wnd_curpos_;
`
481
509
` cpy_src = wnd_ + cpy_pos;
`
482
510
` i += len;
`
483
511
` wnd_curpos_ += len;
`
484
``
`-
while(len--)
`
``
512
`+
while(len--) {
`
485
513
` *cpy_dst++ = *cpy_src++;
`
``
514
`+
}
`
486
515
`set_lit_ctx(wnd_[wnd_curpos_ - 1]);
`
487
516
` } else {
`
488
517
` v = 0;
`
489
518
`DecodeBit(this , v, p_state_[state_ * 3 + 2]);
`
490
``
`-
if (v==0) {
`
``
519
`+
if (v == 0) {
`
491
520
`decode_1byte_match();
`
492
521
` cpy_pos = wnd_curpos_ > rep_dist_[0]?
`
493
522
` wnd_curpos_ - rep_dist_[0] : wnd_curpos_ + wnd_size_ - rep_dist_[0];
`
`@@ -498,8 +527,9 @@ int CSCDecoder::lz_decode(uint8_t *dst, uint32_t *size, uint32_t limit)
`
498
527
`uint32_t repdist_idx;
`
499
528
`decode_repdist_match(repdist_idx, len);
`
500
529
` len += 2;
`
501
``
`-
if (len + i > limit)
`
``
530
`+
if (len + i > limit) {
`
502
531
`throw (int)DECODE_ERROR;
`
``
532
`+
}
`
503
533
``
504
534
` dist = rep_dist_[repdist_idx];
`
505
535
`for(int j = repdist_idx ; j > 0; j--)
`
`@@ -508,7 +538,8 @@ int CSCDecoder::lz_decode(uint8_t *dst, uint32_t *size, uint32_t limit)
`
508
538
``
509
539
` cpy_pos = wnd_curpos_ >= dist?
`
510
540
` wnd_curpos_ - dist : wnd_curpos_ + wnd_size_ - dist;
`
511
``
`-
if (cpy_pos + len >wnd_size_ || len + i > limit)
`
``
541
`+
if (cpy_pos >= wnd_size_ || cpy_pos + len > wnd_size_ ||
`
``
542
`+
len + i > limit || wnd_curpos_ + len > wnd_size_)
`
512
543
`throw (int)DECODE_ERROR;
`
513
544
` cpy_dst = wnd_ + wnd_curpos_;
`
514
545
` cpy_src = wnd_ + cpy_pos;
`
`@@ -521,7 +552,9 @@ int CSCDecoder::lz_decode(uint8_t *dst, uint32_t *size, uint32_t limit)
`
521
552
` }
`
522
553
` }
`
523
554
``
524
``
`-
if (wnd_curpos_ >= wnd_size_) {
`
``
555
`+
if (wnd_curpos_ > wnd_size_) {
`
``
556
`+
throw (int)DECODE_ERROR;
`
``
557
`+
} else if (wnd_curpos_ == wnd_size_) {
`
525
558
` wnd_curpos_ = 0;
`
526
559
`memcpy(dst + copied_size ,wnd_ + copied_wndpos, i - copied_size);
`
527
560
` copied_wndpos = 0;
`
`@@ -553,28 +586,35 @@ int CSCDecoder::Decompress(uint8_t *dst, uint32_t *size, uint32_t max_bsize)
`
553
586
`switch (type) {
`
554
587
`case DT_NORMAL:
`
555
588
` ret = lz_decode(dst, size, max_bsize);
`
556
``
`-
if (ret<0)
`
``
589
`+
if (ret < 0)
`
557
590
`return ret;
`
558
591
`break;
`
559
592
`case DT_EXE:
`
560
593
` ret = lz_decode(dst, size, max_bsize);
`
561
``
`-
if (ret<0)
`
``
594
`+
if (ret < 0)
`
562
595
`return ret;
`
563
596
` filters_->Inverse_E89(dst, *size);
`
564
597
`break;
`
565
598
`case DT_ENGTXT:
`
566
599
` *size = decode_int();
`
567
600
` ret = lz_decode(dst, size, max_bsize);
`
568
``
`-
if (ret<0)
`
``
601
`+
if (ret < 0) {
`
569
602
`return ret;
`
``
603
`+
}
`
570
604
` filters_->Inverse_Dict(dst, *size);
`
571
605
`break;
`
572
606
`case DT_BAD:
`
573
``
`-
decode_bad(dst, size);
`
``
607
`+
ret = decode_bad(dst, size, max_bsize);
`
``
608
`+
if (ret < 0) {
`
``
609
`+
return ret;
`
``
610
`+
}
`
574
611
`lz_copy2dict(dst, *size);
`
575
612
`break;
`
576
613
`case DT_ENTROPY:
`
577
``
`-
decode_literals(dst, size);
`
``
614
`+
ret = decode_literals(dst, size, max_bsize);
`
``
615
`+
if (ret < 0) {
`
``
616
`+
return ret;
`
``
617
`+
}
`
578
618
`lz_copy2dict(dst, *size);
`
579
619
`break;
`
580
620
`//case DT_HARD:
`
`@@ -599,9 +639,10 @@ int CSCDecoder::Decompress(uint8_t *dst, uint32_t *size, uint32_t max_bsize)
`
599
639
`default:
`
600
640
`if (type >= DT_DLT && type < DT_DLT + DLT_CHANNEL_MAX) {
`
601
641
`uint32_t chnNum = DltIndex[type - DT_DLT];
`
602
``
`-
decode_rle(dst,size);
`
603
``
`-
//decode_bad(dst, size);
`
604
``
`-
//ret = lz_decode(dst, size, max_bsize);
`
``
642
`+
ret = decode_rle(dst, size, max_bsize);
`
``
643
`+
if (ret<0) {
`
``
644
`+
return ret;
`
``
645
`+
}
`
605
646
` filters_->Inverse_Delta(dst, *size, chnNum);
`
606
647
`lz_copy2dict(dst, *size);
`
607
648
` } else {
`
`@@ -621,8 +662,11 @@ int CSCDecoder::Decompress(uint8_t *dst, uint32_t *size, uint32_t max_bsize)
`
621
662
` bc_curbits_ = bc_curval_ =0;
`
622
663
` prc_ = rc_buf_;
`
623
664
` pbc_ = bc_buf_;
`
624
``
`-
io_->ReadRCData(rc_buf_, rc_bufsize_);
`
625
``
`-
io_->ReadBCData(bc_buf_, bc_bufsize_);
`
``
665
+
``
666
`+
if (io_->ReadRCData(rc_buf_, rc_bufsize_) < 0 ||
`
``
667
`+
io_->ReadBCData(bc_buf_, bc_bufsize_) < 0)
`
``
668
`+
return -1;
`
``
669
+
626
670
` rc_code_ = ((uint32_t)prc_[1] << 24)
`
627
671
` | ((uint32_t)prc_[2] << 16)
`
628
672
` | ((uint32_t)prc_[3] << 8)
`
`@@ -642,13 +686,17 @@ struct CSCInstance
`
642
686
``
643
687
`CSCDecHandle CSCDec_Create(const CSCProps *props, ISeqInStream *instream)
`
644
688
`{
`
645
``
`-
CSCInstance *csc = new CSCInstance();
`
``
689
`+
if (props->dict_size > 1024 * MB) {
`
``
690
`+
return NULL;
`
``
691
`+
}
`
646
692
``
``
693
`+
CSCInstance *csc = new CSCInstance();
`
647
694
` csc->io = new MemIO();
`
648
695
` csc->io->Init(instream, props->csc_blocksize);
`
649
696
` csc->raw_blocksize = props->raw_blocksize;
`
650
697
``
651
698
` csc->decoder = new CSCDecoder();
`
``
699
+
652
700
`if (csc->decoder->Init(csc->io, props->dict_size, props->csc_blocksize) < 0) {
`
653
701
`CSCDec_Destroy((void *)csc);
`
654
702
`return NULL;
`