diff options
Diffstat (limited to 'vendor/github.com/klauspost/compress/huff0/decompress.go')
-rw-r--r-- | vendor/github.com/klauspost/compress/huff0/decompress.go | 31 |
1 files changed, 25 insertions, 6 deletions
diff --git a/vendor/github.com/klauspost/compress/huff0/decompress.go b/vendor/github.com/klauspost/compress/huff0/decompress.go index 261c54274..43b4815b3 100644 --- a/vendor/github.com/klauspost/compress/huff0/decompress.go +++ b/vendor/github.com/klauspost/compress/huff0/decompress.go @@ -193,14 +193,26 @@ func (s *Scratch) Decompress1X(in []byte) (out []byte, err error) { tmp[off+3] = hasDec(dt[br.peekBitsFast(s.actualTableLog)&tlMask]) off += 4 if off == 0 { + if len(s.Out)+256 > s.MaxDecodedSize { + br.close() + return nil, ErrMaxDecodedSizeExceeded + } s.Out = append(s.Out, tmp...) } } + if len(s.Out)+int(off) > s.MaxDecodedSize { + br.close() + return nil, ErrMaxDecodedSizeExceeded + } s.Out = append(s.Out, tmp[:off]...) for !br.finished() { br.fill() + if len(s.Out) >= s.MaxDecodedSize { + br.close() + return nil, ErrMaxDecodedSizeExceeded + } s.Out = append(s.Out, decode()) } return s.Out, br.close() @@ -218,6 +230,9 @@ func (s *Scratch) Decompress4X(in []byte, dstSize int) (out []byte, err error) { if len(in) < 6+(4*1) { return nil, errors.New("input too small") } + if dstSize > s.MaxDecodedSize { + return nil, ErrMaxDecodedSizeExceeded + } // TODO: We do not detect when we overrun a buffer, except if the last one does. var br [4]bitReader @@ -247,9 +262,13 @@ func (s *Scratch) Decompress4X(in []byte, dstSize int) (out []byte, err error) { dstOut := s.Out dstEvery := (dstSize + 3) / 4 + const tlSize = 1 << tableLogMax + const tlMask = tlSize - 1 + single := s.dt.single[:tlSize] + decode := func(br *bitReader) byte { val := br.peekBitsFast(s.actualTableLog) /* note : actualTableLog >= 1 */ - v := s.dt.single[val] + v := single[val&tlMask] br.bitsRead += v.nBits return v.byte } @@ -279,7 +298,7 @@ bigloop: off += 2 if off == bufoff { if bufoff > dstEvery { - return nil, errors.New("corruption detected: stream overrun") + return nil, errors.New("corruption detected: stream overrun 1") } copy(dstOut, tmp[:bufoff]) copy(dstOut[dstEvery:], tmp[bufoff:bufoff*2]) @@ -288,15 +307,15 @@ bigloop: off = 0 dstOut = dstOut[bufoff:] // There must at least be 3 buffers left. - if len(dstOut) < dstEvery*3+3 { - return nil, errors.New("corruption detected: stream overrun") + if len(dstOut) < dstEvery*3 { + return nil, errors.New("corruption detected: stream overrun 2") } } } if off > 0 { ioff := int(off) if len(dstOut) < dstEvery*3+ioff { - return nil, errors.New("corruption detected: stream overrun") + return nil, errors.New("corruption detected: stream overrun 3") } copy(dstOut, tmp[:off]) copy(dstOut[dstEvery:dstEvery+ioff], tmp[bufoff:bufoff*2]) @@ -311,7 +330,7 @@ bigloop: for !br.finished() { br.fill() if offset >= len(dstOut) { - return nil, errors.New("corruption detected: stream overrun") + return nil, errors.New("corruption detected: stream overrun 4") } dstOut[offset] = decode(br) offset++ |