github.com/fibonacci-chain/fbc@v0.0.0-20231124064014-c7636198c1e9/x/wasm/ioutils/ioutil.go (about) 1 package ioutils 2 3 import ( 4 "bytes" 5 "compress/gzip" 6 "io" 7 "io/ioutil" 8 9 "github.com/fibonacci-chain/fbc/x/wasm/types" 10 ) 11 12 // Uncompress returns gzip uncompressed content if input was gzip, or original src otherwise 13 func Uncompress(src []byte, limit uint64) ([]byte, error) { 14 switch n := uint64(len(src)); { 15 case n < 3: 16 return src, nil 17 case n > limit: 18 return nil, types.ErrLimit 19 } 20 if !bytes.Equal(gzipIdent, src[0:3]) { 21 return src, nil 22 } 23 zr, err := gzip.NewReader(bytes.NewReader(src)) 24 if err != nil { 25 return nil, err 26 } 27 zr.Multistream(false) 28 defer zr.Close() 29 return ioutil.ReadAll(LimitReader(zr, int64(limit))) 30 } 31 32 // LimitReader returns a Reader that reads from r 33 // but stops with types.ErrLimit after n bytes. 34 // The underlying implementation is a *io.LimitedReader. 35 func LimitReader(r io.Reader, n int64) io.Reader { 36 return &LimitedReader{r: &io.LimitedReader{R: r, N: n}} 37 } 38 39 type LimitedReader struct { 40 r *io.LimitedReader 41 } 42 43 func (l *LimitedReader) Read(p []byte) (n int, err error) { 44 if l.r.N <= 0 { 45 return 0, types.ErrLimit 46 } 47 return l.r.Read(p) 48 }