diff options
author | Felix Lange <fjl@twurst.com> | 2015-01-30 23:52:48 +0800 |
---|---|---|
committer | Felix Lange <fjl@twurst.com> | 2015-02-06 07:00:36 +0800 |
commit | 8c3095faf03fb6c8138e6b8691df49be4a6fffae (patch) | |
tree | 0734942413dcc168f0e59b609df4b28eb4ea34a1 | |
parent | 410b35e9135baa86e92bc07e0ef85d04e3ac0561 (diff) | |
download | dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar.gz dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar.bz2 dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar.lz dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar.xz dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.tar.zst dexon-8c3095faf03fb6c8138e6b8691df49be4a6fffae.zip |
rlp: fix encoding of arrays with byte element type
-rw-r--r-- | rlp/encode.go | 22 | ||||
-rw-r--r-- | rlp/encode_test.go | 6 |
2 files changed, 27 insertions, 1 deletions
diff --git a/rlp/encode.go b/rlp/encode.go index d80b66315..b453b5bf4 100644 --- a/rlp/encode.go +++ b/rlp/encode.go @@ -301,8 +301,10 @@ func makeWriter(typ reflect.Type) (writer, error) { return writeUint, nil case kind == reflect.String: return writeString, nil - case kind == reflect.Slice && typ.Elem().Kind() == reflect.Uint8 && !typ.Elem().Implements(encoderInterface): + case kind == reflect.Slice && isByte(typ.Elem()): return writeBytes, nil + case kind == reflect.Array && isByte(typ.Elem()): + return writeByteArray, nil case kind == reflect.Slice || kind == reflect.Array: return makeSliceWriter(typ) case kind == reflect.Struct: @@ -314,6 +316,10 @@ func makeWriter(typ reflect.Type) (writer, error) { } } +func isByte(typ reflect.Type) bool { + return typ.Kind() == reflect.Uint8 && !typ.Implements(encoderInterface) +} + func writeUint(val reflect.Value, w *encbuf) error { i := val.Uint() if i == 0 { @@ -358,6 +364,20 @@ func writeBytes(val reflect.Value, w *encbuf) error { return nil } +func writeByteArray(val reflect.Value, w *encbuf) error { + if !val.CanAddr() { + // Slice requires the value to be addressable. + // Make it addressable by copying. + copy := reflect.New(val.Type()).Elem() + copy.Set(val) + val = copy + } + size := val.Len() + slice := val.Slice(0, size).Bytes() + w.encodeString(slice) + return nil +} + func writeString(val reflect.Value, w *encbuf) error { s := val.String() w.encodeStringHeader(len(s)) diff --git a/rlp/encode_test.go b/rlp/encode_test.go index 18b843737..0309b9258 100644 --- a/rlp/encode_test.go +++ b/rlp/encode_test.go @@ -40,6 +40,8 @@ func (e *encodableReader) Read(b []byte) (int, error) { panic("called") } +type namedByteType byte + var ( _ = Encoder(&testEncoder{}) _ = Encoder(byteEncoder(0)) @@ -102,6 +104,10 @@ var encTests = []encTest{ // byte slices, strings {val: []byte{}, output: "80"}, {val: []byte{1, 2, 3}, output: "83010203"}, + + {val: []namedByteType{1, 2, 3}, output: "83010203"}, + {val: [...]namedByteType{1, 2, 3}, output: "83010203"}, + {val: "", output: "80"}, {val: "dog", output: "83646F67"}, { |