accounts/abi: added abi test cases, minor bug fixes (#20903)
* accounts/abi: added documentation * accounts/abi: reduced usage of arguments.LengthNonIndexed * accounts/abi: simplified reflection logic * accounts/abi: moved testjson data into global declaration * accounts/abi: removed duplicate test cases * accounts/abi: reworked abi tests * accounts/abi: added more tests for abi packing * accounts/abi/bind: refactored base tests * accounts/abi: run pack tests as subtests * accounts/abi: removed duplicate tests * accounts/abi: removed unnused arguments.LengthNonIndexed Due to refactors to the code, we do not need the arguments.LengthNonIndexed function anymore. You can still get the length by calling len(arguments.NonIndexed()) * accounts/abi: added type test * accounts/abi: modified unpack test to pack test * accounts/abi: length check on arrayTy * accounts/abi: test invalid abi * accounts/abi: fixed rebase error * accounts/abi: fixed rebase errors * accounts/abi: removed unused definition * accounts/abi: merged packing/unpacking tests * accounts/abi: fixed [][][32]bytes encoding * accounts/abi: added tuple test cases * accounts/abi: renamed getMockLog -> newMockLog * accounts/abi: removed duplicate test * accounts/abi: bools -> booleans
This commit is contained in:
		
				
					committed by
					
						
						GitHub
					
				
			
			
				
	
			
			
			
						parent
						
							40283d0522
						
					
				
				
					commit
					e32ee6ac05
				
			@@ -32,12 +32,7 @@ import (
 | 
			
		||||
 | 
			
		||||
const jsondata = `
 | 
			
		||||
[
 | 
			
		||||
	{ "type" : "function", "name" : "balance", "stateMutability" : "view" },
 | 
			
		||||
	{ "type" : "function", "name" : "send", "inputs" : [ { "name" : "amount", "type" : "uint256" } ] }
 | 
			
		||||
]`
 | 
			
		||||
 | 
			
		||||
const jsondata2 = `
 | 
			
		||||
[
 | 
			
		||||
	{ "type" : "function", "name" : "", "stateMutability" : "view" },
 | 
			
		||||
	{ "type" : "function", "name" : "balance", "stateMutability" : "view" },
 | 
			
		||||
	{ "type" : "function", "name" : "send", "inputs" : [ { "name" : "amount", "type" : "uint256" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "test", "inputs" : [ { "name" : "number", "type" : "uint32" } ] },
 | 
			
		||||
@@ -46,6 +41,7 @@ const jsondata2 = `
 | 
			
		||||
	{ "type" : "function", "name" : "address", "inputs" : [ { "name" : "inputs", "type" : "address" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "uint64[2]", "inputs" : [ { "name" : "inputs", "type" : "uint64[2]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "uint64[]", "inputs" : [ { "name" : "inputs", "type" : "uint64[]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "int8", "inputs" : [ { "name" : "inputs", "type" : "int8" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "foo", "inputs" : [ { "name" : "inputs", "type" : "uint32" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "bar", "inputs" : [ { "name" : "inputs", "type" : "uint32" }, { "name" : "string", "type" : "uint16" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "slice", "inputs" : [ { "name" : "inputs", "type" : "uint32[2]" } ] },
 | 
			
		||||
@@ -54,16 +50,68 @@ const jsondata2 = `
 | 
			
		||||
	{ "type" : "function", "name" : "sliceMultiAddress", "inputs" : [ { "name" : "a", "type" : "address[]" }, { "name" : "b", "type" : "address[]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "nestedArray", "inputs" : [ { "name" : "a", "type" : "uint256[2][2]" }, { "name" : "b", "type" : "address[]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "nestedArray2", "inputs" : [ { "name" : "a", "type" : "uint8[][2]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "nestedSlice", "inputs" : [ { "name" : "a", "type" : "uint8[][]" } ] }
 | 
			
		||||
	{ "type" : "function", "name" : "nestedSlice", "inputs" : [ { "name" : "a", "type" : "uint8[][]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "receive", "inputs" : [ { "name" : "memo", "type" : "bytes" }], "outputs" : [], "payable" : true, "stateMutability" : "payable" },
 | 
			
		||||
	{ "type" : "function", "name" : "fixedArrStr", "stateMutability" : "view", "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr", "type" : "uint256[2]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "fixedArrBytes", "stateMutability" : "view", "inputs" : [ { "name" : "bytes", "type" : "bytes" }, { "name" : "fixedArr", "type" : "uint256[2]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "mixedArrStr", "stateMutability" : "view", "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr", "type" : "uint256[2]" }, { "name" : "dynArr", "type" : "uint256[]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "doubleFixedArrStr", "stateMutability" : "view", "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr1", "type" : "uint256[2]" }, { "name" : "fixedArr2", "type" : "uint256[3]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "multipleMixedArrStr", "stateMutability" : "view", "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr1", "type" : "uint256[2]" }, { "name" : "dynArr", "type" : "uint256[]" }, { "name" : "fixedArr2", "type" : "uint256[3]" } ] }
 | 
			
		||||
]`
 | 
			
		||||
 | 
			
		||||
var (
 | 
			
		||||
	Uint256, _    = NewType("uint256", "", nil)
 | 
			
		||||
	Uint32, _     = NewType("uint32", "", nil)
 | 
			
		||||
	Uint16, _     = NewType("uint16", "", nil)
 | 
			
		||||
	String, _     = NewType("string", "", nil)
 | 
			
		||||
	Bool, _       = NewType("bool", "", nil)
 | 
			
		||||
	Bytes, _      = NewType("bytes", "", nil)
 | 
			
		||||
	Address, _    = NewType("address", "", nil)
 | 
			
		||||
	Uint64Arr, _  = NewType("uint64[]", "", nil)
 | 
			
		||||
	AddressArr, _ = NewType("address[]", "", nil)
 | 
			
		||||
	Int8, _       = NewType("int8", "", nil)
 | 
			
		||||
	// Special types for testing
 | 
			
		||||
	Uint32Arr2, _       = NewType("uint32[2]", "", nil)
 | 
			
		||||
	Uint64Arr2, _       = NewType("uint64[2]", "", nil)
 | 
			
		||||
	Uint256Arr, _       = NewType("uint256[]", "", nil)
 | 
			
		||||
	Uint256Arr2, _      = NewType("uint256[2]", "", nil)
 | 
			
		||||
	Uint256Arr3, _      = NewType("uint256[3]", "", nil)
 | 
			
		||||
	Uint256ArrNested, _ = NewType("uint256[2][2]", "", nil)
 | 
			
		||||
	Uint8ArrNested, _   = NewType("uint8[][2]", "", nil)
 | 
			
		||||
	Uint8SliceNested, _ = NewType("uint8[][]", "", nil)
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
var methods = map[string]Method{
 | 
			
		||||
	"":                    NewMethod("", "", Function, "view", false, false, nil, nil),
 | 
			
		||||
	"balance":             NewMethod("balance", "balance", Function, "view", false, false, nil, nil),
 | 
			
		||||
	"send":                NewMethod("send", "send", Function, "", false, false, []Argument{{"amount", Uint256, false}}, nil),
 | 
			
		||||
	"test":                NewMethod("test", "test", Function, "", false, false, []Argument{{"number", Uint32, false}}, nil),
 | 
			
		||||
	"string":              NewMethod("string", "string", Function, "", false, false, []Argument{{"inputs", String, false}}, nil),
 | 
			
		||||
	"bool":                NewMethod("bool", "bool", Function, "", false, false, []Argument{{"inputs", Bool, false}}, nil),
 | 
			
		||||
	"address":             NewMethod("address", "address", Function, "", false, false, []Argument{{"inputs", Address, false}}, nil),
 | 
			
		||||
	"uint64[]":            NewMethod("uint64[]", "uint64[]", Function, "", false, false, []Argument{{"inputs", Uint64Arr, false}}, nil),
 | 
			
		||||
	"uint64[2]":           NewMethod("uint64[2]", "uint64[2]", Function, "", false, false, []Argument{{"inputs", Uint64Arr2, false}}, nil),
 | 
			
		||||
	"int8":                NewMethod("int8", "int8", Function, "", false, false, []Argument{{"inputs", Int8, false}}, nil),
 | 
			
		||||
	"foo":                 NewMethod("foo", "foo", Function, "", false, false, []Argument{{"inputs", Uint32, false}}, nil),
 | 
			
		||||
	"bar":                 NewMethod("bar", "bar", Function, "", false, false, []Argument{{"inputs", Uint32, false}, {"string", Uint16, false}}, nil),
 | 
			
		||||
	"slice":               NewMethod("slice", "slice", Function, "", false, false, []Argument{{"inputs", Uint32Arr2, false}}, nil),
 | 
			
		||||
	"slice256":            NewMethod("slice256", "slice256", Function, "", false, false, []Argument{{"inputs", Uint256Arr2, false}}, nil),
 | 
			
		||||
	"sliceAddress":        NewMethod("sliceAddress", "sliceAddress", Function, "", false, false, []Argument{{"inputs", AddressArr, false}}, nil),
 | 
			
		||||
	"sliceMultiAddress":   NewMethod("sliceMultiAddress", "sliceMultiAddress", Function, "", false, false, []Argument{{"a", AddressArr, false}, {"b", AddressArr, false}}, nil),
 | 
			
		||||
	"nestedArray":         NewMethod("nestedArray", "nestedArray", Function, "", false, false, []Argument{{"a", Uint256ArrNested, false}, {"b", AddressArr, false}}, nil),
 | 
			
		||||
	"nestedArray2":        NewMethod("nestedArray2", "nestedArray2", Function, "", false, false, []Argument{{"a", Uint8ArrNested, false}}, nil),
 | 
			
		||||
	"nestedSlice":         NewMethod("nestedSlice", "nestedSlice", Function, "", false, false, []Argument{{"a", Uint8SliceNested, false}}, nil),
 | 
			
		||||
	"receive":             NewMethod("receive", "receive", Function, "payable", false, true, []Argument{{"memo", Bytes, false}}, []Argument{}),
 | 
			
		||||
	"fixedArrStr":         NewMethod("fixedArrStr", "fixedArrStr", Function, "view", false, false, []Argument{{"str", String, false}, {"fixedArr", Uint256Arr2, false}}, nil),
 | 
			
		||||
	"fixedArrBytes":       NewMethod("fixedArrBytes", "fixedArrBytes", Function, "view", false, false, []Argument{{"bytes", Bytes, false}, {"fixedArr", Uint256Arr2, false}}, nil),
 | 
			
		||||
	"mixedArrStr":         NewMethod("mixedArrStr", "mixedArrStr", Function, "view", false, false, []Argument{{"str", String, false}, {"fixedArr", Uint256Arr2, false}, {"dynArr", Uint256Arr, false}}, nil),
 | 
			
		||||
	"doubleFixedArrStr":   NewMethod("doubleFixedArrStr", "doubleFixedArrStr", Function, "view", false, false, []Argument{{"str", String, false}, {"fixedArr1", Uint256Arr2, false}, {"fixedArr2", Uint256Arr3, false}}, nil),
 | 
			
		||||
	"multipleMixedArrStr": NewMethod("multipleMixedArrStr", "multipleMixedArrStr", Function, "view", false, false, []Argument{{"str", String, false}, {"fixedArr1", Uint256Arr2, false}, {"dynArr", Uint256Arr, false}, {"fixedArr2", Uint256Arr3, false}}, nil),
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestReader(t *testing.T) {
 | 
			
		||||
	Uint256, _ := NewType("uint256", "", nil)
 | 
			
		||||
	abi := ABI{
 | 
			
		||||
		Methods: map[string]Method{
 | 
			
		||||
			"balance": NewMethod("balance", "balance", Function, "view", false, false, nil, nil),
 | 
			
		||||
			"send":    NewMethod("send", "send", Function, "", false, false, []Argument{{"amount", Uint256, false}}, nil),
 | 
			
		||||
		},
 | 
			
		||||
		Methods: methods,
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	exp, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
@@ -71,7 +119,6 @@ func TestReader(t *testing.T) {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// deep equal fails for some reason
 | 
			
		||||
	for name, expM := range exp.Methods {
 | 
			
		||||
		gotM, exist := abi.Methods[name]
 | 
			
		||||
		if !exist {
 | 
			
		||||
@@ -93,8 +140,58 @@ func TestReader(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestInvalidABI(t *testing.T) {
 | 
			
		||||
	json := `[{ "type" : "function", "name" : "", "constant" : fals }]`
 | 
			
		||||
	_, err := JSON(strings.NewReader(json))
 | 
			
		||||
	if err == nil {
 | 
			
		||||
		t.Fatal("invalid json should produce error")
 | 
			
		||||
	}
 | 
			
		||||
	json2 := `[{ "type" : "function", "name" : "send", "constant" : false, "inputs" : [ { "name" : "amount", "typ" : "uint256" } ] }]`
 | 
			
		||||
	_, err = JSON(strings.NewReader(json2))
 | 
			
		||||
	if err == nil {
 | 
			
		||||
		t.Fatal("invalid json should produce error")
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TestConstructor tests a constructor function.
 | 
			
		||||
// The test is based on the following contract:
 | 
			
		||||
// 	contract TestConstructor {
 | 
			
		||||
// 		constructor(uint256 a, uint256 b) public{}
 | 
			
		||||
//	}
 | 
			
		||||
func TestConstructor(t *testing.T) {
 | 
			
		||||
	json := `[{	"inputs": [{"internalType": "uint256","name": "a","type": "uint256"	},{	"internalType": "uint256","name": "b","type": "uint256"}],"stateMutability": "nonpayable","type": "constructor"}]`
 | 
			
		||||
	method := NewMethod("", "", Constructor, "nonpayable", false, false, []Argument{{"a", Uint256, false}, {"b", Uint256, false}}, nil)
 | 
			
		||||
	// Test from JSON
 | 
			
		||||
	abi, err := JSON(strings.NewReader(json))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	if !reflect.DeepEqual(abi.Constructor, method) {
 | 
			
		||||
		t.Error("Missing expected constructor")
 | 
			
		||||
	}
 | 
			
		||||
	// Test pack/unpack
 | 
			
		||||
	packed, err := abi.Pack("", big.NewInt(1), big.NewInt(2))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
	v := struct {
 | 
			
		||||
		A *big.Int
 | 
			
		||||
		B *big.Int
 | 
			
		||||
	}{new(big.Int), new(big.Int)}
 | 
			
		||||
	//abi.Unpack(&v, "", packed)
 | 
			
		||||
	if err := abi.Constructor.Inputs.Unpack(&v, packed); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
	if !reflect.DeepEqual(v.A, big.NewInt(1)) {
 | 
			
		||||
		t.Error("Unable to pack/unpack from constructor")
 | 
			
		||||
	}
 | 
			
		||||
	if !reflect.DeepEqual(v.B, big.NewInt(2)) {
 | 
			
		||||
		t.Error("Unable to pack/unpack from constructor")
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestTestNumbers(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
@@ -130,44 +227,7 @@ func TestTestNumbers(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestTestString(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if _, err := abi.Pack("string", "hello world"); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestTestBool(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if _, err := abi.Pack("bool", true); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestTestSlice(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	slice := make([]uint64, 2)
 | 
			
		||||
	if _, err := abi.Pack("uint64[2]", slice); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
	if _, err := abi.Pack("uint64[]", slice); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestMethodSignature(t *testing.T) {
 | 
			
		||||
	String, _ := NewType("string", "", nil)
 | 
			
		||||
	m := NewMethod("foo", "foo", Function, "", false, false, []Argument{{"bar", String, false}, {"baz", String, false}}, nil)
 | 
			
		||||
	exp := "foo(string,string)"
 | 
			
		||||
	if m.Sig != exp {
 | 
			
		||||
@@ -179,8 +239,7 @@ func TestMethodSignature(t *testing.T) {
 | 
			
		||||
		t.Errorf("expected ids to match %x != %x", m.ID, idexp)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	uintt, _ := NewType("uint256", "", nil)
 | 
			
		||||
	m = NewMethod("foo", "foo", Function, "", false, false, []Argument{{"bar", uintt, false}}, nil)
 | 
			
		||||
	m = NewMethod("foo", "foo", Function, "", false, false, []Argument{{"bar", Uint256, false}}, nil)
 | 
			
		||||
	exp = "foo(uint256)"
 | 
			
		||||
	if m.Sig != exp {
 | 
			
		||||
		t.Error("signature mismatch", exp, "!=", m.Sig)
 | 
			
		||||
@@ -230,7 +289,7 @@ func TestOverloadedMethodSignature(t *testing.T) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestMultiPack(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
@@ -395,15 +454,7 @@ func TestInputVariableInputLength(t *testing.T) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestInputFixedArrayAndVariableInputLength(t *testing.T) {
 | 
			
		||||
	const definition = `[
 | 
			
		||||
	{ "type" : "function", "name" : "fixedArrStr", "constant" : true, "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr", "type" : "uint256[2]" } ] },
 | 
			
		||||
	{ "type" : "function", "name" : "fixedArrBytes", "constant" : true, "inputs" : [ { "name" : "str", "type" : "bytes" }, { "name" : "fixedArr", "type" : "uint256[2]" } ] },
 | 
			
		||||
    { "type" : "function", "name" : "mixedArrStr", "constant" : true, "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr", "type": "uint256[2]" }, { "name" : "dynArr", "type": "uint256[]" } ] },
 | 
			
		||||
    { "type" : "function", "name" : "doubleFixedArrStr", "constant" : true, "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr1", "type": "uint256[2]" }, { "name" : "fixedArr2", "type": "uint256[3]" } ] },
 | 
			
		||||
    { "type" : "function", "name" : "multipleMixedArrStr", "constant" : true, "inputs" : [ { "name" : "str", "type" : "string" }, { "name" : "fixedArr1", "type": "uint256[2]" }, { "name" : "dynArr", "type" : "uint256[]" }, { "name" : "fixedArr2", "type" : "uint256[3]" } ] }
 | 
			
		||||
	]`
 | 
			
		||||
 | 
			
		||||
	abi, err := JSON(strings.NewReader(definition))
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
@@ -597,8 +648,6 @@ func TestBareEvents(t *testing.T) {
 | 
			
		||||
	{ "type" : "event", "name" : "tuple", "inputs" : [{ "indexed":false, "name":"t", "type":"tuple", "components":[{"name":"a", "type":"uint256"}] }, { "indexed":true, "name":"arg1", "type":"address" }] }
 | 
			
		||||
	]`
 | 
			
		||||
 | 
			
		||||
	arg0, _ := NewType("uint256", "", nil)
 | 
			
		||||
	arg1, _ := NewType("address", "", nil)
 | 
			
		||||
	tuple, _ := NewType("tuple", "", []ArgumentMarshaling{{Name: "a", Type: "uint256"}})
 | 
			
		||||
 | 
			
		||||
	expectedEvents := map[string]struct {
 | 
			
		||||
@@ -608,12 +657,12 @@ func TestBareEvents(t *testing.T) {
 | 
			
		||||
		"balance": {false, nil},
 | 
			
		||||
		"anon":    {true, nil},
 | 
			
		||||
		"args": {false, []Argument{
 | 
			
		||||
			{Name: "arg0", Type: arg0, Indexed: false},
 | 
			
		||||
			{Name: "arg1", Type: arg1, Indexed: true},
 | 
			
		||||
			{Name: "arg0", Type: Uint256, Indexed: false},
 | 
			
		||||
			{Name: "arg1", Type: Address, Indexed: true},
 | 
			
		||||
		}},
 | 
			
		||||
		"tuple": {false, []Argument{
 | 
			
		||||
			{Name: "t", Type: tuple, Indexed: false},
 | 
			
		||||
			{Name: "arg1", Type: arg1, Indexed: true},
 | 
			
		||||
			{Name: "arg1", Type: Address, Indexed: true},
 | 
			
		||||
		}},
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
@@ -886,31 +935,7 @@ func TestUnpackIntoMapNamingConflict(t *testing.T) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestABI_MethodById(t *testing.T) {
 | 
			
		||||
	const abiJSON = `[
 | 
			
		||||
		{"type":"function","name":"receive","constant":false,"inputs":[{"name":"memo","type":"bytes"}],"outputs":[],"payable":true,"stateMutability":"payable"},
 | 
			
		||||
		{"type":"event","name":"received","anonymous":false,"inputs":[{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}]},
 | 
			
		||||
		{"type":"function","name":"fixedArrStr","constant":true,"inputs":[{"name":"str","type":"string"},{"name":"fixedArr","type":"uint256[2]"}]},
 | 
			
		||||
		{"type":"function","name":"fixedArrBytes","constant":true,"inputs":[{"name":"str","type":"bytes"},{"name":"fixedArr","type":"uint256[2]"}]},
 | 
			
		||||
		{"type":"function","name":"mixedArrStr","constant":true,"inputs":[{"name":"str","type":"string"},{"name":"fixedArr","type":"uint256[2]"},{"name":"dynArr","type":"uint256[]"}]},
 | 
			
		||||
		{"type":"function","name":"doubleFixedArrStr","constant":true,"inputs":[{"name":"str","type":"string"},{"name":"fixedArr1","type":"uint256[2]"},{"name":"fixedArr2","type":"uint256[3]"}]},
 | 
			
		||||
		{"type":"function","name":"multipleMixedArrStr","constant":true,"inputs":[{"name":"str","type":"string"},{"name":"fixedArr1","type":"uint256[2]"},{"name":"dynArr","type":"uint256[]"},{"name":"fixedArr2","type":"uint256[3]"}]},
 | 
			
		||||
		{"type":"function","name":"balance","constant":true},
 | 
			
		||||
		{"type":"function","name":"send","constant":false,"inputs":[{"name":"amount","type":"uint256"}]},
 | 
			
		||||
		{"type":"function","name":"test","constant":false,"inputs":[{"name":"number","type":"uint32"}]},
 | 
			
		||||
		{"type":"function","name":"string","constant":false,"inputs":[{"name":"inputs","type":"string"}]},
 | 
			
		||||
		{"type":"function","name":"bool","constant":false,"inputs":[{"name":"inputs","type":"bool"}]},
 | 
			
		||||
		{"type":"function","name":"address","constant":false,"inputs":[{"name":"inputs","type":"address"}]},
 | 
			
		||||
		{"type":"function","name":"uint64[2]","constant":false,"inputs":[{"name":"inputs","type":"uint64[2]"}]},
 | 
			
		||||
		{"type":"function","name":"uint64[]","constant":false,"inputs":[{"name":"inputs","type":"uint64[]"}]},
 | 
			
		||||
		{"type":"function","name":"foo","constant":false,"inputs":[{"name":"inputs","type":"uint32"}]},
 | 
			
		||||
		{"type":"function","name":"bar","constant":false,"inputs":[{"name":"inputs","type":"uint32"},{"name":"string","type":"uint16"}]},
 | 
			
		||||
		{"type":"function","name":"_slice","constant":false,"inputs":[{"name":"inputs","type":"uint32[2]"}]},
 | 
			
		||||
		{"type":"function","name":"__slice256","constant":false,"inputs":[{"name":"inputs","type":"uint256[2]"}]},
 | 
			
		||||
		{"type":"function","name":"sliceAddress","constant":false,"inputs":[{"name":"inputs","type":"address[]"}]},
 | 
			
		||||
		{"type":"function","name":"sliceMultiAddress","constant":false,"inputs":[{"name":"a","type":"address[]"},{"name":"b","type":"address[]"}]}
 | 
			
		||||
	]
 | 
			
		||||
`
 | 
			
		||||
	abi, err := JSON(strings.NewReader(abiJSON))
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
@@ -925,6 +950,10 @@ func TestABI_MethodById(t *testing.T) {
 | 
			
		||||
			t.Errorf("Method %v (id %x) not 'findable' by id in ABI", name, m.ID)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	// test unsuccessful lookups
 | 
			
		||||
	if _, err = abi.MethodById(crypto.Keccak256()); err == nil {
 | 
			
		||||
		t.Error("Expected error: no method with this id")
 | 
			
		||||
	}
 | 
			
		||||
	// Also test empty
 | 
			
		||||
	if _, err := abi.MethodById([]byte{0x00}); err == nil {
 | 
			
		||||
		t.Errorf("Expected error, too short to decode data")
 | 
			
		||||
@@ -1005,26 +1034,6 @@ func TestABI_EventById(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestDuplicateMethodNames(t *testing.T) {
 | 
			
		||||
	abiJSON := `[{"constant":false,"inputs":[{"name":"to","type":"address"},{"name":"value","type":"uint256"}],"name":"transfer","outputs":[{"name":"ok","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"name":"to","type":"address"},{"name":"value","type":"uint256"},{"name":"data","type":"bytes"}],"name":"transfer","outputs":[{"name":"ok","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"name":"to","type":"address"},{"name":"value","type":"uint256"},{"name":"data","type":"bytes"},{"name":"customFallback","type":"string"}],"name":"transfer","outputs":[{"name":"ok","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"}]`
 | 
			
		||||
	contractAbi, err := JSON(strings.NewReader(abiJSON))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Methods["transfer"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find original method")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Methods["transfer0"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find duplicate method")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Methods["transfer1"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find duplicate method")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Methods["transfer2"]; ok {
 | 
			
		||||
		t.Fatalf("Should not have found extra method")
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TestDoubleDuplicateMethodNames checks that if transfer0 already exists, there won't be a name
 | 
			
		||||
// conflict and that the second transfer method will be renamed transfer1.
 | 
			
		||||
func TestDoubleDuplicateMethodNames(t *testing.T) {
 | 
			
		||||
@@ -1047,6 +1056,34 @@ func TestDoubleDuplicateMethodNames(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TestDoubleDuplicateEventNames checks that if send0 already exists, there won't be a name
 | 
			
		||||
// conflict and that the second send event will be renamed send1.
 | 
			
		||||
// The test runs the abi of the following contract.
 | 
			
		||||
// 	contract DuplicateEvent {
 | 
			
		||||
// 		event send(uint256 a);
 | 
			
		||||
//		event send0();
 | 
			
		||||
//		event send();
 | 
			
		||||
//	}
 | 
			
		||||
func TestDoubleDuplicateEventNames(t *testing.T) {
 | 
			
		||||
	abiJSON := `[{"anonymous": false,"inputs": [{"indexed": false,"internalType": "uint256","name": "a","type": "uint256"}],"name": "send","type": "event"},{"anonymous": false,"inputs": [],"name": "send0","type": "event"},{	"anonymous": false,	"inputs": [],"name": "send","type": "event"}]`
 | 
			
		||||
	contractAbi, err := JSON(strings.NewReader(abiJSON))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Events["send"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find original event")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Events["send0"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find duplicate event")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Events["send1"]; !ok {
 | 
			
		||||
		t.Fatalf("Could not find duplicate event")
 | 
			
		||||
	}
 | 
			
		||||
	if _, ok := contractAbi.Events["send2"]; ok {
 | 
			
		||||
		t.Fatalf("Should not have found extra event")
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TestUnnamedEventParam checks that an event with unnamed parameters is
 | 
			
		||||
// correctly handled
 | 
			
		||||
// The test runs the abi of the following contract.
 | 
			
		||||
 
 | 
			
		||||
@@ -59,18 +59,6 @@ func (argument *Argument) UnmarshalJSON(data []byte) error {
 | 
			
		||||
	return nil
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// LengthNonIndexed returns the number of arguments when not counting 'indexed' ones. Only events
 | 
			
		||||
// can ever have 'indexed' arguments, it should always be false on arguments for method input/output
 | 
			
		||||
func (arguments Arguments) LengthNonIndexed() int {
 | 
			
		||||
	out := 0
 | 
			
		||||
	for _, arg := range arguments {
 | 
			
		||||
		if !arg.Indexed {
 | 
			
		||||
			out++
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	return out
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// NonIndexed returns the arguments with indexed arguments filtered out
 | 
			
		||||
func (arguments Arguments) NonIndexed() Arguments {
 | 
			
		||||
	var ret []Argument
 | 
			
		||||
@@ -205,10 +193,11 @@ func unpack(t *Type, dst interface{}, src interface{}) error {
 | 
			
		||||
 | 
			
		||||
// unpackAtomic unpacks ( hexdata -> go ) a single value
 | 
			
		||||
func (arguments Arguments) unpackAtomic(v interface{}, marshalledValues interface{}) error {
 | 
			
		||||
	if arguments.LengthNonIndexed() == 0 {
 | 
			
		||||
	nonIndexedArgs := arguments.NonIndexed()
 | 
			
		||||
	if len(nonIndexedArgs) == 0 {
 | 
			
		||||
		return nil
 | 
			
		||||
	}
 | 
			
		||||
	argument := arguments.NonIndexed()[0]
 | 
			
		||||
	argument := nonIndexedArgs[0]
 | 
			
		||||
	elem := reflect.ValueOf(v).Elem()
 | 
			
		||||
 | 
			
		||||
	if elem.Kind() == reflect.Struct && argument.Type.T != TupleTy {
 | 
			
		||||
@@ -282,9 +271,10 @@ func (arguments Arguments) unpackTuple(v interface{}, marshalledValues []interfa
 | 
			
		||||
// without supplying a struct to unpack into. Instead, this method returns a list containing the
 | 
			
		||||
// values. An atomic argument will be a list with one element.
 | 
			
		||||
func (arguments Arguments) UnpackValues(data []byte) ([]interface{}, error) {
 | 
			
		||||
	retval := make([]interface{}, 0, arguments.LengthNonIndexed())
 | 
			
		||||
	nonIndexedArgs := arguments.NonIndexed()
 | 
			
		||||
	retval := make([]interface{}, 0, len(nonIndexedArgs))
 | 
			
		||||
	virtualArgs := 0
 | 
			
		||||
	for index, arg := range arguments.NonIndexed() {
 | 
			
		||||
	for index, arg := range nonIndexedArgs {
 | 
			
		||||
		marshalledValue, err := ToGoType((index+virtualArgs)*32, arg.Type, data)
 | 
			
		||||
		if arg.Type.T == ArrayTy && !isDynamicType(arg.Type) {
 | 
			
		||||
			// If we have a static array, like [3]uint256, these are coded as
 | 
			
		||||
 
 | 
			
		||||
@@ -17,9 +17,9 @@
 | 
			
		||||
package bind_test
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"bytes"
 | 
			
		||||
	"context"
 | 
			
		||||
	"math/big"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"strings"
 | 
			
		||||
	"testing"
 | 
			
		||||
 | 
			
		||||
@@ -88,51 +88,23 @@ const hexData = "0x000000000000000000000000376c47978271565f56deb45495afa69e59c16
 | 
			
		||||
 | 
			
		||||
func TestUnpackIndexedStringTyLogIntoMap(t *testing.T) {
 | 
			
		||||
	hash := crypto.Keccak256Hash([]byte("testName"))
 | 
			
		||||
	mockLog := types.Log{
 | 
			
		||||
		Address: common.HexToAddress("0x0"),
 | 
			
		||||
		Topics: []common.Hash{
 | 
			
		||||
			common.HexToHash("0x0"),
 | 
			
		||||
			hash,
 | 
			
		||||
		},
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      common.HexToHash("0x0"),
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	topics := []common.Hash{
 | 
			
		||||
		common.HexToHash("0x0"),
 | 
			
		||||
		hash,
 | 
			
		||||
	}
 | 
			
		||||
	mockLog := newMockLog(topics, common.HexToHash("0x0"))
 | 
			
		||||
 | 
			
		||||
	abiString := `[{"anonymous":false,"inputs":[{"indexed":true,"name":"name","type":"string"},{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}],"name":"received","type":"event"}]`
 | 
			
		||||
	parsedAbi, _ := abi.JSON(strings.NewReader(abiString))
 | 
			
		||||
	bc := bind.NewBoundContract(common.HexToAddress("0x0"), parsedAbi, nil, nil, nil)
 | 
			
		||||
 | 
			
		||||
	receivedMap := make(map[string]interface{})
 | 
			
		||||
	expectedReceivedMap := map[string]interface{}{
 | 
			
		||||
		"name":   hash,
 | 
			
		||||
		"sender": common.HexToAddress("0x376c47978271565f56DEB45495afa69E59c16Ab2"),
 | 
			
		||||
		"amount": big.NewInt(1),
 | 
			
		||||
		"memo":   []byte{88},
 | 
			
		||||
	}
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(receivedMap, "received", mockLog); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(receivedMap) != 4 {
 | 
			
		||||
		t.Fatal("unpacked map expected to have length 4")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["name"] != expectedReceivedMap["name"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["sender"] != expectedReceivedMap["sender"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["amount"].(*big.Int).Cmp(expectedReceivedMap["amount"].(*big.Int)) != 0 {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if !bytes.Equal(receivedMap["memo"].([]byte), expectedReceivedMap["memo"].([]byte)) {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	unpackAndCheck(t, bc, expectedReceivedMap, mockLog)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestUnpackIndexedSliceTyLogIntoMap(t *testing.T) {
 | 
			
		||||
@@ -141,51 +113,23 @@ func TestUnpackIndexedSliceTyLogIntoMap(t *testing.T) {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	hash := crypto.Keccak256Hash(sliceBytes)
 | 
			
		||||
	mockLog := types.Log{
 | 
			
		||||
		Address: common.HexToAddress("0x0"),
 | 
			
		||||
		Topics: []common.Hash{
 | 
			
		||||
			common.HexToHash("0x0"),
 | 
			
		||||
			hash,
 | 
			
		||||
		},
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      common.HexToHash("0x0"),
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	topics := []common.Hash{
 | 
			
		||||
		common.HexToHash("0x0"),
 | 
			
		||||
		hash,
 | 
			
		||||
	}
 | 
			
		||||
	mockLog := newMockLog(topics, common.HexToHash("0x0"))
 | 
			
		||||
 | 
			
		||||
	abiString := `[{"anonymous":false,"inputs":[{"indexed":true,"name":"names","type":"string[]"},{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}],"name":"received","type":"event"}]`
 | 
			
		||||
	parsedAbi, _ := abi.JSON(strings.NewReader(abiString))
 | 
			
		||||
	bc := bind.NewBoundContract(common.HexToAddress("0x0"), parsedAbi, nil, nil, nil)
 | 
			
		||||
 | 
			
		||||
	receivedMap := make(map[string]interface{})
 | 
			
		||||
	expectedReceivedMap := map[string]interface{}{
 | 
			
		||||
		"names":  hash,
 | 
			
		||||
		"sender": common.HexToAddress("0x376c47978271565f56DEB45495afa69E59c16Ab2"),
 | 
			
		||||
		"amount": big.NewInt(1),
 | 
			
		||||
		"memo":   []byte{88},
 | 
			
		||||
	}
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(receivedMap, "received", mockLog); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(receivedMap) != 4 {
 | 
			
		||||
		t.Fatal("unpacked map expected to have length 4")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["names"] != expectedReceivedMap["names"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["sender"] != expectedReceivedMap["sender"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["amount"].(*big.Int).Cmp(expectedReceivedMap["amount"].(*big.Int)) != 0 {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if !bytes.Equal(receivedMap["memo"].([]byte), expectedReceivedMap["memo"].([]byte)) {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	unpackAndCheck(t, bc, expectedReceivedMap, mockLog)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestUnpackIndexedArrayTyLogIntoMap(t *testing.T) {
 | 
			
		||||
@@ -194,51 +138,23 @@ func TestUnpackIndexedArrayTyLogIntoMap(t *testing.T) {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
	hash := crypto.Keccak256Hash(arrBytes)
 | 
			
		||||
	mockLog := types.Log{
 | 
			
		||||
		Address: common.HexToAddress("0x0"),
 | 
			
		||||
		Topics: []common.Hash{
 | 
			
		||||
			common.HexToHash("0x0"),
 | 
			
		||||
			hash,
 | 
			
		||||
		},
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      common.HexToHash("0x0"),
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	topics := []common.Hash{
 | 
			
		||||
		common.HexToHash("0x0"),
 | 
			
		||||
		hash,
 | 
			
		||||
	}
 | 
			
		||||
	mockLog := newMockLog(topics, common.HexToHash("0x0"))
 | 
			
		||||
 | 
			
		||||
	abiString := `[{"anonymous":false,"inputs":[{"indexed":true,"name":"addresses","type":"address[2]"},{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}],"name":"received","type":"event"}]`
 | 
			
		||||
	parsedAbi, _ := abi.JSON(strings.NewReader(abiString))
 | 
			
		||||
	bc := bind.NewBoundContract(common.HexToAddress("0x0"), parsedAbi, nil, nil, nil)
 | 
			
		||||
 | 
			
		||||
	receivedMap := make(map[string]interface{})
 | 
			
		||||
	expectedReceivedMap := map[string]interface{}{
 | 
			
		||||
		"addresses": hash,
 | 
			
		||||
		"sender":    common.HexToAddress("0x376c47978271565f56DEB45495afa69E59c16Ab2"),
 | 
			
		||||
		"amount":    big.NewInt(1),
 | 
			
		||||
		"memo":      []byte{88},
 | 
			
		||||
	}
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(receivedMap, "received", mockLog); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(receivedMap) != 4 {
 | 
			
		||||
		t.Fatal("unpacked map expected to have length 4")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["addresses"] != expectedReceivedMap["addresses"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["sender"] != expectedReceivedMap["sender"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["amount"].(*big.Int).Cmp(expectedReceivedMap["amount"].(*big.Int)) != 0 {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if !bytes.Equal(receivedMap["memo"].([]byte), expectedReceivedMap["memo"].([]byte)) {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	unpackAndCheck(t, bc, expectedReceivedMap, mockLog)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestUnpackIndexedFuncTyLogIntoMap(t *testing.T) {
 | 
			
		||||
@@ -249,99 +165,72 @@ func TestUnpackIndexedFuncTyLogIntoMap(t *testing.T) {
 | 
			
		||||
	functionTyBytes := append(addrBytes, functionSelector...)
 | 
			
		||||
	var functionTy [24]byte
 | 
			
		||||
	copy(functionTy[:], functionTyBytes[0:24])
 | 
			
		||||
	mockLog := types.Log{
 | 
			
		||||
		Address: common.HexToAddress("0x0"),
 | 
			
		||||
		Topics: []common.Hash{
 | 
			
		||||
			common.HexToHash("0x99b5620489b6ef926d4518936cfec15d305452712b88bd59da2d9c10fb0953e8"),
 | 
			
		||||
			common.BytesToHash(functionTyBytes),
 | 
			
		||||
		},
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      common.HexToHash("0x5c698f13940a2153440c6d19660878bc90219d9298fdcf37365aa8d88d40fc42"),
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	topics := []common.Hash{
 | 
			
		||||
		common.HexToHash("0x99b5620489b6ef926d4518936cfec15d305452712b88bd59da2d9c10fb0953e8"),
 | 
			
		||||
		common.BytesToHash(functionTyBytes),
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	mockLog := newMockLog(topics, common.HexToHash("0x5c698f13940a2153440c6d19660878bc90219d9298fdcf37365aa8d88d40fc42"))
 | 
			
		||||
	abiString := `[{"anonymous":false,"inputs":[{"indexed":true,"name":"function","type":"function"},{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}],"name":"received","type":"event"}]`
 | 
			
		||||
	parsedAbi, _ := abi.JSON(strings.NewReader(abiString))
 | 
			
		||||
	bc := bind.NewBoundContract(common.HexToAddress("0x0"), parsedAbi, nil, nil, nil)
 | 
			
		||||
 | 
			
		||||
	receivedMap := make(map[string]interface{})
 | 
			
		||||
	expectedReceivedMap := map[string]interface{}{
 | 
			
		||||
		"function": functionTy,
 | 
			
		||||
		"sender":   common.HexToAddress("0x376c47978271565f56DEB45495afa69E59c16Ab2"),
 | 
			
		||||
		"amount":   big.NewInt(1),
 | 
			
		||||
		"memo":     []byte{88},
 | 
			
		||||
	}
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(receivedMap, "received", mockLog); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(receivedMap) != 4 {
 | 
			
		||||
		t.Fatal("unpacked map expected to have length 4")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["function"] != expectedReceivedMap["function"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["sender"] != expectedReceivedMap["sender"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["amount"].(*big.Int).Cmp(expectedReceivedMap["amount"].(*big.Int)) != 0 {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if !bytes.Equal(receivedMap["memo"].([]byte), expectedReceivedMap["memo"].([]byte)) {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	unpackAndCheck(t, bc, expectedReceivedMap, mockLog)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestUnpackIndexedBytesTyLogIntoMap(t *testing.T) {
 | 
			
		||||
	byts := []byte{1, 2, 3, 4, 5}
 | 
			
		||||
	hash := crypto.Keccak256Hash(byts)
 | 
			
		||||
	mockLog := types.Log{
 | 
			
		||||
		Address: common.HexToAddress("0x0"),
 | 
			
		||||
		Topics: []common.Hash{
 | 
			
		||||
			common.HexToHash("0x99b5620489b6ef926d4518936cfec15d305452712b88bd59da2d9c10fb0953e8"),
 | 
			
		||||
			hash,
 | 
			
		||||
		},
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      common.HexToHash("0x5c698f13940a2153440c6d19660878bc90219d9298fdcf37365aa8d88d40fc42"),
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	bytes := []byte{1, 2, 3, 4, 5}
 | 
			
		||||
	hash := crypto.Keccak256Hash(bytes)
 | 
			
		||||
	topics := []common.Hash{
 | 
			
		||||
		common.HexToHash("0x99b5620489b6ef926d4518936cfec15d305452712b88bd59da2d9c10fb0953e8"),
 | 
			
		||||
		hash,
 | 
			
		||||
	}
 | 
			
		||||
	mockLog := newMockLog(topics, common.HexToHash("0x5c698f13940a2153440c6d19660878bc90219d9298fdcf37365aa8d88d40fc42"))
 | 
			
		||||
 | 
			
		||||
	abiString := `[{"anonymous":false,"inputs":[{"indexed":true,"name":"content","type":"bytes"},{"indexed":false,"name":"sender","type":"address"},{"indexed":false,"name":"amount","type":"uint256"},{"indexed":false,"name":"memo","type":"bytes"}],"name":"received","type":"event"}]`
 | 
			
		||||
	parsedAbi, _ := abi.JSON(strings.NewReader(abiString))
 | 
			
		||||
	bc := bind.NewBoundContract(common.HexToAddress("0x0"), parsedAbi, nil, nil, nil)
 | 
			
		||||
 | 
			
		||||
	receivedMap := make(map[string]interface{})
 | 
			
		||||
	expectedReceivedMap := map[string]interface{}{
 | 
			
		||||
		"content": hash,
 | 
			
		||||
		"sender":  common.HexToAddress("0x376c47978271565f56DEB45495afa69E59c16Ab2"),
 | 
			
		||||
		"amount":  big.NewInt(1),
 | 
			
		||||
		"memo":    []byte{88},
 | 
			
		||||
	}
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(receivedMap, "received", mockLog); err != nil {
 | 
			
		||||
	unpackAndCheck(t, bc, expectedReceivedMap, mockLog)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func unpackAndCheck(t *testing.T, bc *bind.BoundContract, expected map[string]interface{}, mockLog types.Log) {
 | 
			
		||||
	received := make(map[string]interface{})
 | 
			
		||||
	if err := bc.UnpackLogIntoMap(received, "received", mockLog); err != nil {
 | 
			
		||||
		t.Error(err)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(receivedMap) != 4 {
 | 
			
		||||
		t.Fatal("unpacked map expected to have length 4")
 | 
			
		||||
	if len(received) != len(expected) {
 | 
			
		||||
		t.Fatalf("unpacked map length %v not equal expected length of %v", len(received), len(expected))
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["content"] != expectedReceivedMap["content"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["sender"] != expectedReceivedMap["sender"] {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if receivedMap["amount"].(*big.Int).Cmp(expectedReceivedMap["amount"].(*big.Int)) != 0 {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	}
 | 
			
		||||
	if !bytes.Equal(receivedMap["memo"].([]byte), expectedReceivedMap["memo"].([]byte)) {
 | 
			
		||||
		t.Error("unpacked map does not match expected map")
 | 
			
		||||
	for name, elem := range expected {
 | 
			
		||||
		if !reflect.DeepEqual(elem, received[name]) {
 | 
			
		||||
			t.Errorf("field %v does not match expected, want %v, got %v", name, elem, received[name])
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func newMockLog(topics []common.Hash, txHash common.Hash) types.Log {
 | 
			
		||||
	return types.Log{
 | 
			
		||||
		Address:     common.HexToAddress("0x0"),
 | 
			
		||||
		Topics:      topics,
 | 
			
		||||
		Data:        hexutil.MustDecode(hexData),
 | 
			
		||||
		BlockNumber: uint64(26),
 | 
			
		||||
		TxHash:      txHash,
 | 
			
		||||
		TxIndex:     111,
 | 
			
		||||
		BlockHash:   common.BytesToHash([]byte{1, 2, 3, 4, 5}),
 | 
			
		||||
		Index:       7,
 | 
			
		||||
		Removed:     false,
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -46,12 +46,10 @@ func sliceTypeCheck(t Type, val reflect.Value) error {
 | 
			
		||||
		return typeErr(formatSliceString(t.Elem.Kind, t.Size), formatSliceString(val.Type().Elem().Kind(), val.Len()))
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if t.Elem.T == SliceTy {
 | 
			
		||||
	if t.Elem.T == SliceTy || t.Elem.T == ArrayTy {
 | 
			
		||||
		if val.Len() > 0 {
 | 
			
		||||
			return sliceTypeCheck(*t.Elem, val.Index(0))
 | 
			
		||||
		}
 | 
			
		||||
	} else if t.Elem.T == ArrayTy {
 | 
			
		||||
		return sliceTypeCheck(*t.Elem, val.Index(0))
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if elemKind := val.Type().Elem().Kind(); elemKind != t.Elem.Kind {
 | 
			
		||||
 
 | 
			
		||||
@@ -39,6 +39,7 @@ var (
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
// U256 converts a big Int into a 256bit EVM number.
 | 
			
		||||
// This operation is destructive.
 | 
			
		||||
func U256(n *big.Int) []byte {
 | 
			
		||||
	return math.PaddedBigBytes(math.U256(n), 32)
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -18,618 +18,57 @@ package abi
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"bytes"
 | 
			
		||||
	"encoding/hex"
 | 
			
		||||
	"fmt"
 | 
			
		||||
	"math"
 | 
			
		||||
	"math/big"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"strconv"
 | 
			
		||||
	"strings"
 | 
			
		||||
	"testing"
 | 
			
		||||
 | 
			
		||||
	"github.com/ethereum/go-ethereum/common"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
// TestPack tests the general pack/unpack tests in packing_test.go
 | 
			
		||||
func TestPack(t *testing.T) {
 | 
			
		||||
	for i, test := range []struct {
 | 
			
		||||
		typ        string
 | 
			
		||||
		components []ArgumentMarshaling
 | 
			
		||||
		input      interface{}
 | 
			
		||||
		output     []byte
 | 
			
		||||
	}{
 | 
			
		||||
		{
 | 
			
		||||
			"uint8",
 | 
			
		||||
			nil,
 | 
			
		||||
			uint8(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint8[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]uint8{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint16",
 | 
			
		||||
			nil,
 | 
			
		||||
			uint16(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint16[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]uint16{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint32",
 | 
			
		||||
			nil,
 | 
			
		||||
			uint32(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint32[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]uint32{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint64",
 | 
			
		||||
			nil,
 | 
			
		||||
			uint64(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint64[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]uint64{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint256",
 | 
			
		||||
			nil,
 | 
			
		||||
			big.NewInt(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint256[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int8",
 | 
			
		||||
			nil,
 | 
			
		||||
			int8(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int8[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]int8{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int16",
 | 
			
		||||
			nil,
 | 
			
		||||
			int16(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int16[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]int16{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int32",
 | 
			
		||||
			nil,
 | 
			
		||||
			int32(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int32[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]int32{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int64",
 | 
			
		||||
			nil,
 | 
			
		||||
			int64(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int64[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]int64{1, 2},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int256",
 | 
			
		||||
			nil,
 | 
			
		||||
			big.NewInt(2),
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"int256[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes1",
 | 
			
		||||
			nil,
 | 
			
		||||
			[1]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes2",
 | 
			
		||||
			nil,
 | 
			
		||||
			[2]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes3",
 | 
			
		||||
			nil,
 | 
			
		||||
			[3]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes4",
 | 
			
		||||
			nil,
 | 
			
		||||
			[4]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes5",
 | 
			
		||||
			nil,
 | 
			
		||||
			[5]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes6",
 | 
			
		||||
			nil,
 | 
			
		||||
			[6]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes7",
 | 
			
		||||
			nil,
 | 
			
		||||
			[7]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes8",
 | 
			
		||||
			nil,
 | 
			
		||||
			[8]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes9",
 | 
			
		||||
			nil,
 | 
			
		||||
			[9]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes10",
 | 
			
		||||
			nil,
 | 
			
		||||
			[10]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes11",
 | 
			
		||||
			nil,
 | 
			
		||||
			[11]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes12",
 | 
			
		||||
			nil,
 | 
			
		||||
			[12]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes13",
 | 
			
		||||
			nil,
 | 
			
		||||
			[13]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes14",
 | 
			
		||||
			nil,
 | 
			
		||||
			[14]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes15",
 | 
			
		||||
			nil,
 | 
			
		||||
			[15]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes16",
 | 
			
		||||
			nil,
 | 
			
		||||
			[16]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes17",
 | 
			
		||||
			nil,
 | 
			
		||||
			[17]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes18",
 | 
			
		||||
			nil,
 | 
			
		||||
			[18]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes19",
 | 
			
		||||
			nil,
 | 
			
		||||
			[19]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes20",
 | 
			
		||||
			nil,
 | 
			
		||||
			[20]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes21",
 | 
			
		||||
			nil,
 | 
			
		||||
			[21]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes22",
 | 
			
		||||
			nil,
 | 
			
		||||
			[22]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes23",
 | 
			
		||||
			nil,
 | 
			
		||||
			[23]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes24",
 | 
			
		||||
			nil,
 | 
			
		||||
			[24]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes25",
 | 
			
		||||
			nil,
 | 
			
		||||
			[25]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes26",
 | 
			
		||||
			nil,
 | 
			
		||||
			[26]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes27",
 | 
			
		||||
			nil,
 | 
			
		||||
			[27]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes28",
 | 
			
		||||
			nil,
 | 
			
		||||
			[28]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes29",
 | 
			
		||||
			nil,
 | 
			
		||||
			[29]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes30",
 | 
			
		||||
			nil,
 | 
			
		||||
			[30]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes31",
 | 
			
		||||
			nil,
 | 
			
		||||
			[31]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes32",
 | 
			
		||||
			nil,
 | 
			
		||||
			[32]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"uint32[2][3][4]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[4][3][2]uint32{{{1, 2}, {3, 4}, {5, 6}}, {{7, 8}, {9, 10}, {11, 12}}, {{13, 14}, {15, 16}, {17, 18}}, {{19, 20}, {21, 22}, {23, 24}}},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000700000000000000000000000000000000000000000000000000000000000000080000000000000000000000000000000000000000000000000000000000000009000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000000000000000000000000000000000000000000b000000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000d000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000f000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000110000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000001300000000000000000000000000000000000000000000000000000000000000140000000000000000000000000000000000000000000000000000000000000015000000000000000000000000000000000000000000000000000000000000001600000000000000000000000000000000000000000000000000000000000000170000000000000000000000000000000000000000000000000000000000000018"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"address[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]common.Address{{1}, {2}},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000200000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes32[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]common.Hash{{1}, {2}},
 | 
			
		||||
			common.Hex2Bytes("000000000000000000000000000000000000000000000000000000000000000201000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"function",
 | 
			
		||||
			nil,
 | 
			
		||||
			[24]byte{1},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"string",
 | 
			
		||||
			nil,
 | 
			
		||||
			"foobar",
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000006666f6f6261720000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"string[]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]string{"hello", "foobar"},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002" + // len(array) = 2
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000080" + // offset 128 to i = 1
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000005" + // len(str[0]) = 5
 | 
			
		||||
				"68656c6c6f000000000000000000000000000000000000000000000000000000" + // str[0]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000006" + // len(str[1]) = 6
 | 
			
		||||
				"666f6f6261720000000000000000000000000000000000000000000000000000"), // str[1]
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"string[2]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[]string{"hello", "foobar"},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000040" + // offset to i = 0
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000080" + // offset to i = 1
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000005" + // len(str[0]) = 5
 | 
			
		||||
				"68656c6c6f000000000000000000000000000000000000000000000000000000" + // str[0]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000006" + // len(str[1]) = 6
 | 
			
		||||
				"666f6f6261720000000000000000000000000000000000000000000000000000"), // str[1]
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			"bytes32[][]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[][]common.Hash{{{1}, {2}}, {{3}, {4}, {5}}},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002" + // len(array) = 2
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
				"00000000000000000000000000000000000000000000000000000000000000a0" + // offset 160 to i = 1
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // len(array[0]) = 2
 | 
			
		||||
				"0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
				"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000003" + // len(array[1]) = 3
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
				"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
				"0500000000000000000000000000000000000000000000000000000000000000"), // array[1][2]
 | 
			
		||||
		},
 | 
			
		||||
 | 
			
		||||
		{
 | 
			
		||||
			"bytes32[][2]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[][]common.Hash{{{1}, {2}}, {{3}, {4}, {5}}},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
				"00000000000000000000000000000000000000000000000000000000000000a0" + // offset 160 to i = 1
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // len(array[0]) = 2
 | 
			
		||||
				"0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
				"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000003" + // len(array[1]) = 3
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
				"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
				"0500000000000000000000000000000000000000000000000000000000000000"), // array[1][2]
 | 
			
		||||
		},
 | 
			
		||||
 | 
			
		||||
		{
 | 
			
		||||
			"bytes32[3][2]",
 | 
			
		||||
			nil,
 | 
			
		||||
			[][]common.Hash{{{1}, {2}, {3}}, {{3}, {4}, {5}}},
 | 
			
		||||
			common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
				"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // array[0][2]
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
				"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
				"0500000000000000000000000000000000000000000000000000000000000000"), // array[1][2]
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// static tuple
 | 
			
		||||
			"tuple",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "int64"},
 | 
			
		||||
				{Name: "b", Type: "int256"},
 | 
			
		||||
				{Name: "c", Type: "int256"},
 | 
			
		||||
				{Name: "d", Type: "bool"},
 | 
			
		||||
				{Name: "e", Type: "bytes32[3][2]"},
 | 
			
		||||
			},
 | 
			
		||||
			struct {
 | 
			
		||||
				A int64
 | 
			
		||||
				B *big.Int
 | 
			
		||||
				C *big.Int
 | 
			
		||||
				D bool
 | 
			
		||||
				E [][]common.Hash
 | 
			
		||||
			}{1, big.NewInt(1), big.NewInt(-1), true, [][]common.Hash{{{1}, {2}, {3}}, {{3}, {4}, {5}}}},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000001" + // struct[a]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // struct[b]
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // struct[c]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // struct[d]
 | 
			
		||||
				"0100000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][0]
 | 
			
		||||
				"0200000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][1]
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][2]
 | 
			
		||||
				"0300000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[1][0]
 | 
			
		||||
				"0400000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[1][1]
 | 
			
		||||
				"0500000000000000000000000000000000000000000000000000000000000000"), // struct[e] array[1][2]
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// dynamic tuple
 | 
			
		||||
			"tuple",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "string"},
 | 
			
		||||
				{Name: "b", Type: "int64"},
 | 
			
		||||
				{Name: "c", Type: "bytes"},
 | 
			
		||||
				{Name: "d", Type: "string[]"},
 | 
			
		||||
				{Name: "e", Type: "int256[]"},
 | 
			
		||||
				{Name: "f", Type: "address[]"},
 | 
			
		||||
			},
 | 
			
		||||
			struct {
 | 
			
		||||
				FieldA string `abi:"a"` // Test whether abi tag works
 | 
			
		||||
				FieldB int64  `abi:"b"`
 | 
			
		||||
				C      []byte
 | 
			
		||||
				D      []string
 | 
			
		||||
				E      []*big.Int
 | 
			
		||||
				F      []common.Address
 | 
			
		||||
			}{"foobar", 1, []byte{1}, []string{"foo", "bar"}, []*big.Int{big.NewInt(1), big.NewInt(-1)}, []common.Address{{1}, {2}}},
 | 
			
		||||
			common.Hex2Bytes("00000000000000000000000000000000000000000000000000000000000000c0" + // struct[a] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // struct[b]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000100" + // struct[c] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000140" + // struct[d] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000220" + // struct[e] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000280" + // struct[f] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000006" + // struct[a] length
 | 
			
		||||
				"666f6f6261720000000000000000000000000000000000000000000000000000" + // struct[a] "foobar"
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // struct[c] length
 | 
			
		||||
				"0100000000000000000000000000000000000000000000000000000000000000" + // []byte{1}
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // struct[d] length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // foo offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000080" + // bar offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000003" + // foo length
 | 
			
		||||
				"666f6f0000000000000000000000000000000000000000000000000000000000" + // foo
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000003" + // bar offset
 | 
			
		||||
				"6261720000000000000000000000000000000000000000000000000000000000" + // bar
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // struct[e] length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // 1
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // -1
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // struct[f] length
 | 
			
		||||
				"0000000000000000000000000100000000000000000000000000000000000000" + // common.Address{1}
 | 
			
		||||
				"0000000000000000000000000200000000000000000000000000000000000000"), // common.Address{2}
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// nested tuple
 | 
			
		||||
			"tuple",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "tuple", Components: []ArgumentMarshaling{{Name: "a", Type: "uint256"}, {Name: "b", Type: "uint256[]"}}},
 | 
			
		||||
				{Name: "b", Type: "int256[]"},
 | 
			
		||||
			},
 | 
			
		||||
			struct {
 | 
			
		||||
				A struct {
 | 
			
		||||
					FieldA *big.Int `abi:"a"`
 | 
			
		||||
					B      []*big.Int
 | 
			
		||||
	for i, test := range packUnpackTests {
 | 
			
		||||
		t.Run(strconv.Itoa(i), func(t *testing.T) {
 | 
			
		||||
			encb, err := hex.DecodeString(test.packed)
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("invalid hex %s: %v", test.packed, err)
 | 
			
		||||
			}
 | 
			
		||||
			inDef := fmt.Sprintf(`[{ "name" : "method", "type": "function", "inputs": %s}]`, test.def)
 | 
			
		||||
			inAbi, err := JSON(strings.NewReader(inDef))
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("invalid ABI definition %s, %v", inDef, err)
 | 
			
		||||
			}
 | 
			
		||||
			var packed []byte
 | 
			
		||||
			if reflect.TypeOf(test.unpacked).Kind() != reflect.Struct {
 | 
			
		||||
				packed, err = inAbi.Pack("method", test.unpacked)
 | 
			
		||||
			} else {
 | 
			
		||||
				// if want is a struct we need to use the components.
 | 
			
		||||
				elem := reflect.ValueOf(test.unpacked)
 | 
			
		||||
				var values []interface{}
 | 
			
		||||
				for i := 0; i < elem.NumField(); i++ {
 | 
			
		||||
					field := elem.Field(i)
 | 
			
		||||
					values = append(values, field.Interface())
 | 
			
		||||
				}
 | 
			
		||||
				B []*big.Int
 | 
			
		||||
			}{
 | 
			
		||||
				A: struct {
 | 
			
		||||
					FieldA *big.Int `abi:"a"` // Test whether abi tag works for nested tuple
 | 
			
		||||
					B      []*big.Int
 | 
			
		||||
				}{big.NewInt(1), []*big.Int{big.NewInt(1), big.NewInt(0)}},
 | 
			
		||||
				B: []*big.Int{big.NewInt(1), big.NewInt(0)}},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000040" + // a offset
 | 
			
		||||
				"00000000000000000000000000000000000000000000000000000000000000e0" + // b offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // a.a value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // a.b offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // a.b length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // a.b[0] value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000000" + // a.b[1] value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // b length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // b[0] value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000000"), // b[1] value
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// tuple slice
 | 
			
		||||
			"tuple[]",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "int256"},
 | 
			
		||||
				{Name: "b", Type: "int256[]"},
 | 
			
		||||
			},
 | 
			
		||||
			[]struct {
 | 
			
		||||
				A *big.Int
 | 
			
		||||
				B []*big.Int
 | 
			
		||||
			}{
 | 
			
		||||
				{big.NewInt(-1), []*big.Int{big.NewInt(1), big.NewInt(0)}},
 | 
			
		||||
				{big.NewInt(1), []*big.Int{big.NewInt(2), big.NewInt(-1)}},
 | 
			
		||||
			},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000002" + // tuple length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0] offset
 | 
			
		||||
				"00000000000000000000000000000000000000000000000000000000000000e0" + // tuple[1] offset
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].A
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0].B offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[0].B length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].B[0] value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000000" + // tuple[0].B[1] value
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].A
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[1].B offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].B length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].B[0] value
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"), // tuple[1].B[1] value
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// static tuple array
 | 
			
		||||
			"tuple[2]",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "int256"},
 | 
			
		||||
				{Name: "b", Type: "int256"},
 | 
			
		||||
			},
 | 
			
		||||
			[2]struct {
 | 
			
		||||
				A *big.Int
 | 
			
		||||
				B *big.Int
 | 
			
		||||
			}{
 | 
			
		||||
				{big.NewInt(-1), big.NewInt(1)},
 | 
			
		||||
				{big.NewInt(1), big.NewInt(-1)},
 | 
			
		||||
			},
 | 
			
		||||
			common.Hex2Bytes("ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].a
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].b
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].a
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"), // tuple[1].b
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			// dynamic tuple array
 | 
			
		||||
			"tuple[2]",
 | 
			
		||||
			[]ArgumentMarshaling{
 | 
			
		||||
				{Name: "a", Type: "int256[]"},
 | 
			
		||||
			},
 | 
			
		||||
			[2]struct {
 | 
			
		||||
				A []*big.Int
 | 
			
		||||
			}{
 | 
			
		||||
				{[]*big.Int{big.NewInt(-1), big.NewInt(1)}},
 | 
			
		||||
				{[]*big.Int{big.NewInt(1), big.NewInt(-1)}},
 | 
			
		||||
			},
 | 
			
		||||
			common.Hex2Bytes("0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0] offset
 | 
			
		||||
				"00000000000000000000000000000000000000000000000000000000000000c0" + // tuple[1] offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000020" + // tuple[0].A offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[0].A length
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].A[0]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].A[1]
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000020" + // tuple[1].A offset
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].A length
 | 
			
		||||
				"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].A[0]
 | 
			
		||||
				"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"), // tuple[1].A[1]
 | 
			
		||||
		},
 | 
			
		||||
	} {
 | 
			
		||||
		typ, err := NewType(test.typ, "", test.components)
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			t.Fatalf("%v failed. Unexpected parse error: %v", i, err)
 | 
			
		||||
		}
 | 
			
		||||
		output, err := typ.pack(reflect.ValueOf(test.input))
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			t.Fatalf("%v failed. Unexpected pack error: %v", i, err)
 | 
			
		||||
		}
 | 
			
		||||
				packed, err = inAbi.Pack("method", values...)
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
		if !bytes.Equal(output, test.output) {
 | 
			
		||||
			t.Errorf("input %d for typ: %v failed. Expected bytes: '%x' Got: '%x'", i, typ.String(), test.output, output)
 | 
			
		||||
		}
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("test %d (%v) failed: %v", i, test.def, err)
 | 
			
		||||
			}
 | 
			
		||||
			if !reflect.DeepEqual(packed[4:], encb) {
 | 
			
		||||
				t.Errorf("test %d (%v) failed: expected %v, got %v", i, test.def, encb, packed[4:])
 | 
			
		||||
			}
 | 
			
		||||
		})
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestMethodPack(t *testing.T) {
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata2))
 | 
			
		||||
	abi, err := JSON(strings.NewReader(jsondata))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Fatal(err)
 | 
			
		||||
	}
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										988
									
								
								accounts/abi/packing_test.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										988
									
								
								accounts/abi/packing_test.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,988 @@
 | 
			
		||||
// Copyright 2020 The go-ethereum Authors
 | 
			
		||||
// This file is part of the go-ethereum library.
 | 
			
		||||
//
 | 
			
		||||
// The go-ethereum library is free software: you can redistribute it and/or modify
 | 
			
		||||
// it under the terms of the GNU Lesser General Public License as published by
 | 
			
		||||
// the Free Software Foundation, either version 3 of the License, or
 | 
			
		||||
// (at your option) any later version.
 | 
			
		||||
//
 | 
			
		||||
// The go-ethereum library is distributed in the hope that it will be useful,
 | 
			
		||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
 | 
			
		||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 | 
			
		||||
// GNU Lesser General Public License for more details.
 | 
			
		||||
//
 | 
			
		||||
// You should have received a copy of the GNU Lesser General Public License
 | 
			
		||||
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
 | 
			
		||||
 | 
			
		||||
package abi
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"math/big"
 | 
			
		||||
 | 
			
		||||
	"github.com/ethereum/go-ethereum/common"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
type packUnpackTest struct {
 | 
			
		||||
	def      string
 | 
			
		||||
	unpacked interface{}
 | 
			
		||||
	packed   string
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
var packUnpackTests = []packUnpackTest{
 | 
			
		||||
	// Booleans
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "bool" }]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: true,
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "bool" }]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: false,
 | 
			
		||||
	},
 | 
			
		||||
	// Integers
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "uint8" }]`,
 | 
			
		||||
		unpacked: uint8(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "uint8[]" }]`,
 | 
			
		||||
		unpacked: []uint8{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "uint16" }]`,
 | 
			
		||||
		unpacked: uint16(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{ "type": "uint16[]" }]`,
 | 
			
		||||
		unpacked: []uint16{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint17"}]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: big.NewInt(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint32"}]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: uint32(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint32[]"}]`,
 | 
			
		||||
		unpacked: []uint32{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint64"}]`,
 | 
			
		||||
		unpacked: uint64(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint64[]"}]`,
 | 
			
		||||
		unpacked: []uint64{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint256"}]`,
 | 
			
		||||
		unpacked: big.NewInt(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint256[]"}]`,
 | 
			
		||||
		unpacked: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int8"}]`,
 | 
			
		||||
		unpacked: int8(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int8[]"}]`,
 | 
			
		||||
		unpacked: []int8{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int16"}]`,
 | 
			
		||||
		unpacked: int16(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int16[]"}]`,
 | 
			
		||||
		unpacked: []int16{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int17"}]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: big.NewInt(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int32"}]`,
 | 
			
		||||
		unpacked: int32(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int32"}]`,
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: int32(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int32[]"}]`,
 | 
			
		||||
		unpacked: []int32{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int64"}]`,
 | 
			
		||||
		unpacked: int64(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int64[]"}]`,
 | 
			
		||||
		unpacked: []int64{1, 2},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int256"}]`,
 | 
			
		||||
		unpacked: big.NewInt(2),
 | 
			
		||||
		packed:   "0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int256"}]`,
 | 
			
		||||
		packed:   "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
 | 
			
		||||
		unpacked: big.NewInt(-1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "int256[]"}]`,
 | 
			
		||||
		unpacked: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
	},
 | 
			
		||||
	// Address
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "address"}]`,
 | 
			
		||||
		packed:   "0000000000000000000000000100000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: common.Address{1},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "address[]"}]`,
 | 
			
		||||
		unpacked: []common.Address{{1}, {2}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000100000000000000000000000000000000000000" +
 | 
			
		||||
			"0000000000000000000000000200000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	// Bytes
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes1"}]`,
 | 
			
		||||
		unpacked: [1]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes2"}]`,
 | 
			
		||||
		unpacked: [2]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes3"}]`,
 | 
			
		||||
		unpacked: [3]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes4"}]`,
 | 
			
		||||
		unpacked: [4]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes5"}]`,
 | 
			
		||||
		unpacked: [5]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes6"}]`,
 | 
			
		||||
		unpacked: [6]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes7"}]`,
 | 
			
		||||
		unpacked: [7]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes8"}]`,
 | 
			
		||||
		unpacked: [8]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes9"}]`,
 | 
			
		||||
		unpacked: [9]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes10"}]`,
 | 
			
		||||
		unpacked: [10]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes11"}]`,
 | 
			
		||||
		unpacked: [11]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes12"}]`,
 | 
			
		||||
		unpacked: [12]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes13"}]`,
 | 
			
		||||
		unpacked: [13]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes14"}]`,
 | 
			
		||||
		unpacked: [14]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes15"}]`,
 | 
			
		||||
		unpacked: [15]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes16"}]`,
 | 
			
		||||
		unpacked: [16]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes17"}]`,
 | 
			
		||||
		unpacked: [17]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes18"}]`,
 | 
			
		||||
		unpacked: [18]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes19"}]`,
 | 
			
		||||
		unpacked: [19]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes20"}]`,
 | 
			
		||||
		unpacked: [20]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes21"}]`,
 | 
			
		||||
		unpacked: [21]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes22"}]`,
 | 
			
		||||
		unpacked: [22]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes23"}]`,
 | 
			
		||||
		unpacked: [23]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes24"}]`,
 | 
			
		||||
		unpacked: [24]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes25"}]`,
 | 
			
		||||
		unpacked: [25]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes26"}]`,
 | 
			
		||||
		unpacked: [26]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes27"}]`,
 | 
			
		||||
		unpacked: [27]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes28"}]`,
 | 
			
		||||
		unpacked: [28]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes29"}]`,
 | 
			
		||||
		unpacked: [29]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes30"}]`,
 | 
			
		||||
		unpacked: [30]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes31"}]`,
 | 
			
		||||
		unpacked: [31]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32"}]`,
 | 
			
		||||
		unpacked: [32]byte{1},
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32"}]`,
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [32]byte{1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "bytes"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32"}]`,
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [32]byte{1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 | 
			
		||||
	},
 | 
			
		||||
	// Functions
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "function"}]`,
 | 
			
		||||
		packed:   "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [24]byte{1},
 | 
			
		||||
	},
 | 
			
		||||
	// Slice and Array
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []uint8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: []uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint256[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: []*big.Int{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]uint8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int8[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]int8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int16[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []int16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int16[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]int16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int32[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []int32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int32[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]int32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int64[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []int64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int64[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]int64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int256[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "int256[3]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		unpacked: [3]*big.Int{big.NewInt(1), big.NewInt(2), big.NewInt(3)},
 | 
			
		||||
	},
 | 
			
		||||
	// multi dimensional, if these pass, all types that don't require length prefix should pass
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [][]uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000a0" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [][]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000a0" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		unpacked: [][]uint8{{1, 2}, {1, 2, 3}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[2][2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2][2]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[][2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000060" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [2][]uint8{{}, {}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[][2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: [2][]uint8{{1}, {1}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [][2]uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [][2]uint8{{1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [][2]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint16[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []uint16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint16[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]uint16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint32[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []uint32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "uint32[2][3][4]"}]`,
 | 
			
		||||
		unpacked: [4][3][2]uint32{{{1, 2}, {3, 4}, {5, 6}}, {{7, 8}, {9, 10}, {11, 12}}, {{13, 14}, {15, 16}, {17, 18}}, {{19, 20}, {21, 22}, {23, 24}}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000004" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000005" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000006" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000007" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000008" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000009" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000a" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000b" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000c" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000d" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000e" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000f" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000010" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000011" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000012" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000013" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000014" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000015" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000016" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000017" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000018",
 | 
			
		||||
	},
 | 
			
		||||
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32[]"}]`,
 | 
			
		||||
		unpacked: []common.Hash{{1}, {2}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"0200000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint32[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]uint32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint64[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []uint64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint64[2]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: [2]uint64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint256[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint256[3]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		unpacked: [3]*big.Int{big.NewInt(1), big.NewInt(2), big.NewInt(3)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "string[4]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000c0" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000100" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000140" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000005" +
 | 
			
		||||
			"48656c6c6f000000000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000005" +
 | 
			
		||||
			"576f726c64000000000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000b" +
 | 
			
		||||
			"476f2d657468657265756d000000000000000000000000000000000000000000" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000008" +
 | 
			
		||||
			"457468657265756d000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [4]string{"Hello", "World", "Go-ethereum", "Ethereum"},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "string[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000008" +
 | 
			
		||||
			"457468657265756d000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"000000000000000000000000000000000000000000000000000000000000000b" +
 | 
			
		||||
			"676f2d657468657265756d000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: []string{"Ethereum", "go-ethereum"},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "bytes[]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" +
 | 
			
		||||
			"f0f0f00000000000000000000000000000000000000000000000000000000000" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" +
 | 
			
		||||
			"f0f0f00000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		unpacked: [][]byte{{0xf0, 0xf0, 0xf0}, {0xf0, 0xf0, 0xf0}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"type": "uint256[2][][]"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000e0" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000c8" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000003e8" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000c8" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000003e8",
 | 
			
		||||
		unpacked: [][][2]*big.Int{{{big.NewInt(1), big.NewInt(200)}, {big.NewInt(1), big.NewInt(1000)}}, {{big.NewInt(1), big.NewInt(200)}, {big.NewInt(1), big.NewInt(1000)}}},
 | 
			
		||||
	},
 | 
			
		||||
	// struct outputs
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int1","type":"int256"},{"name":"int2","type":"int256"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			Int1 *big.Int
 | 
			
		||||
			Int2 *big.Int
 | 
			
		||||
		}{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:    `[{"name":"int_one","type":"int256"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:    `[{"name":"int__one","type":"int256"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:    `[{"name":"int_one_","type":"int256"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one","type":"int256"}, {"name":"intone","type":"int256"}]`,
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
			Intone *big.Int
 | 
			
		||||
		}{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "string"}]`,
 | 
			
		||||
		unpacked: "foobar",
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000006" +
 | 
			
		||||
			"666f6f6261720000000000000000000000000000000000000000000000000000",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "string[]"}]`,
 | 
			
		||||
		unpacked: []string{"hello", "foobar"},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // len(array) = 2
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" + // offset 128 to i = 1
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000005" + // len(str[0]) = 5
 | 
			
		||||
			"68656c6c6f000000000000000000000000000000000000000000000000000000" + // str[0]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000006" + // len(str[1]) = 6
 | 
			
		||||
			"666f6f6261720000000000000000000000000000000000000000000000000000", // str[1]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "string[2]"}]`,
 | 
			
		||||
		unpacked: [2]string{"hello", "foobar"},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // offset to i = 0
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" + // offset to i = 1
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000005" + // len(str[0]) = 5
 | 
			
		||||
			"68656c6c6f000000000000000000000000000000000000000000000000000000" + // str[0]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000006" + // len(str[1]) = 6
 | 
			
		||||
			"666f6f6261720000000000000000000000000000000000000000000000000000", // str[1]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32[][]"}]`,
 | 
			
		||||
		unpacked: [][][32]byte{{{1}, {2}}, {{3}, {4}, {5}}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // len(array) = 2
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000a0" + // offset 160 to i = 1
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // len(array[0]) = 2
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
			"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" + // len(array[1]) = 3
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
			"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
			"0500000000000000000000000000000000000000000000000000000000000000", // array[1][2]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32[][2]"}]`,
 | 
			
		||||
		unpacked: [2][][32]byte{{{1}, {2}}, {{3}, {4}, {5}}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // offset 64 to i = 0
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000a0" + // offset 160 to i = 1
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // len(array[0]) = 2
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
			"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" + // len(array[1]) = 3
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
			"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
			"0500000000000000000000000000000000000000000000000000000000000000", // array[1][2]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:      `[{"type": "bytes32[3][2]"}]`,
 | 
			
		||||
		unpacked: [2][3][32]byte{{{1}, {2}, {3}}, {{3}, {4}, {5}}},
 | 
			
		||||
		packed: "0100000000000000000000000000000000000000000000000000000000000000" + // array[0][0]
 | 
			
		||||
			"0200000000000000000000000000000000000000000000000000000000000000" + // array[0][1]
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // array[0][2]
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // array[1][0]
 | 
			
		||||
			"0400000000000000000000000000000000000000000000000000000000000000" + // array[1][1]
 | 
			
		||||
			"0500000000000000000000000000000000000000000000000000000000000000", // array[1][2]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		// static tuple
 | 
			
		||||
		def: `[{"name":"a","type":"int64"}, 
 | 
			
		||||
		{"name":"b","type":"int256"}, 
 | 
			
		||||
		{"name":"c","type":"int256"}, 
 | 
			
		||||
		{"name":"d","type":"bool"},
 | 
			
		||||
		{"name":"e","type":"bytes32[3][2]"}]`,
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			A int64
 | 
			
		||||
			B *big.Int
 | 
			
		||||
			C *big.Int
 | 
			
		||||
			D bool
 | 
			
		||||
			E [2][3][32]byte
 | 
			
		||||
		}{1, big.NewInt(1), big.NewInt(-1), true, [2][3][32]byte{{{1}, {2}, {3}}, {{3}, {4}, {5}}}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000001" + // struct[a]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // struct[b]
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // struct[c]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // struct[d]
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][0]
 | 
			
		||||
			"0200000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][1]
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[0][2]
 | 
			
		||||
			"0300000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[1][0]
 | 
			
		||||
			"0400000000000000000000000000000000000000000000000000000000000000" + // struct[e] array[1][1]
 | 
			
		||||
			"0500000000000000000000000000000000000000000000000000000000000000", // struct[e] array[1][2]
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"a","type":"string"}, 
 | 
			
		||||
		{"name":"b","type":"int64"}, 
 | 
			
		||||
		{"name":"c","type":"bytes"}, 
 | 
			
		||||
		{"name":"d","type":"string[]"},
 | 
			
		||||
		{"name":"e","type":"int256[]"},
 | 
			
		||||
		{"name":"f","type":"address[]"}]`,
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			FieldA string `abi:"a"` // Test whether abi tag works
 | 
			
		||||
			FieldB int64  `abi:"b"`
 | 
			
		||||
			C      []byte
 | 
			
		||||
			D      []string
 | 
			
		||||
			E      []*big.Int
 | 
			
		||||
			F      []common.Address
 | 
			
		||||
		}{"foobar", 1, []byte{1}, []string{"foo", "bar"}, []*big.Int{big.NewInt(1), big.NewInt(-1)}, []common.Address{{1}, {2}}},
 | 
			
		||||
		packed: "00000000000000000000000000000000000000000000000000000000000000c0" + // struct[a] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // struct[b]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000100" + // struct[c] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000140" + // struct[d] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000220" + // struct[e] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000280" + // struct[f] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000006" + // struct[a] length
 | 
			
		||||
			"666f6f6261720000000000000000000000000000000000000000000000000000" + // struct[a] "foobar"
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // struct[c] length
 | 
			
		||||
			"0100000000000000000000000000000000000000000000000000000000000000" + // []byte{1}
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // struct[d] length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // foo offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000080" + // bar offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" + // foo length
 | 
			
		||||
			"666f6f0000000000000000000000000000000000000000000000000000000000" + // foo
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" + // bar offset
 | 
			
		||||
			"6261720000000000000000000000000000000000000000000000000000000000" + // bar
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // struct[e] length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // 1
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // -1
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // struct[f] length
 | 
			
		||||
			"0000000000000000000000000100000000000000000000000000000000000000" + // common.Address{1}
 | 
			
		||||
			"0000000000000000000000000200000000000000000000000000000000000000", // common.Address{2}
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"components": [{"name": "a","type": "uint256"},	
 | 
			
		||||
							{"name": "b","type": "uint256[]"}],	
 | 
			
		||||
							"name": "a","type": "tuple"},
 | 
			
		||||
							{"name": "b","type": "uint256[]"}]`,
 | 
			
		||||
		unpacked: struct {
 | 
			
		||||
			A struct {
 | 
			
		||||
				FieldA *big.Int `abi:"a"`
 | 
			
		||||
				B      []*big.Int
 | 
			
		||||
			}
 | 
			
		||||
			B []*big.Int
 | 
			
		||||
		}{
 | 
			
		||||
			A: struct {
 | 
			
		||||
				FieldA *big.Int `abi:"a"` // Test whether abi tag works for nested tuple
 | 
			
		||||
				B      []*big.Int
 | 
			
		||||
			}{big.NewInt(1), []*big.Int{big.NewInt(1), big.NewInt(2)}},
 | 
			
		||||
			B: []*big.Int{big.NewInt(1), big.NewInt(2)}},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000040" + // a offset
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000e0" + // b offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // a.a value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // a.b offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // a.b length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // a.b[0] value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // a.b[1] value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // b length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // b[0] value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002", // b[1] value
 | 
			
		||||
	},
 | 
			
		||||
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"components": [{"name": "a","type": "int256"},	
 | 
			
		||||
							{"name": "b","type": "int256[]"}],	
 | 
			
		||||
							"name": "a","type": "tuple[]"}]`,
 | 
			
		||||
		unpacked: []struct {
 | 
			
		||||
			A *big.Int
 | 
			
		||||
			B []*big.Int
 | 
			
		||||
		}{
 | 
			
		||||
			{big.NewInt(-1), []*big.Int{big.NewInt(1), big.NewInt(3)}},
 | 
			
		||||
			{big.NewInt(1), []*big.Int{big.NewInt(2), big.NewInt(-1)}},
 | 
			
		||||
		},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0] offset
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000e0" + // tuple[1] offset
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].A
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0].B offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[0].B length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].B[0] value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000003" + // tuple[0].B[1] value
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].A
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[1].B offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].B length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].B[0] value
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff", // tuple[1].B[1] value
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"components": [{"name": "a","type": "int256"},	
 | 
			
		||||
							{"name": "b","type": "int256"}],	
 | 
			
		||||
							"name": "a","type": "tuple[2]"}]`,
 | 
			
		||||
		unpacked: [2]struct {
 | 
			
		||||
			A *big.Int
 | 
			
		||||
			B *big.Int
 | 
			
		||||
		}{
 | 
			
		||||
			{big.NewInt(-1), big.NewInt(1)},
 | 
			
		||||
			{big.NewInt(1), big.NewInt(-1)},
 | 
			
		||||
		},
 | 
			
		||||
		packed: "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].a
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].b
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].a
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff", // tuple[1].b
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"components": [{"name": "a","type": "int256[]"}],
 | 
			
		||||
							"name": "a","type": "tuple[2]"}]`,
 | 
			
		||||
		unpacked: [2]struct {
 | 
			
		||||
			A []*big.Int
 | 
			
		||||
		}{
 | 
			
		||||
			{[]*big.Int{big.NewInt(-1), big.NewInt(1)}},
 | 
			
		||||
			{[]*big.Int{big.NewInt(1), big.NewInt(-1)}},
 | 
			
		||||
		},
 | 
			
		||||
		packed: "0000000000000000000000000000000000000000000000000000000000000020" +
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000040" + // tuple[0] offset
 | 
			
		||||
			"00000000000000000000000000000000000000000000000000000000000000c0" + // tuple[1] offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000020" + // tuple[0].A offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[0].A length
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff" + // tuple[0].A[0]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[0].A[1]
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000020" + // tuple[1].A offset
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000002" + // tuple[1].A length
 | 
			
		||||
			"0000000000000000000000000000000000000000000000000000000000000001" + // tuple[1].A[0]
 | 
			
		||||
			"ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff", // tuple[1].A[1]
 | 
			
		||||
	},
 | 
			
		||||
}
 | 
			
		||||
@@ -42,26 +42,26 @@ func indirectInterfaceOrPtr(v reflect.Value) reflect.Value {
 | 
			
		||||
// reflectIntKind returns the reflect using the given size and
 | 
			
		||||
// unsignedness.
 | 
			
		||||
func reflectIntKindAndType(unsigned bool, size int) (reflect.Kind, reflect.Type) {
 | 
			
		||||
	switch size {
 | 
			
		||||
	case 8:
 | 
			
		||||
		if unsigned {
 | 
			
		||||
	if unsigned {
 | 
			
		||||
		switch size {
 | 
			
		||||
		case 8:
 | 
			
		||||
			return reflect.Uint8, uint8T
 | 
			
		||||
		}
 | 
			
		||||
		return reflect.Int8, int8T
 | 
			
		||||
	case 16:
 | 
			
		||||
		if unsigned {
 | 
			
		||||
		case 16:
 | 
			
		||||
			return reflect.Uint16, uint16T
 | 
			
		||||
		}
 | 
			
		||||
		return reflect.Int16, int16T
 | 
			
		||||
	case 32:
 | 
			
		||||
		if unsigned {
 | 
			
		||||
		case 32:
 | 
			
		||||
			return reflect.Uint32, uint32T
 | 
			
		||||
		}
 | 
			
		||||
		return reflect.Int32, int32T
 | 
			
		||||
	case 64:
 | 
			
		||||
		if unsigned {
 | 
			
		||||
		case 64:
 | 
			
		||||
			return reflect.Uint64, uint64T
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	switch size {
 | 
			
		||||
	case 8:
 | 
			
		||||
		return reflect.Int8, int8T
 | 
			
		||||
	case 16:
 | 
			
		||||
		return reflect.Int16, int16T
 | 
			
		||||
	case 32:
 | 
			
		||||
		return reflect.Int32, int32T
 | 
			
		||||
	case 64:
 | 
			
		||||
		return reflect.Int64, int64T
 | 
			
		||||
	}
 | 
			
		||||
	return reflect.Ptr, bigT
 | 
			
		||||
@@ -88,8 +88,8 @@ func set(dst, src reflect.Value) error {
 | 
			
		||||
		return set(dst.Elem(), src)
 | 
			
		||||
	case srcType.AssignableTo(dstType) && dst.CanSet():
 | 
			
		||||
		dst.Set(src)
 | 
			
		||||
	case dstType.Kind() == reflect.Slice && srcType.Kind() == reflect.Slice:
 | 
			
		||||
		return setSlice(dst, src)
 | 
			
		||||
	case dstType.Kind() == reflect.Slice && srcType.Kind() == reflect.Slice && dst.CanSet():
 | 
			
		||||
		setSlice(dst, src)
 | 
			
		||||
	default:
 | 
			
		||||
		return fmt.Errorf("abi: cannot unmarshal %v in to %v", src.Type(), dst.Type())
 | 
			
		||||
	}
 | 
			
		||||
@@ -98,15 +98,13 @@ func set(dst, src reflect.Value) error {
 | 
			
		||||
 | 
			
		||||
// setSlice attempts to assign src to dst when slices are not assignable by default
 | 
			
		||||
// e.g. src: [][]byte -> dst: [][15]byte
 | 
			
		||||
func setSlice(dst, src reflect.Value) error {
 | 
			
		||||
// setSlice ignores if we cannot copy all of src' elements.
 | 
			
		||||
func setSlice(dst, src reflect.Value) {
 | 
			
		||||
	slice := reflect.MakeSlice(dst.Type(), src.Len(), src.Len())
 | 
			
		||||
	for i := 0; i < src.Len(); i++ {
 | 
			
		||||
		v := src.Index(i)
 | 
			
		||||
		reflect.Copy(slice.Index(i), v)
 | 
			
		||||
		reflect.Copy(slice.Index(i), src.Index(i))
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	dst.Set(slice)
 | 
			
		||||
	return nil
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// requireAssignable assures that `dest` is a pointer and it's not an interface.
 | 
			
		||||
 
 | 
			
		||||
@@ -306,3 +306,28 @@ func TestTypeCheck(t *testing.T) {
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestInternalType(t *testing.T) {
 | 
			
		||||
	components := []ArgumentMarshaling{{Name: "a", Type: "int64"}}
 | 
			
		||||
	internalType := "struct a.b[]"
 | 
			
		||||
	kind := Type{
 | 
			
		||||
		Kind: reflect.Struct,
 | 
			
		||||
		T:    TupleTy,
 | 
			
		||||
		Type: reflect.TypeOf(struct {
 | 
			
		||||
			A int64 `json:"a"`
 | 
			
		||||
		}{}),
 | 
			
		||||
		stringKind:    "(int64)",
 | 
			
		||||
		TupleRawName:  "ab[]",
 | 
			
		||||
		TupleElems:    []*Type{{Kind: reflect.Int64, T: IntTy, Type: reflect.TypeOf(int64(0)), Size: 64, stringKind: "int64"}},
 | 
			
		||||
		TupleRawNames: []string{"a"},
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	blob := "tuple"
 | 
			
		||||
	typ, err := NewType(blob, internalType, components)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Errorf("type %q: failed to parse type string: %v", blob, err)
 | 
			
		||||
	}
 | 
			
		||||
	if !reflect.DeepEqual(typ, kind) {
 | 
			
		||||
		t.Errorf("type %q: parsed type mismatch:\nGOT %s\nWANT %s ", blob, spew.Sdump(typeWithoutStringer(typ)), spew.Sdump(typeWithoutStringer(kind)))
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -30,6 +30,34 @@ import (
 | 
			
		||||
	"github.com/stretchr/testify/require"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
// TestUnpack tests the general pack/unpack tests in packing_test.go
 | 
			
		||||
func TestUnpack(t *testing.T) {
 | 
			
		||||
	for i, test := range packUnpackTests {
 | 
			
		||||
		t.Run(strconv.Itoa(i), func(t *testing.T) {
 | 
			
		||||
			//Unpack
 | 
			
		||||
			def := fmt.Sprintf(`[{ "name" : "method", "type": "function", "outputs": %s}]`, test.def)
 | 
			
		||||
			abi, err := JSON(strings.NewReader(def))
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("invalid ABI definition %s: %v", def, err)
 | 
			
		||||
			}
 | 
			
		||||
			encb, err := hex.DecodeString(test.packed)
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Fatalf("invalid hex %s: %v", test.packed, err)
 | 
			
		||||
			}
 | 
			
		||||
			outptr := reflect.New(reflect.TypeOf(test.unpacked))
 | 
			
		||||
			err = abi.Unpack(outptr.Interface(), "method", encb)
 | 
			
		||||
			if err != nil {
 | 
			
		||||
				t.Errorf("test %d (%v) failed: %v", i, test.def, err)
 | 
			
		||||
				return
 | 
			
		||||
			}
 | 
			
		||||
			out := outptr.Elem().Interface()
 | 
			
		||||
			if !reflect.DeepEqual(test.unpacked, out) {
 | 
			
		||||
				t.Errorf("test %d (%v) failed: expected %v, got %v", i, test.def, test.unpacked, out)
 | 
			
		||||
			}
 | 
			
		||||
		})
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
type unpackTest struct {
 | 
			
		||||
	def  string      // ABI definition JSON
 | 
			
		||||
	enc  string      // evm return data
 | 
			
		||||
@@ -52,16 +80,6 @@ func (test unpackTest) checkError(err error) error {
 | 
			
		||||
 | 
			
		||||
var unpackTests = []unpackTest{
 | 
			
		||||
	// Bools
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{ "type": "bool" }]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: true,
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{ "type": "bool" }]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: false,
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{ "type": "bool" }]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000001000000000001",
 | 
			
		||||
@@ -75,11 +93,6 @@ var unpackTests = []unpackTest{
 | 
			
		||||
		err:  "abi: improperly encoded boolean value",
 | 
			
		||||
	},
 | 
			
		||||
	// Integers
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint32"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: uint32(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint32"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
@@ -92,16 +105,6 @@ var unpackTests = []unpackTest{
 | 
			
		||||
		want: uint16(0),
 | 
			
		||||
		err:  "abi: cannot unmarshal *big.Int in to uint16",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint17"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: big.NewInt(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int32"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: int32(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int32"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
@@ -114,33 +117,6 @@ var unpackTests = []unpackTest{
 | 
			
		||||
		want: int16(0),
 | 
			
		||||
		err:  "abi: cannot unmarshal *big.Int in to int16",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int17"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: big.NewInt(1),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int256"}]`,
 | 
			
		||||
		enc:  "ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
 | 
			
		||||
		want: big.NewInt(-1),
 | 
			
		||||
	},
 | 
			
		||||
	// Address
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "address"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000100000000000000000000000000000000000000",
 | 
			
		||||
		want: common.Address{1},
 | 
			
		||||
	},
 | 
			
		||||
	// Bytes
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "bytes32"}]`,
 | 
			
		||||
		enc:  "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [32]byte{1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "bytes"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000200100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: common.Hex2Bytes("0100000000000000000000000000000000000000000000000000000000000000"),
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "bytes"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000200100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
@@ -153,237 +129,6 @@ var unpackTests = []unpackTest{
 | 
			
		||||
		want: []byte(nil),
 | 
			
		||||
		err:  "abi: cannot unmarshal [32]uint8 in to []uint8",
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "bytes32"}]`,
 | 
			
		||||
		enc:  "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [32]byte{1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 | 
			
		||||
	},
 | 
			
		||||
	// Functions
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "function"}]`,
 | 
			
		||||
		enc:  "0100000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [24]byte{1},
 | 
			
		||||
	},
 | 
			
		||||
	// Slice and Array
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []uint8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: []uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint256[]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: []*big.Int{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]uint8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	// multi dimensional, if these pass, all types that don't require length prefix should pass
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [][]uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000a0000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [][]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[][]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000a00000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		want: [][]uint8{{1, 2}, {1, 2, 3}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[2][2]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2][2]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[][2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [2][]uint8{{}, {}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[][2]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001",
 | 
			
		||||
		want: [2][]uint8{{1}, {1}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [][2]uint8{},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [][2]uint8{{1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint8[2][]"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [][2]uint8{{1, 2}, {1, 2}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint16[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []uint16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint16[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]uint16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint32[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []uint32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint32[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]uint32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint32[2][3][4]"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003000000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000050000000000000000000000000000000000000000000000000000000000000006000000000000000000000000000000000000000000000000000000000000000700000000000000000000000000000000000000000000000000000000000000080000000000000000000000000000000000000000000000000000000000000009000000000000000000000000000000000000000000000000000000000000000a000000000000000000000000000000000000000000000000000000000000000b000000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000000d000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000f000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000110000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000001300000000000000000000000000000000000000000000000000000000000000140000000000000000000000000000000000000000000000000000000000000015000000000000000000000000000000000000000000000000000000000000001600000000000000000000000000000000000000000000000000000000000000170000000000000000000000000000000000000000000000000000000000000018",
 | 
			
		||||
		want: [4][3][2]uint32{{{1, 2}, {3, 4}, {5, 6}}, {{7, 8}, {9, 10}, {11, 12}}, {{13, 14}, {15, 16}, {17, 18}}, {{19, 20}, {21, 22}, {23, 24}}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint64[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []uint64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint64[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]uint64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint256[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint256[3]"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		want: [3]*big.Int{big.NewInt(1), big.NewInt(2), big.NewInt(3)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "string[4]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000000c000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000000140000000000000000000000000000000000000000000000000000000000000000548656c6c6f0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000005576f726c64000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000b476f2d657468657265756d0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000008457468657265756d000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [4]string{"Hello", "World", "Go-ethereum", "Ethereum"},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "string[]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000008457468657265756d000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000b676f2d657468657265756d000000000000000000000000000000000000000000",
 | 
			
		||||
		want: []string{"Ethereum", "go-ethereum"},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "bytes[]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000003f0f0f000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000003f0f0f00000000000000000000000000000000000000000000000000000000000",
 | 
			
		||||
		want: [][]byte{{0xf0, 0xf0, 0xf0}, {0xf0, 0xf0, 0xf0}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "uint256[2][][]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e00000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000c8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000003e80000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000c8000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000003e8",
 | 
			
		||||
		want: [][][2]*big.Int{{{big.NewInt(1), big.NewInt(200)}, {big.NewInt(1), big.NewInt(1000)}}, {{big.NewInt(1), big.NewInt(200)}, {big.NewInt(1), big.NewInt(1000)}}},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int8[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []int8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int8[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]int8{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int16[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []int16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int16[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]int16{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int32[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []int32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int32[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]int32{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int64[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []int64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int64[2]"}]`,
 | 
			
		||||
		enc:  "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: [2]int64{1, 2},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int256[]"}]`,
 | 
			
		||||
		enc:  "0000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: []*big.Int{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def:  `[{"type": "int256[3]"}]`,
 | 
			
		||||
		enc:  "000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000003",
 | 
			
		||||
		want: [3]*big.Int{big.NewInt(1), big.NewInt(2), big.NewInt(3)},
 | 
			
		||||
	},
 | 
			
		||||
	// struct outputs
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int1","type":"int256"},{"name":"int2","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			Int1 *big.Int
 | 
			
		||||
			Int2 *big.Int
 | 
			
		||||
		}{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int__one","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one_","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one","type":"int256"}, {"name":"intone","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
			Intone *big.Int
 | 
			
		||||
		}{big.NewInt(1), big.NewInt(2)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"___","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
@@ -438,11 +183,36 @@ var unpackTests = []unpackTest{
 | 
			
		||||
		}{},
 | 
			
		||||
		err: "abi: purely underscored output cannot unpack to struct",
 | 
			
		||||
	},
 | 
			
		||||
	// Make sure only the first argument is consumed
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int__one","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
	{
 | 
			
		||||
		def: `[{"name":"int_one_","type":"int256"}]`,
 | 
			
		||||
		enc: "00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002",
 | 
			
		||||
		want: struct {
 | 
			
		||||
			IntOne *big.Int
 | 
			
		||||
		}{big.NewInt(1)},
 | 
			
		||||
	},
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestUnpack(t *testing.T) {
 | 
			
		||||
// TestLocalUnpackTests runs test specially designed only for unpacking.
 | 
			
		||||
// All test cases that can be used to test packing and unpacking should move to packing_test.go
 | 
			
		||||
func TestLocalUnpackTests(t *testing.T) {
 | 
			
		||||
	for i, test := range unpackTests {
 | 
			
		||||
		t.Run(strconv.Itoa(i), func(t *testing.T) {
 | 
			
		||||
			//Unpack
 | 
			
		||||
			def := fmt.Sprintf(`[{ "name" : "method", "type": "function", "outputs": %s}]`, test.def)
 | 
			
		||||
			abi, err := JSON(strings.NewReader(def))
 | 
			
		||||
			if err != nil {
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user