diff --git a/rlp/encbuffer.go b/rlp/encbuffer.go index 61d8bd059c..5ddb92e87a 100644 --- a/rlp/encbuffer.go +++ b/rlp/encbuffer.go @@ -359,11 +359,16 @@ func (w *EncoderBuffer) ToBytes() []byte { } // AppendToBytes appends the encoded bytes to dst. -func (w *EncoderBuffer) AppendToBytes(dst []byte) []byte { +func (w *EncoderBuffer) AppendToBytes(dst *[]byte) { size := w.buf.size() - out := append(dst, make([]byte, size)...) - w.buf.copyTo(out[len(dst):]) - return out + tmp, length := *dst, len(*dst) + if cap(tmp) >= size+length { + tmp = tmp[:size+length] + } else { + tmp = append(tmp, make([]byte, size)...) + } + *dst = tmp + w.buf.copyTo(tmp[length:]) } // Write appends b directly to the encoder output. diff --git a/rlp/encode_test.go b/rlp/encode_test.go index 314958eb56..16fb8a574c 100644 --- a/rlp/encode_test.go +++ b/rlp/encode_test.go @@ -435,7 +435,7 @@ func TestEncodeToBytes(t *testing.T) { } func TestEncodeAppendToBytes(t *testing.T) { - buffer := make([]byte, 20) + buffer := make([]byte, 3) runEncTests(t, func(val interface{}) ([]byte, error) { w := NewEncoderBuffer(nil) defer w.Flush() @@ -444,8 +444,9 @@ func TestEncodeAppendToBytes(t *testing.T) { if err != nil { return nil, err } - output := w.AppendToBytes(buffer[:0]) - return output, nil + buffer = buffer[:0] + w.AppendToBytes(&buffer) + return buffer, nil }) } diff --git a/trie/hasher.go b/trie/hasher.go index a2a1f5b662..d44a650743 100644 --- a/trie/hasher.go +++ b/trie/hasher.go @@ -181,7 +181,8 @@ func (h *hasher) encodeFullNode(n *fullNode) []byte { // This convention exists because node.encode can only be inlined/escape-analyzed when // called on a concrete receiver type. func (h *hasher) encodedBytes() []byte { - h.tmp = h.encbuf.AppendToBytes(h.tmp[:0]) + h.tmp = h.tmp[:0] + h.encbuf.AppendToBytes(&h.tmp) h.encbuf.Reset(nil) return h.tmp }