github.com/theQRL/go-zond@v0.1.1/rlp/encode.go (about) 1 // Copyright 2014 The go-ethereum Authors 2 // This file is part of the go-ethereum library. 3 // 4 // The go-ethereum library is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU Lesser General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // The go-ethereum library is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU Lesser General Public License for more details. 13 // 14 // You should have received a copy of the GNU Lesser General Public License 15 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 16 17 package rlp 18 19 import ( 20 "errors" 21 "fmt" 22 "io" 23 "math/big" 24 "reflect" 25 26 "github.com/holiman/uint256" 27 "github.com/theQRL/go-zond/rlp/internal/rlpstruct" 28 ) 29 30 var ( 31 // Common encoded values. 32 // These are useful when implementing EncodeRLP. 33 34 // EmptyString is the encoding of an empty string. 35 EmptyString = []byte{0x80} 36 // EmptyList is the encoding of an empty list. 37 EmptyList = []byte{0xC0} 38 ) 39 40 var ErrNegativeBigInt = errors.New("rlp: cannot encode negative big.Int") 41 42 // Encoder is implemented by types that require custom 43 // encoding rules or want to encode private fields. 44 type Encoder interface { 45 // EncodeRLP should write the RLP encoding of its receiver to w. 46 // If the implementation is a pointer method, it may also be 47 // called for nil pointers. 48 // 49 // Implementations should generate valid RLP. The data written is 50 // not verified at the moment, but a future version might. It is 51 // recommended to write only a single value but writing multiple 52 // values or no value at all is also permitted. 53 EncodeRLP(io.Writer) error 54 } 55 56 // Encode writes the RLP encoding of val to w. Note that Encode may 57 // perform many small writes in some cases. Consider making w 58 // buffered. 59 // 60 // Please see package-level documentation of encoding rules. 61 func Encode(w io.Writer, val interface{}) error { 62 // Optimization: reuse *encBuffer when called by EncodeRLP. 63 if buf := encBufferFromWriter(w); buf != nil { 64 return buf.encode(val) 65 } 66 67 buf := getEncBuffer() 68 defer encBufferPool.Put(buf) 69 if err := buf.encode(val); err != nil { 70 return err 71 } 72 return buf.writeTo(w) 73 } 74 75 // EncodeToBytes returns the RLP encoding of val. 76 // Please see package-level documentation for the encoding rules. 77 func EncodeToBytes(val interface{}) ([]byte, error) { 78 buf := getEncBuffer() 79 defer encBufferPool.Put(buf) 80 81 if err := buf.encode(val); err != nil { 82 return nil, err 83 } 84 return buf.makeBytes(), nil 85 } 86 87 // EncodeToReader returns a reader from which the RLP encoding of val 88 // can be read. The returned size is the total size of the encoded 89 // data. 90 // 91 // Please see the documentation of Encode for the encoding rules. 92 func EncodeToReader(val interface{}) (size int, r io.Reader, err error) { 93 buf := getEncBuffer() 94 if err := buf.encode(val); err != nil { 95 encBufferPool.Put(buf) 96 return 0, nil, err 97 } 98 // Note: can't put the reader back into the pool here 99 // because it is held by encReader. The reader puts it 100 // back when it has been fully consumed. 101 return buf.size(), &encReader{buf: buf}, nil 102 } 103 104 type listhead struct { 105 offset int // index of this header in string data 106 size int // total size of encoded data (including list headers) 107 } 108 109 // encode writes head to the given buffer, which must be at least 110 // 9 bytes long. It returns the encoded bytes. 111 func (head *listhead) encode(buf []byte) []byte { 112 return buf[:puthead(buf, 0xC0, 0xF7, uint64(head.size))] 113 } 114 115 // headsize returns the size of a list or string header 116 // for a value of the given size. 117 func headsize(size uint64) int { 118 if size < 56 { 119 return 1 120 } 121 return 1 + intsize(size) 122 } 123 124 // puthead writes a list or string header to buf. 125 // buf must be at least 9 bytes long. 126 func puthead(buf []byte, smalltag, largetag byte, size uint64) int { 127 if size < 56 { 128 buf[0] = smalltag + byte(size) 129 return 1 130 } 131 sizesize := putint(buf[1:], size) 132 buf[0] = largetag + byte(sizesize) 133 return sizesize + 1 134 } 135 136 var encoderInterface = reflect.TypeOf(new(Encoder)).Elem() 137 138 // makeWriter creates a writer function for the given type. 139 func makeWriter(typ reflect.Type, ts rlpstruct.Tags) (writer, error) { 140 kind := typ.Kind() 141 switch { 142 case typ == rawValueType: 143 return writeRawValue, nil 144 case typ.AssignableTo(reflect.PtrTo(bigInt)): 145 return writeBigIntPtr, nil 146 case typ.AssignableTo(bigInt): 147 return writeBigIntNoPtr, nil 148 case typ == reflect.PtrTo(u256Int): 149 return writeU256IntPtr, nil 150 case typ == u256Int: 151 return writeU256IntNoPtr, nil 152 case kind == reflect.Ptr: 153 return makePtrWriter(typ, ts) 154 case reflect.PtrTo(typ).Implements(encoderInterface): 155 return makeEncoderWriter(typ), nil 156 case isUint(kind): 157 return writeUint, nil 158 case kind == reflect.Bool: 159 return writeBool, nil 160 case kind == reflect.String: 161 return writeString, nil 162 case kind == reflect.Slice && isByte(typ.Elem()): 163 return writeBytes, nil 164 case kind == reflect.Array && isByte(typ.Elem()): 165 return makeByteArrayWriter(typ), nil 166 case kind == reflect.Slice || kind == reflect.Array: 167 return makeSliceWriter(typ, ts) 168 case kind == reflect.Struct: 169 return makeStructWriter(typ) 170 case kind == reflect.Interface: 171 return writeInterface, nil 172 default: 173 return nil, fmt.Errorf("rlp: type %v is not RLP-serializable", typ) 174 } 175 } 176 177 func writeRawValue(val reflect.Value, w *encBuffer) error { 178 w.str = append(w.str, val.Bytes()...) 179 return nil 180 } 181 182 func writeUint(val reflect.Value, w *encBuffer) error { 183 w.writeUint64(val.Uint()) 184 return nil 185 } 186 187 func writeBool(val reflect.Value, w *encBuffer) error { 188 w.writeBool(val.Bool()) 189 return nil 190 } 191 192 func writeBigIntPtr(val reflect.Value, w *encBuffer) error { 193 ptr := val.Interface().(*big.Int) 194 if ptr == nil { 195 w.str = append(w.str, 0x80) 196 return nil 197 } 198 if ptr.Sign() == -1 { 199 return ErrNegativeBigInt 200 } 201 w.writeBigInt(ptr) 202 return nil 203 } 204 205 func writeBigIntNoPtr(val reflect.Value, w *encBuffer) error { 206 i := val.Interface().(big.Int) 207 if i.Sign() == -1 { 208 return ErrNegativeBigInt 209 } 210 w.writeBigInt(&i) 211 return nil 212 } 213 214 func writeU256IntPtr(val reflect.Value, w *encBuffer) error { 215 ptr := val.Interface().(*uint256.Int) 216 if ptr == nil { 217 w.str = append(w.str, 0x80) 218 return nil 219 } 220 w.writeUint256(ptr) 221 return nil 222 } 223 224 func writeU256IntNoPtr(val reflect.Value, w *encBuffer) error { 225 i := val.Interface().(uint256.Int) 226 w.writeUint256(&i) 227 return nil 228 } 229 230 func writeBytes(val reflect.Value, w *encBuffer) error { 231 w.writeBytes(val.Bytes()) 232 return nil 233 } 234 235 func makeByteArrayWriter(typ reflect.Type) writer { 236 switch typ.Len() { 237 case 0: 238 return writeLengthZeroByteArray 239 case 1: 240 return writeLengthOneByteArray 241 default: 242 length := typ.Len() 243 return func(val reflect.Value, w *encBuffer) error { 244 if !val.CanAddr() { 245 // Getting the byte slice of val requires it to be addressable. Make it 246 // addressable by copying. 247 copy := reflect.New(val.Type()).Elem() 248 copy.Set(val) 249 val = copy 250 } 251 slice := byteArrayBytes(val, length) 252 w.encodeStringHeader(len(slice)) 253 w.str = append(w.str, slice...) 254 return nil 255 } 256 } 257 } 258 259 func writeLengthZeroByteArray(val reflect.Value, w *encBuffer) error { 260 w.str = append(w.str, 0x80) 261 return nil 262 } 263 264 func writeLengthOneByteArray(val reflect.Value, w *encBuffer) error { 265 b := byte(val.Index(0).Uint()) 266 if b <= 0x7f { 267 w.str = append(w.str, b) 268 } else { 269 w.str = append(w.str, 0x81, b) 270 } 271 return nil 272 } 273 274 func writeString(val reflect.Value, w *encBuffer) error { 275 s := val.String() 276 if len(s) == 1 && s[0] <= 0x7f { 277 // fits single byte, no string header 278 w.str = append(w.str, s[0]) 279 } else { 280 w.encodeStringHeader(len(s)) 281 w.str = append(w.str, s...) 282 } 283 return nil 284 } 285 286 func writeInterface(val reflect.Value, w *encBuffer) error { 287 if val.IsNil() { 288 // Write empty list. This is consistent with the previous RLP 289 // encoder that we had and should therefore avoid any 290 // problems. 291 w.str = append(w.str, 0xC0) 292 return nil 293 } 294 eval := val.Elem() 295 writer, err := cachedWriter(eval.Type()) 296 if err != nil { 297 return err 298 } 299 return writer(eval, w) 300 } 301 302 func makeSliceWriter(typ reflect.Type, ts rlpstruct.Tags) (writer, error) { 303 etypeinfo := theTC.infoWhileGenerating(typ.Elem(), rlpstruct.Tags{}) 304 if etypeinfo.writerErr != nil { 305 return nil, etypeinfo.writerErr 306 } 307 308 var wfn writer 309 if ts.Tail { 310 // This is for struct tail slices. 311 // w.list is not called for them. 312 wfn = func(val reflect.Value, w *encBuffer) error { 313 vlen := val.Len() 314 for i := 0; i < vlen; i++ { 315 if err := etypeinfo.writer(val.Index(i), w); err != nil { 316 return err 317 } 318 } 319 return nil 320 } 321 } else { 322 // This is for regular slices and arrays. 323 wfn = func(val reflect.Value, w *encBuffer) error { 324 vlen := val.Len() 325 if vlen == 0 { 326 w.str = append(w.str, 0xC0) 327 return nil 328 } 329 listOffset := w.list() 330 for i := 0; i < vlen; i++ { 331 if err := etypeinfo.writer(val.Index(i), w); err != nil { 332 return err 333 } 334 } 335 w.listEnd(listOffset) 336 return nil 337 } 338 } 339 return wfn, nil 340 } 341 342 func makeStructWriter(typ reflect.Type) (writer, error) { 343 fields, err := structFields(typ) 344 if err != nil { 345 return nil, err 346 } 347 for _, f := range fields { 348 if f.info.writerErr != nil { 349 return nil, structFieldError{typ, f.index, f.info.writerErr} 350 } 351 } 352 353 var writer writer 354 firstOptionalField := firstOptionalField(fields) 355 if firstOptionalField == len(fields) { 356 // This is the writer function for structs without any optional fields. 357 writer = func(val reflect.Value, w *encBuffer) error { 358 lh := w.list() 359 for _, f := range fields { 360 if err := f.info.writer(val.Field(f.index), w); err != nil { 361 return err 362 } 363 } 364 w.listEnd(lh) 365 return nil 366 } 367 } else { 368 // If there are any "optional" fields, the writer needs to perform additional 369 // checks to determine the output list length. 370 writer = func(val reflect.Value, w *encBuffer) error { 371 lastField := len(fields) - 1 372 for ; lastField >= firstOptionalField; lastField-- { 373 if !val.Field(fields[lastField].index).IsZero() { 374 break 375 } 376 } 377 lh := w.list() 378 for i := 0; i <= lastField; i++ { 379 if err := fields[i].info.writer(val.Field(fields[i].index), w); err != nil { 380 return err 381 } 382 } 383 w.listEnd(lh) 384 return nil 385 } 386 } 387 return writer, nil 388 } 389 390 func makePtrWriter(typ reflect.Type, ts rlpstruct.Tags) (writer, error) { 391 nilEncoding := byte(0xC0) 392 if typeNilKind(typ.Elem(), ts) == String { 393 nilEncoding = 0x80 394 } 395 396 etypeinfo := theTC.infoWhileGenerating(typ.Elem(), rlpstruct.Tags{}) 397 if etypeinfo.writerErr != nil { 398 return nil, etypeinfo.writerErr 399 } 400 401 writer := func(val reflect.Value, w *encBuffer) error { 402 if ev := val.Elem(); ev.IsValid() { 403 return etypeinfo.writer(ev, w) 404 } 405 w.str = append(w.str, nilEncoding) 406 return nil 407 } 408 return writer, nil 409 } 410 411 func makeEncoderWriter(typ reflect.Type) writer { 412 if typ.Implements(encoderInterface) { 413 return func(val reflect.Value, w *encBuffer) error { 414 return val.Interface().(Encoder).EncodeRLP(w) 415 } 416 } 417 w := func(val reflect.Value, w *encBuffer) error { 418 if !val.CanAddr() { 419 // package json simply doesn't call MarshalJSON for this case, but encodes the 420 // value as if it didn't implement the interface. We don't want to handle it that 421 // way. 422 return fmt.Errorf("rlp: unaddressable value of type %v, EncodeRLP is pointer method", val.Type()) 423 } 424 return val.Addr().Interface().(Encoder).EncodeRLP(w) 425 } 426 return w 427 } 428 429 // putint writes i to the beginning of b in big endian byte 430 // order, using the least number of bytes needed to represent i. 431 func putint(b []byte, i uint64) (size int) { 432 switch { 433 case i < (1 << 8): 434 b[0] = byte(i) 435 return 1 436 case i < (1 << 16): 437 b[0] = byte(i >> 8) 438 b[1] = byte(i) 439 return 2 440 case i < (1 << 24): 441 b[0] = byte(i >> 16) 442 b[1] = byte(i >> 8) 443 b[2] = byte(i) 444 return 3 445 case i < (1 << 32): 446 b[0] = byte(i >> 24) 447 b[1] = byte(i >> 16) 448 b[2] = byte(i >> 8) 449 b[3] = byte(i) 450 return 4 451 case i < (1 << 40): 452 b[0] = byte(i >> 32) 453 b[1] = byte(i >> 24) 454 b[2] = byte(i >> 16) 455 b[3] = byte(i >> 8) 456 b[4] = byte(i) 457 return 5 458 case i < (1 << 48): 459 b[0] = byte(i >> 40) 460 b[1] = byte(i >> 32) 461 b[2] = byte(i >> 24) 462 b[3] = byte(i >> 16) 463 b[4] = byte(i >> 8) 464 b[5] = byte(i) 465 return 6 466 case i < (1 << 56): 467 b[0] = byte(i >> 48) 468 b[1] = byte(i >> 40) 469 b[2] = byte(i >> 32) 470 b[3] = byte(i >> 24) 471 b[4] = byte(i >> 16) 472 b[5] = byte(i >> 8) 473 b[6] = byte(i) 474 return 7 475 default: 476 b[0] = byte(i >> 56) 477 b[1] = byte(i >> 48) 478 b[2] = byte(i >> 40) 479 b[3] = byte(i >> 32) 480 b[4] = byte(i >> 24) 481 b[5] = byte(i >> 16) 482 b[6] = byte(i >> 8) 483 b[7] = byte(i) 484 return 8 485 } 486 } 487 488 // intsize computes the minimum number of bytes required to store i. 489 func intsize(i uint64) (size int) { 490 for size = 1; ; size++ { 491 if i >>= 8; i == 0 { 492 return size 493 } 494 } 495 }