Limit uncompressed content

This commit is contained in:
Alex Peters 2020-01-11 14:53:07 +01:00
parent bf1e51c6aa
commit dfba1699e2
No known key found for this signature in database
GPG Key ID: BD28388D49EE708D
3 changed files with 27 additions and 5 deletions

View File

@ -15,12 +15,13 @@ var gzipIdent = []byte("\x1F\x8B\x08")
// limit max bytes read to prevent gzip bombs
const maxSize = 400 * 1024
// uncompress returns gzip uncompressed content or given src when not gzip.
func uncompress(src []byte) ([]byte, error) {
if len(src) < 3 {
return src, nil
}
in := io.LimitReader(bytes.NewReader(src), maxSize)
in := bytes.NewReader(src)
buf := make([]byte, 3)
if _, err := io.ReadAtLeast(in, buf, 3); err != nil {
return nil, err
@ -34,5 +35,5 @@ func uncompress(src []byte) ([]byte, error) {
}
zr.Multistream(false)
return ioutil.ReadAll(zr)
return ioutil.ReadAll(io.LimitReader(zr, maxSize))
}

View File

@ -1,6 +1,8 @@
package keeper
import (
"bytes"
"compress/gzip"
"errors"
"io"
"io/ioutil"
@ -39,7 +41,7 @@ func TestUncompress(t *testing.T) {
src: []byte{0x1, 0x2},
expResult: []byte{0x1, 0x2},
},
"handle big slice": {
"handle big input slice": {
src: []byte(strings.Repeat("a", maxSize+1)),
expResult: []byte(strings.Repeat("a", maxSize+1)),
},
@ -51,13 +53,32 @@ func TestUncompress(t *testing.T) {
src: append(gzipIdent, byte(0x1)),
expError: io.ErrUnexpectedEOF,
},
"handle incomplete gzip": {
src: wasmGzipped[:len(wasmGzipped)-5],
expError: io.ErrUnexpectedEOF,
},
"handle big gzip output": {
src: asGzip(strings.Repeat("a", maxSize+1)),
expError: io.ErrUnexpectedEOF,
},
}
for msg, spec := range specs {
t.Run(msg, func(t *testing.T) {
r, err := uncompress(spec.src)
require.True(t, errors.Is(spec.expError, err), "exp %+v got %+v", spec.expError, err)
if spec.expError != nil {
return
}
assert.Equal(t, spec.expResult, r)
})
}
}
func asGzip(src string) []byte {
var buf bytes.Buffer
if _, err := io.Copy(gzip.NewWriter(&buf), strings.NewReader(src)); err != nil {
panic(err)
}
return buf.Bytes()
}

View File

@ -9,9 +9,9 @@ const (
)
type MsgStoreCode struct {
Sender sdk.AccAddress `json:"sender" yaml:"sender"`
Sender sdk.AccAddress `json:"sender" yaml:"sender"`
// WASMByteCode can be raw or gzip compressed
WASMByteCode []byte `json:"wasm_byte_code" yaml:"wasm_byte_code"`
WASMByteCode []byte `json:"wasm_byte_code" yaml:"wasm_byte_code"`
}
func (msg MsgStoreCode) Route() string {