github.com/linapex/ethereum-dpos-chinese@v0.0.0-20190316121959-b78b3a4a1ece/rlp/encode_test.go (about)

     1  
     2  //<developer>
     3  //    <name>linapex 曹一峰</name>
     4  //    <email>linapex@163.com</email>
     5  //    <wx>superexc</wx>
     6  //    <qqgroup>128148617</qqgroup>
     7  //    <url>https://jsq.ink</url>
     8  //    <role>pku engineer</role>
     9  //    <date>2019-03-16 12:09:45</date>
    10  //</624342663285444608>
    11  
    12  
    13  package rlp
    14  
    15  import (
    16  	"bytes"
    17  	"errors"
    18  	"fmt"
    19  	"io"
    20  	"io/ioutil"
    21  	"math/big"
    22  	"sync"
    23  	"testing"
    24  )
    25  
    26  type testEncoder struct {
    27  	err error
    28  }
    29  
    30  func (e *testEncoder) EncodeRLP(w io.Writer) error {
    31  	if e == nil {
    32  		w.Write([]byte{0, 0, 0, 0})
    33  	} else if e.err != nil {
    34  		return e.err
    35  	} else {
    36  		w.Write([]byte{0, 1, 0, 1, 0, 1, 0, 1, 0, 1})
    37  	}
    38  	return nil
    39  }
    40  
    41  type byteEncoder byte
    42  
    43  func (e byteEncoder) EncodeRLP(w io.Writer) error {
    44  	w.Write(EmptyList)
    45  	return nil
    46  }
    47  
    48  type encodableReader struct {
    49  	A, B uint
    50  }
    51  
    52  func (e *encodableReader) Read(b []byte) (int, error) {
    53  	panic("called")
    54  }
    55  
    56  type namedByteType byte
    57  
    58  var (
    59  	_ = Encoder(&testEncoder{})
    60  	_ = Encoder(byteEncoder(0))
    61  
    62  	reader io.Reader = &encodableReader{1, 2}
    63  )
    64  
    65  type encTest struct {
    66  	val           interface{}
    67  	output, error string
    68  }
    69  
    70  var encTests = []encTest{
    71  //布尔运算
    72  	{val: true, output: "01"},
    73  	{val: false, output: "80"},
    74  
    75  //整数
    76  	{val: uint32(0), output: "80"},
    77  	{val: uint32(127), output: "7F"},
    78  	{val: uint32(128), output: "8180"},
    79  	{val: uint32(256), output: "820100"},
    80  	{val: uint32(1024), output: "820400"},
    81  	{val: uint32(0xFFFFFF), output: "83FFFFFF"},
    82  	{val: uint32(0xFFFFFFFF), output: "84FFFFFFFF"},
    83  	{val: uint64(0xFFFFFFFF), output: "84FFFFFFFF"},
    84  	{val: uint64(0xFFFFFFFFFF), output: "85FFFFFFFFFF"},
    85  	{val: uint64(0xFFFFFFFFFFFF), output: "86FFFFFFFFFFFF"},
    86  	{val: uint64(0xFFFFFFFFFFFFFF), output: "87FFFFFFFFFFFFFF"},
    87  	{val: uint64(0xFFFFFFFFFFFFFFFF), output: "88FFFFFFFFFFFFFFFF"},
    88  
    89  //大整数(小值应与uint匹配)
    90  	{val: big.NewInt(0), output: "80"},
    91  	{val: big.NewInt(1), output: "01"},
    92  	{val: big.NewInt(127), output: "7F"},
    93  	{val: big.NewInt(128), output: "8180"},
    94  	{val: big.NewInt(256), output: "820100"},
    95  	{val: big.NewInt(1024), output: "820400"},
    96  	{val: big.NewInt(0xFFFFFF), output: "83FFFFFF"},
    97  	{val: big.NewInt(0xFFFFFFFF), output: "84FFFFFFFF"},
    98  	{val: big.NewInt(0xFFFFFFFFFF), output: "85FFFFFFFFFF"},
    99  	{val: big.NewInt(0xFFFFFFFFFFFF), output: "86FFFFFFFFFFFF"},
   100  	{val: big.NewInt(0xFFFFFFFFFFFFFF), output: "87FFFFFFFFFFFFFF"},
   101  	{
   102  		val:    big.NewInt(0).SetBytes(unhex("102030405060708090A0B0C0D0E0F2")),
   103  		output: "8F102030405060708090A0B0C0D0E0F2",
   104  	},
   105  	{
   106  		val:    big.NewInt(0).SetBytes(unhex("0100020003000400050006000700080009000A000B000C000D000E01")),
   107  		output: "9C0100020003000400050006000700080009000A000B000C000D000E01",
   108  	},
   109  	{
   110  		val:    big.NewInt(0).SetBytes(unhex("010000000000000000000000000000000000000000000000000000000000000000")),
   111  		output: "A1010000000000000000000000000000000000000000000000000000000000000000",
   112  	},
   113  
   114  //非指针大整数
   115  	{val: *big.NewInt(0), output: "80"},
   116  	{val: *big.NewInt(0xFFFFFF), output: "83FFFFFF"},
   117  
   118  //不支持负整数
   119  	{val: big.NewInt(-1), error: "rlp: cannot encode negative *big.Int"},
   120  
   121  //字节片、字符串
   122  	{val: []byte{}, output: "80"},
   123  	{val: []byte{0x7E}, output: "7E"},
   124  	{val: []byte{0x7F}, output: "7F"},
   125  	{val: []byte{0x80}, output: "8180"},
   126  	{val: []byte{1, 2, 3}, output: "83010203"},
   127  
   128  	{val: []namedByteType{1, 2, 3}, output: "83010203"},
   129  	{val: [...]namedByteType{1, 2, 3}, output: "83010203"},
   130  
   131  	{val: "", output: "80"},
   132  	{val: "\x7E", output: "7E"},
   133  	{val: "\x7F", output: "7F"},
   134  	{val: "\x80", output: "8180"},
   135  	{val: "dog", output: "83646F67"},
   136  	{
   137  		val:    "Lorem ipsum dolor sit amet, consectetur adipisicing eli",
   138  		output: "B74C6F72656D20697073756D20646F6C6F722073697420616D65742C20636F6E7365637465747572206164697069736963696E6720656C69",
   139  	},
   140  	{
   141  		val:    "Lorem ipsum dolor sit amet, consectetur adipisicing elit",
   142  		output: "B8384C6F72656D20697073756D20646F6C6F722073697420616D65742C20636F6E7365637465747572206164697069736963696E6720656C6974",
   143  	},
   144  	{
   145  		val:    "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur mauris magna, suscipit sed vehicula non, iaculis faucibus tortor. Proin suscipit ultricies malesuada. Duis tortor elit, dictum quis tristique eu, ultrices at risus. Morbi a est imperdiet mi ullamcorper aliquet suscipit nec lorem. Aenean quis leo mollis, vulputate elit varius, consequat enim. Nulla ultrices turpis justo, et posuere urna consectetur nec. Proin non convallis metus. Donec tempor ipsum in mauris congue sollicitudin. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Suspendisse convallis sem vel massa faucibus, eget lacinia lacus tempor. Nulla quis ultricies purus. Proin auctor rhoncus nibh condimentum mollis. Aliquam consequat enim at metus luctus, a eleifend purus egestas. Curabitur at nibh metus. Nam bibendum, neque at auctor tristique, lorem libero aliquet arcu, non interdum tellus lectus sit amet eros. Cras rhoncus, metus ac ornare cursus, dolor justo ultrices metus, at ullamcorper volutpat",
   146  		output: "B904004C6F72656D20697073756D20646F6C6F722073697420616D65742C20636F6E73656374657475722061646970697363696E6720656C69742E20437572616269747572206D6175726973206D61676E612C20737573636970697420736564207665686963756C61206E6F6E2C20696163756C697320666175636962757320746F72746F722E2050726F696E20737573636970697420756C74726963696573206D616C6573756164612E204475697320746F72746F7220656C69742C2064696374756D2071756973207472697374697175652065752C20756C7472696365732061742072697375732E204D6F72626920612065737420696D70657264696574206D6920756C6C616D636F7270657220616C6971756574207375736369706974206E6563206C6F72656D2E2041656E65616E2071756973206C656F206D6F6C6C69732C2076756C70757461746520656C6974207661726975732C20636F6E73657175617420656E696D2E204E756C6C6120756C74726963657320747572706973206A7573746F2C20657420706F73756572652075726E6120636F6E7365637465747572206E65632E2050726F696E206E6F6E20636F6E76616C6C6973206D657475732E20446F6E65632074656D706F7220697073756D20696E206D617572697320636F6E67756520736F6C6C696369747564696E2E20566573746962756C756D20616E746520697073756D207072696D697320696E206661756369627573206F726369206C756374757320657420756C74726963657320706F737565726520637562696C69612043757261653B2053757370656E646973736520636F6E76616C6C69732073656D2076656C206D617373612066617563696275732C2065676574206C6163696E6961206C616375732074656D706F722E204E756C6C61207175697320756C747269636965732070757275732E2050726F696E20617563746F722072686F6E637573206E69626820636F6E64696D656E74756D206D6F6C6C69732E20416C697175616D20636F6E73657175617420656E696D206174206D65747573206C75637475732C206120656C656966656E6420707572757320656765737461732E20437572616269747572206174206E696268206D657475732E204E616D20626962656E64756D2C206E6571756520617420617563746F72207472697374697175652C206C6F72656D206C696265726F20616C697175657420617263752C206E6F6E20696E74657264756D2074656C6C7573206C65637475732073697420616D65742065726F732E20437261732072686F6E6375732C206D65747573206163206F726E617265206375727375732C20646F6C6F72206A7573746F20756C747269636573206D657475732C20617420756C6C616D636F7270657220766F6C7574706174",
   147  	},
   148  
   149  //片
   150  	{val: []uint{}, output: "C0"},
   151  	{val: []uint{1, 2, 3}, output: "C3010203"},
   152  	{
   153  //[答],[答],[答],[答],[答]]
   154  		val:    []interface{}{[]interface{}{}, [][]interface{}{{}}, []interface{}{[]interface{}{}, [][]interface{}{{}}}},
   155  		output: "C7C0C1C0C3C0C1C0",
   156  	},
   157  	{
   158  		val:    []string{"aaa", "bbb", "ccc", "ddd", "eee", "fff", "ggg", "hhh", "iii", "jjj", "kkk", "lll", "mmm", "nnn", "ooo"},
   159  		output: "F83C836161618362626283636363836464648365656583666666836767678368686883696969836A6A6A836B6B6B836C6C6C836D6D6D836E6E6E836F6F6F",
   160  	},
   161  	{
   162  		val:    []interface{}{uint(1), uint(0xFFFFFF), []interface{}{[]uint{4, 5, 5}}, "abc"},
   163  		output: "CE0183FFFFFFC4C304050583616263",
   164  	},
   165  	{
   166  		val: [][]string{
   167  			{"asdf", "qwer", "zxcv"},
   168  			{"asdf", "qwer", "zxcv"},
   169  			{"asdf", "qwer", "zxcv"},
   170  			{"asdf", "qwer", "zxcv"},
   171  			{"asdf", "qwer", "zxcv"},
   172  			{"asdf", "qwer", "zxcv"},
   173  			{"asdf", "qwer", "zxcv"},
   174  			{"asdf", "qwer", "zxcv"},
   175  			{"asdf", "qwer", "zxcv"},
   176  			{"asdf", "qwer", "zxcv"},
   177  			{"asdf", "qwer", "zxcv"},
   178  			{"asdf", "qwer", "zxcv"},
   179  			{"asdf", "qwer", "zxcv"},
   180  			{"asdf", "qwer", "zxcv"},
   181  			{"asdf", "qwer", "zxcv"},
   182  			{"asdf", "qwer", "zxcv"},
   183  			{"asdf", "qwer", "zxcv"},
   184  			{"asdf", "qwer", "zxcv"},
   185  			{"asdf", "qwer", "zxcv"},
   186  			{"asdf", "qwer", "zxcv"},
   187  			{"asdf", "qwer", "zxcv"},
   188  			{"asdf", "qwer", "zxcv"},
   189  			{"asdf", "qwer", "zxcv"},
   190  			{"asdf", "qwer", "zxcv"},
   191  			{"asdf", "qwer", "zxcv"},
   192  			{"asdf", "qwer", "zxcv"},
   193  			{"asdf", "qwer", "zxcv"},
   194  			{"asdf", "qwer", "zxcv"},
   195  			{"asdf", "qwer", "zxcv"},
   196  			{"asdf", "qwer", "zxcv"},
   197  			{"asdf", "qwer", "zxcv"},
   198  			{"asdf", "qwer", "zxcv"},
   199  		},
   200  		output: "F90200CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376CF84617364668471776572847A786376",
   201  	},
   202  
   203  //RAW值
   204  	{val: RawValue(unhex("01")), output: "01"},
   205  	{val: RawValue(unhex("82FFFF")), output: "82FFFF"},
   206  	{val: []RawValue{unhex("01"), unhex("02")}, output: "C20102"},
   207  
   208  //结构体
   209  	{val: simplestruct{}, output: "C28080"},
   210  	{val: simplestruct{A: 3, B: "foo"}, output: "C50383666F6F"},
   211  	{val: &recstruct{5, nil}, output: "C205C0"},
   212  	{val: &recstruct{5, &recstruct{4, &recstruct{3, nil}}}, output: "C605C404C203C0"},
   213  	{val: &tailRaw{A: 1, Tail: []RawValue{unhex("02"), unhex("03")}}, output: "C3010203"},
   214  	{val: &tailRaw{A: 1, Tail: []RawValue{unhex("02")}}, output: "C20102"},
   215  	{val: &tailRaw{A: 1, Tail: []RawValue{}}, output: "C101"},
   216  	{val: &tailRaw{A: 1, Tail: nil}, output: "C101"},
   217  	{val: &hasIgnoredField{A: 1, B: 2, C: 3}, output: "C20103"},
   218  
   219  //零
   220  	{val: (*uint)(nil), output: "80"},
   221  	{val: (*string)(nil), output: "80"},
   222  	{val: (*[]byte)(nil), output: "80"},
   223  	{val: (*[10]byte)(nil), output: "80"},
   224  	{val: (*big.Int)(nil), output: "80"},
   225  	{val: (*[]string)(nil), output: "C0"},
   226  	{val: (*[10]string)(nil), output: "C0"},
   227  	{val: (*[]interface{})(nil), output: "C0"},
   228  	{val: (*[]struct{ uint })(nil), output: "C0"},
   229  	{val: (*interface{})(nil), output: "C0"},
   230  
   231  //界面
   232  {val: []io.Reader{reader}, output: "C3C20102"}, //包含的值是结构
   233  
   234  //编码器
   235  	{val: (*testEncoder)(nil), output: "00000000"},
   236  	{val: &testEncoder{}, output: "00010001000100010001"},
   237  	{val: &testEncoder{errors.New("test error")}, error: "test error"},
   238  //验证是否为调用了指针方法testencoder.encoderlp
   239  //可寻址非指针值。
   240  	{val: &struct{ TE testEncoder }{testEncoder{}}, output: "CA00010001000100010001"},
   241  	{val: &struct{ TE testEncoder }{testEncoder{errors.New("test error")}}, error: "test error"},
   242  //验证非可寻址非指针编码器的错误
   243  	{val: testEncoder{}, error: "rlp: game over: unadressable value of type rlp.testEncoder, EncodeRLP is pointer method"},
   244  //验证[]字节的特殊情况
   245  	{val: []byteEncoder{0, 1, 2, 3, 4}, output: "C5C0C0C0C0C0"},
   246  }
   247  
   248  func runEncTests(t *testing.T, f func(val interface{}) ([]byte, error)) {
   249  	for i, test := range encTests {
   250  		output, err := f(test.val)
   251  		if err != nil && test.error == "" {
   252  			t.Errorf("test %d: unexpected error: %v\nvalue %#v\ntype %T",
   253  				i, err, test.val, test.val)
   254  			continue
   255  		}
   256  		if test.error != "" && fmt.Sprint(err) != test.error {
   257  			t.Errorf("test %d: error mismatch\ngot   %v\nwant  %v\nvalue %#v\ntype  %T",
   258  				i, err, test.error, test.val, test.val)
   259  			continue
   260  		}
   261  		if err == nil && !bytes.Equal(output, unhex(test.output)) {
   262  			t.Errorf("test %d: output mismatch:\ngot   %X\nwant  %s\nvalue %#v\ntype  %T",
   263  				i, output, test.output, test.val, test.val)
   264  		}
   265  	}
   266  }
   267  
   268  func TestEncode(t *testing.T) {
   269  	runEncTests(t, func(val interface{}) ([]byte, error) {
   270  		b := new(bytes.Buffer)
   271  		err := Encode(b, val)
   272  		return b.Bytes(), err
   273  	})
   274  }
   275  
   276  func TestEncodeToBytes(t *testing.T) {
   277  	runEncTests(t, EncodeToBytes)
   278  }
   279  
   280  func TestEncodeToReader(t *testing.T) {
   281  	runEncTests(t, func(val interface{}) ([]byte, error) {
   282  		_, r, err := EncodeToReader(val)
   283  		if err != nil {
   284  			return nil, err
   285  		}
   286  		return ioutil.ReadAll(r)
   287  	})
   288  }
   289  
   290  func TestEncodeToReaderPiecewise(t *testing.T) {
   291  	runEncTests(t, func(val interface{}) ([]byte, error) {
   292  		size, r, err := EncodeToReader(val)
   293  		if err != nil {
   294  			return nil, err
   295  		}
   296  
   297  //逐段读取输出
   298  		output := make([]byte, size)
   299  		for start, end := 0, 0; start < size; start = end {
   300  			if remaining := size - start; remaining < 3 {
   301  				end += remaining
   302  			} else {
   303  				end = start + 3
   304  			}
   305  			n, err := r.Read(output[start:end])
   306  			end = start + n
   307  			if err == io.EOF {
   308  				break
   309  			} else if err != nil {
   310  				return nil, err
   311  			}
   312  		}
   313  		return output, nil
   314  	})
   315  }
   316  
   317  //这是一个回归测试,用于验证加密程序
   318  //仅将其encbuf返回池一次。
   319  func TestEncodeToReaderReturnToPool(t *testing.T) {
   320  	buf := make([]byte, 50)
   321  	wg := new(sync.WaitGroup)
   322  	for i := 0; i < 5; i++ {
   323  		wg.Add(1)
   324  		go func() {
   325  			for i := 0; i < 1000; i++ {
   326  				_, r, _ := EncodeToReader("foo")
   327  				ioutil.ReadAll(r)
   328  				r.Read(buf)
   329  				r.Read(buf)
   330  				r.Read(buf)
   331  				r.Read(buf)
   332  			}
   333  			wg.Done()
   334  		}()
   335  	}
   336  	wg.Wait()
   337  }
   338