github.com/aidoskuneen/adk-node@v0.0.0-20220315131952-2e32567cb7f4/rlp/encode.go (about)

     1  // Copyright 2021 The adkgo Authors
     2  // This file is part of the adkgo library (adapted for adkgo from go--ethereum v1.10.8).
     3  //
     4  // the adkgo 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 adkgo 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 adkgo library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package rlp
    18  
    19  import (
    20  	"fmt"
    21  	"io"
    22  	"math/big"
    23  	"reflect"
    24  	"sync"
    25  )
    26  
    27  var (
    28  	// Common encoded values.
    29  	// These are useful when implementing EncodeRLP.
    30  	EmptyString = []byte{0x80}
    31  	EmptyList   = []byte{0xC0}
    32  )
    33  
    34  // Encoder is implemented by types that require custom
    35  // encoding rules or want to encode private fields.
    36  type Encoder interface {
    37  	// EncodeRLP should write the RLP encoding of its receiver to w.
    38  	// If the implementation is a pointer method, it may also be
    39  	// called for nil pointers.
    40  	//
    41  	// Implementations should generate valid RLP. The data written is
    42  	// not verified at the moment, but a future version might. It is
    43  	// recommended to write only a single value but writing multiple
    44  	// values or no value at all is also permitted.
    45  	EncodeRLP(io.Writer) error
    46  }
    47  
    48  // Encode writes the RLP encoding of val to w. Note that Encode may
    49  // perform many small writes in some cases. Consider making w
    50  // buffered.
    51  //
    52  // Please see package-level documentation of encoding rules.
    53  func Encode(w io.Writer, val interface{}) error {
    54  	if outer, ok := w.(*encbuf); ok {
    55  		// Encode was called by some type's EncodeRLP.
    56  		// Avoid copying by writing to the outer encbuf directly.
    57  		return outer.encode(val)
    58  	}
    59  	eb := encbufPool.Get().(*encbuf)
    60  	defer encbufPool.Put(eb)
    61  	eb.reset()
    62  	if err := eb.encode(val); err != nil {
    63  		return err
    64  	}
    65  	return eb.toWriter(w)
    66  }
    67  
    68  // EncodeToBytes returns the RLP encoding of val.
    69  // Please see package-level documentation for the encoding rules.
    70  func EncodeToBytes(val interface{}) ([]byte, error) {
    71  	eb := encbufPool.Get().(*encbuf)
    72  	defer encbufPool.Put(eb)
    73  	eb.reset()
    74  	if err := eb.encode(val); err != nil {
    75  		return nil, err
    76  	}
    77  	return eb.toBytes(), nil
    78  }
    79  
    80  // EncodeToReader returns a reader from which the RLP encoding of val
    81  // can be read. The returned size is the total size of the encoded
    82  // data.
    83  //
    84  // Please see the documentation of Encode for the encoding rules.
    85  func EncodeToReader(val interface{}) (size int, r io.Reader, err error) {
    86  	eb := encbufPool.Get().(*encbuf)
    87  	eb.reset()
    88  	if err := eb.encode(val); err != nil {
    89  		return 0, nil, err
    90  	}
    91  	return eb.size(), &encReader{buf: eb}, nil
    92  }
    93  
    94  type listhead struct {
    95  	offset int // index of this header in string data
    96  	size   int // total size of encoded data (including list headers)
    97  }
    98  
    99  // encode writes head to the given buffer, which must be at least
   100  // 9 bytes long. It returns the encoded bytes.
   101  func (head *listhead) encode(buf []byte) []byte {
   102  	return buf[:puthead(buf, 0xC0, 0xF7, uint64(head.size))]
   103  }
   104  
   105  // headsize returns the size of a list or string header
   106  // for a value of the given size.
   107  func headsize(size uint64) int {
   108  	if size < 56 {
   109  		return 1
   110  	}
   111  	return 1 + intsize(size)
   112  }
   113  
   114  // puthead writes a list or string header to buf.
   115  // buf must be at least 9 bytes long.
   116  func puthead(buf []byte, smalltag, largetag byte, size uint64) int {
   117  	if size < 56 {
   118  		buf[0] = smalltag + byte(size)
   119  		return 1
   120  	}
   121  	sizesize := putint(buf[1:], size)
   122  	buf[0] = largetag + byte(sizesize)
   123  	return sizesize + 1
   124  }
   125  
   126  type encbuf struct {
   127  	str     []byte     // string data, contains everything except list headers
   128  	lheads  []listhead // all list headers
   129  	lhsize  int        // sum of sizes of all encoded list headers
   130  	sizebuf [9]byte    // auxiliary buffer for uint encoding
   131  }
   132  
   133  // encbufs are pooled.
   134  var encbufPool = sync.Pool{
   135  	New: func() interface{} { return new(encbuf) },
   136  }
   137  
   138  func (w *encbuf) reset() {
   139  	w.lhsize = 0
   140  	w.str = w.str[:0]
   141  	w.lheads = w.lheads[:0]
   142  }
   143  
   144  // encbuf implements io.Writer so it can be passed it into EncodeRLP.
   145  func (w *encbuf) Write(b []byte) (int, error) {
   146  	w.str = append(w.str, b...)
   147  	return len(b), nil
   148  }
   149  
   150  func (w *encbuf) encode(val interface{}) error {
   151  	rval := reflect.ValueOf(val)
   152  	writer, err := cachedWriter(rval.Type())
   153  	if err != nil {
   154  		return err
   155  	}
   156  	return writer(rval, w)
   157  }
   158  
   159  func (w *encbuf) encodeStringHeader(size int) {
   160  	if size < 56 {
   161  		w.str = append(w.str, 0x80+byte(size))
   162  	} else {
   163  		sizesize := putint(w.sizebuf[1:], uint64(size))
   164  		w.sizebuf[0] = 0xB7 + byte(sizesize)
   165  		w.str = append(w.str, w.sizebuf[:sizesize+1]...)
   166  	}
   167  }
   168  
   169  func (w *encbuf) encodeString(b []byte) {
   170  	if len(b) == 1 && b[0] <= 0x7F {
   171  		// fits single byte, no string header
   172  		w.str = append(w.str, b[0])
   173  	} else {
   174  		w.encodeStringHeader(len(b))
   175  		w.str = append(w.str, b...)
   176  	}
   177  }
   178  
   179  func (w *encbuf) encodeUint(i uint64) {
   180  	if i == 0 {
   181  		w.str = append(w.str, 0x80)
   182  	} else if i < 128 {
   183  		// fits single byte
   184  		w.str = append(w.str, byte(i))
   185  	} else {
   186  		s := putint(w.sizebuf[1:], i)
   187  		w.sizebuf[0] = 0x80 + byte(s)
   188  		w.str = append(w.str, w.sizebuf[:s+1]...)
   189  	}
   190  }
   191  
   192  // list adds a new list header to the header stack. It returns the index
   193  // of the header. The caller must call listEnd with this index after encoding
   194  // the content of the list.
   195  func (w *encbuf) list() int {
   196  	w.lheads = append(w.lheads, listhead{offset: len(w.str), size: w.lhsize})
   197  	return len(w.lheads) - 1
   198  }
   199  
   200  func (w *encbuf) listEnd(index int) {
   201  	lh := &w.lheads[index]
   202  	lh.size = w.size() - lh.offset - lh.size
   203  	if lh.size < 56 {
   204  		w.lhsize++ // length encoded into kind tag
   205  	} else {
   206  		w.lhsize += 1 + intsize(uint64(lh.size))
   207  	}
   208  }
   209  
   210  func (w *encbuf) size() int {
   211  	return len(w.str) + w.lhsize
   212  }
   213  
   214  func (w *encbuf) toBytes() []byte {
   215  	out := make([]byte, w.size())
   216  	strpos := 0
   217  	pos := 0
   218  	for _, head := range w.lheads {
   219  		// write string data before header
   220  		n := copy(out[pos:], w.str[strpos:head.offset])
   221  		pos += n
   222  		strpos += n
   223  		// write the header
   224  		enc := head.encode(out[pos:])
   225  		pos += len(enc)
   226  	}
   227  	// copy string data after the last list header
   228  	copy(out[pos:], w.str[strpos:])
   229  	return out
   230  }
   231  
   232  func (w *encbuf) toWriter(out io.Writer) (err error) {
   233  	strpos := 0
   234  	for _, head := range w.lheads {
   235  		// write string data before header
   236  		if head.offset-strpos > 0 {
   237  			n, err := out.Write(w.str[strpos:head.offset])
   238  			strpos += n
   239  			if err != nil {
   240  				return err
   241  			}
   242  		}
   243  		// write the header
   244  		enc := head.encode(w.sizebuf[:])
   245  		if _, err = out.Write(enc); err != nil {
   246  			return err
   247  		}
   248  	}
   249  	if strpos < len(w.str) {
   250  		// write string data after the last list header
   251  		_, err = out.Write(w.str[strpos:])
   252  	}
   253  	return err
   254  }
   255  
   256  // encReader is the io.Reader returned by EncodeToReader.
   257  // It releases its encbuf at EOF.
   258  type encReader struct {
   259  	buf    *encbuf // the buffer we're reading from. this is nil when we're at EOF.
   260  	lhpos  int     // index of list header that we're reading
   261  	strpos int     // current position in string buffer
   262  	piece  []byte  // next piece to be read
   263  }
   264  
   265  func (r *encReader) Read(b []byte) (n int, err error) {
   266  	for {
   267  		if r.piece = r.next(); r.piece == nil {
   268  			// Put the encode buffer back into the pool at EOF when it
   269  			// is first encountered. Subsequent calls still return EOF
   270  			// as the error but the buffer is no longer valid.
   271  			if r.buf != nil {
   272  				encbufPool.Put(r.buf)
   273  				r.buf = nil
   274  			}
   275  			return n, io.EOF
   276  		}
   277  		nn := copy(b[n:], r.piece)
   278  		n += nn
   279  		if nn < len(r.piece) {
   280  			// piece didn't fit, see you next time.
   281  			r.piece = r.piece[nn:]
   282  			return n, nil
   283  		}
   284  		r.piece = nil
   285  	}
   286  }
   287  
   288  // next returns the next piece of data to be read.
   289  // it returns nil at EOF.
   290  func (r *encReader) next() []byte {
   291  	switch {
   292  	case r.buf == nil:
   293  		return nil
   294  
   295  	case r.piece != nil:
   296  		// There is still data available for reading.
   297  		return r.piece
   298  
   299  	case r.lhpos < len(r.buf.lheads):
   300  		// We're before the last list header.
   301  		head := r.buf.lheads[r.lhpos]
   302  		sizebefore := head.offset - r.strpos
   303  		if sizebefore > 0 {
   304  			// String data before header.
   305  			p := r.buf.str[r.strpos:head.offset]
   306  			r.strpos += sizebefore
   307  			return p
   308  		}
   309  		r.lhpos++
   310  		return head.encode(r.buf.sizebuf[:])
   311  
   312  	case r.strpos < len(r.buf.str):
   313  		// String data at the end, after all list headers.
   314  		p := r.buf.str[r.strpos:]
   315  		r.strpos = len(r.buf.str)
   316  		return p
   317  
   318  	default:
   319  		return nil
   320  	}
   321  }
   322  
   323  var encoderInterface = reflect.TypeOf(new(Encoder)).Elem()
   324  
   325  // makeWriter creates a writer function for the given type.
   326  func makeWriter(typ reflect.Type, ts tags) (writer, error) {
   327  	kind := typ.Kind()
   328  	switch {
   329  	case typ == rawValueType:
   330  		return writeRawValue, nil
   331  	case typ.AssignableTo(reflect.PtrTo(bigInt)):
   332  		return writeBigIntPtr, nil
   333  	case typ.AssignableTo(bigInt):
   334  		return writeBigIntNoPtr, nil
   335  	case kind == reflect.Ptr:
   336  		return makePtrWriter(typ, ts)
   337  	case reflect.PtrTo(typ).Implements(encoderInterface):
   338  		return makeEncoderWriter(typ), nil
   339  	case isUint(kind):
   340  		return writeUint, nil
   341  	case kind == reflect.Bool:
   342  		return writeBool, nil
   343  	case kind == reflect.String:
   344  		return writeString, nil
   345  	case kind == reflect.Slice && isByte(typ.Elem()):
   346  		return writeBytes, nil
   347  	case kind == reflect.Array && isByte(typ.Elem()):
   348  		return makeByteArrayWriter(typ), nil
   349  	case kind == reflect.Slice || kind == reflect.Array:
   350  		return makeSliceWriter(typ, ts)
   351  	case kind == reflect.Struct:
   352  		return makeStructWriter(typ)
   353  	case kind == reflect.Interface:
   354  		return writeInterface, nil
   355  	default:
   356  		return nil, fmt.Errorf("rlp: type %v is not RLP-serializable", typ)
   357  	}
   358  }
   359  
   360  func writeRawValue(val reflect.Value, w *encbuf) error {
   361  	w.str = append(w.str, val.Bytes()...)
   362  	return nil
   363  }
   364  
   365  func writeUint(val reflect.Value, w *encbuf) error {
   366  	w.encodeUint(val.Uint())
   367  	return nil
   368  }
   369  
   370  func writeBool(val reflect.Value, w *encbuf) error {
   371  	if val.Bool() {
   372  		w.str = append(w.str, 0x01)
   373  	} else {
   374  		w.str = append(w.str, 0x80)
   375  	}
   376  	return nil
   377  }
   378  
   379  func writeBigIntPtr(val reflect.Value, w *encbuf) error {
   380  	ptr := val.Interface().(*big.Int)
   381  	if ptr == nil {
   382  		w.str = append(w.str, 0x80)
   383  		return nil
   384  	}
   385  	return writeBigInt(ptr, w)
   386  }
   387  
   388  func writeBigIntNoPtr(val reflect.Value, w *encbuf) error {
   389  	i := val.Interface().(big.Int)
   390  	return writeBigInt(&i, w)
   391  }
   392  
   393  // wordBytes is the number of bytes in a big.Word
   394  const wordBytes = (32 << (uint64(^big.Word(0)) >> 63)) / 8
   395  
   396  func writeBigInt(i *big.Int, w *encbuf) error {
   397  	if i.Sign() == -1 {
   398  		return fmt.Errorf("rlp: cannot encode negative *big.Int")
   399  	}
   400  	bitlen := i.BitLen()
   401  	if bitlen <= 64 {
   402  		w.encodeUint(i.Uint64())
   403  		return nil
   404  	}
   405  	// Integer is larger than 64 bits, encode from i.Bits().
   406  	// The minimal byte length is bitlen rounded up to the next
   407  	// multiple of 8, divided by 8.
   408  	length := ((bitlen + 7) & -8) >> 3
   409  	w.encodeStringHeader(length)
   410  	w.str = append(w.str, make([]byte, length)...)
   411  	index := length
   412  	buf := w.str[len(w.str)-length:]
   413  	for _, d := range i.Bits() {
   414  		for j := 0; j < wordBytes && index > 0; j++ {
   415  			index--
   416  			buf[index] = byte(d)
   417  			d >>= 8
   418  		}
   419  	}
   420  	return nil
   421  }
   422  
   423  func writeBytes(val reflect.Value, w *encbuf) error {
   424  	w.encodeString(val.Bytes())
   425  	return nil
   426  }
   427  
   428  func makeByteArrayWriter(typ reflect.Type) writer {
   429  	switch typ.Len() {
   430  	case 0:
   431  		return writeLengthZeroByteArray
   432  	case 1:
   433  		return writeLengthOneByteArray
   434  	default:
   435  		return writeByteArray
   436  	}
   437  }
   438  
   439  func writeLengthZeroByteArray(val reflect.Value, w *encbuf) error {
   440  	w.str = append(w.str, 0x80)
   441  	return nil
   442  }
   443  
   444  func writeLengthOneByteArray(val reflect.Value, w *encbuf) error {
   445  	b := byte(val.Index(0).Uint())
   446  	if b <= 0x7f {
   447  		w.str = append(w.str, b)
   448  	} else {
   449  		w.str = append(w.str, 0x81, b)
   450  	}
   451  	return nil
   452  }
   453  
   454  func writeByteArray(val reflect.Value, w *encbuf) error {
   455  	if !val.CanAddr() {
   456  		// Getting the byte slice of val requires it to be addressable. Make it
   457  		// addressable by copying.
   458  		copy := reflect.New(val.Type()).Elem()
   459  		copy.Set(val)
   460  		val = copy
   461  	}
   462  
   463  	slice := byteArrayBytes(val)
   464  	w.encodeStringHeader(len(slice))
   465  	w.str = append(w.str, slice...)
   466  	return nil
   467  }
   468  
   469  func writeString(val reflect.Value, w *encbuf) error {
   470  	s := val.String()
   471  	if len(s) == 1 && s[0] <= 0x7f {
   472  		// fits single byte, no string header
   473  		w.str = append(w.str, s[0])
   474  	} else {
   475  		w.encodeStringHeader(len(s))
   476  		w.str = append(w.str, s...)
   477  	}
   478  	return nil
   479  }
   480  
   481  func writeInterface(val reflect.Value, w *encbuf) error {
   482  	if val.IsNil() {
   483  		// Write empty list. This is consistent with the previous RLP
   484  		// encoder that we had and should therefore avoid any
   485  		// problems.
   486  		w.str = append(w.str, 0xC0)
   487  		return nil
   488  	}
   489  	eval := val.Elem()
   490  	writer, err := cachedWriter(eval.Type())
   491  	if err != nil {
   492  		return err
   493  	}
   494  	return writer(eval, w)
   495  }
   496  
   497  func makeSliceWriter(typ reflect.Type, ts tags) (writer, error) {
   498  	etypeinfo := theTC.infoWhileGenerating(typ.Elem(), tags{})
   499  	if etypeinfo.writerErr != nil {
   500  		return nil, etypeinfo.writerErr
   501  	}
   502  	writer := func(val reflect.Value, w *encbuf) error {
   503  		if !ts.tail {
   504  			defer w.listEnd(w.list())
   505  		}
   506  		vlen := val.Len()
   507  		for i := 0; i < vlen; i++ {
   508  			if err := etypeinfo.writer(val.Index(i), w); err != nil {
   509  				return err
   510  			}
   511  		}
   512  		return nil
   513  	}
   514  	return writer, nil
   515  }
   516  
   517  func makeStructWriter(typ reflect.Type) (writer, error) {
   518  	fields, err := structFields(typ)
   519  	if err != nil {
   520  		return nil, err
   521  	}
   522  	for _, f := range fields {
   523  		if f.info.writerErr != nil {
   524  			return nil, structFieldError{typ, f.index, f.info.writerErr}
   525  		}
   526  	}
   527  
   528  	var writer writer
   529  	firstOptionalField := firstOptionalField(fields)
   530  	if firstOptionalField == len(fields) {
   531  		// This is the writer function for structs without any optional fields.
   532  		writer = func(val reflect.Value, w *encbuf) error {
   533  			lh := w.list()
   534  			for _, f := range fields {
   535  				if err := f.info.writer(val.Field(f.index), w); err != nil {
   536  					return err
   537  				}
   538  			}
   539  			w.listEnd(lh)
   540  			return nil
   541  		}
   542  	} else {
   543  		// If there are any "optional" fields, the writer needs to perform additional
   544  		// checks to determine the output list length.
   545  		writer = func(val reflect.Value, w *encbuf) error {
   546  			lastField := len(fields) - 1
   547  			for ; lastField >= firstOptionalField; lastField-- {
   548  				if !val.Field(fields[lastField].index).IsZero() {
   549  					break
   550  				}
   551  			}
   552  			lh := w.list()
   553  			for i := 0; i <= lastField; i++ {
   554  				if err := fields[i].info.writer(val.Field(fields[i].index), w); err != nil {
   555  					return err
   556  				}
   557  			}
   558  			w.listEnd(lh)
   559  			return nil
   560  		}
   561  	}
   562  	return writer, nil
   563  }
   564  
   565  func makePtrWriter(typ reflect.Type, ts tags) (writer, error) {
   566  	etypeinfo := theTC.infoWhileGenerating(typ.Elem(), tags{})
   567  	if etypeinfo.writerErr != nil {
   568  		return nil, etypeinfo.writerErr
   569  	}
   570  	// Determine how to encode nil pointers.
   571  	var nilKind Kind
   572  	if ts.nilOK {
   573  		nilKind = ts.nilKind // use struct tag if provided
   574  	} else {
   575  		nilKind = defaultNilKind(typ.Elem())
   576  	}
   577  
   578  	writer := func(val reflect.Value, w *encbuf) error {
   579  		if val.IsNil() {
   580  			if nilKind == String {
   581  				w.str = append(w.str, 0x80)
   582  			} else {
   583  				w.listEnd(w.list())
   584  			}
   585  			return nil
   586  		}
   587  		return etypeinfo.writer(val.Elem(), w)
   588  	}
   589  	return writer, nil
   590  }
   591  
   592  func makeEncoderWriter(typ reflect.Type) writer {
   593  	if typ.Implements(encoderInterface) {
   594  		return func(val reflect.Value, w *encbuf) error {
   595  			return val.Interface().(Encoder).EncodeRLP(w)
   596  		}
   597  	}
   598  	w := func(val reflect.Value, w *encbuf) error {
   599  		if !val.CanAddr() {
   600  			// package json simply doesn't call MarshalJSON for this case, but encodes the
   601  			// value as if it didn't implement the interface. We don't want to handle it that
   602  			// way.
   603  			return fmt.Errorf("rlp: unadressable value of type %v, EncodeRLP is pointer method", val.Type())
   604  		}
   605  		return val.Addr().Interface().(Encoder).EncodeRLP(w)
   606  	}
   607  	return w
   608  }
   609  
   610  // putint writes i to the beginning of b in big endian byte
   611  // order, using the least number of bytes needed to represent i.
   612  func putint(b []byte, i uint64) (size int) {
   613  	switch {
   614  	case i < (1 << 8):
   615  		b[0] = byte(i)
   616  		return 1
   617  	case i < (1 << 16):
   618  		b[0] = byte(i >> 8)
   619  		b[1] = byte(i)
   620  		return 2
   621  	case i < (1 << 24):
   622  		b[0] = byte(i >> 16)
   623  		b[1] = byte(i >> 8)
   624  		b[2] = byte(i)
   625  		return 3
   626  	case i < (1 << 32):
   627  		b[0] = byte(i >> 24)
   628  		b[1] = byte(i >> 16)
   629  		b[2] = byte(i >> 8)
   630  		b[3] = byte(i)
   631  		return 4
   632  	case i < (1 << 40):
   633  		b[0] = byte(i >> 32)
   634  		b[1] = byte(i >> 24)
   635  		b[2] = byte(i >> 16)
   636  		b[3] = byte(i >> 8)
   637  		b[4] = byte(i)
   638  		return 5
   639  	case i < (1 << 48):
   640  		b[0] = byte(i >> 40)
   641  		b[1] = byte(i >> 32)
   642  		b[2] = byte(i >> 24)
   643  		b[3] = byte(i >> 16)
   644  		b[4] = byte(i >> 8)
   645  		b[5] = byte(i)
   646  		return 6
   647  	case i < (1 << 56):
   648  		b[0] = byte(i >> 48)
   649  		b[1] = byte(i >> 40)
   650  		b[2] = byte(i >> 32)
   651  		b[3] = byte(i >> 24)
   652  		b[4] = byte(i >> 16)
   653  		b[5] = byte(i >> 8)
   654  		b[6] = byte(i)
   655  		return 7
   656  	default:
   657  		b[0] = byte(i >> 56)
   658  		b[1] = byte(i >> 48)
   659  		b[2] = byte(i >> 40)
   660  		b[3] = byte(i >> 32)
   661  		b[4] = byte(i >> 24)
   662  		b[5] = byte(i >> 16)
   663  		b[6] = byte(i >> 8)
   664  		b[7] = byte(i)
   665  		return 8
   666  	}
   667  }
   668  
   669  // intsize computes the minimum number of bytes required to store i.
   670  func intsize(i uint64) (size int) {
   671  	for size = 1; ; size++ {
   672  		if i >>= 8; i == 0 {
   673  			return size
   674  		}
   675  	}
   676  }