diff --git a/accounts/abi/unpack.go b/accounts/abi/unpack.go index 0cc00914d2..51a0d43684 100644 --- a/accounts/abi/unpack.go +++ b/accounts/abi/unpack.go @@ -97,6 +97,11 @@ func toGoSlice(i int, t Argument, output []byte) (interface{}, error) { inter = common.BytesToHash(returnOutput) case FixedBytesTy: inter = returnOutput + case SliceTy, ArrayTy: + inter, err = toGoSlice(i+index/32, t, output) + if err != nil { + return nil, err + } default: return nil, fmt.Errorf("abi: unsupported slice type passed in") } @@ -158,6 +163,9 @@ func readBool(word []byte) (bool, error) { // toGoType parses the input and casts it to the proper type defined by the ABI // argument in T. func toGoType(i int, t Argument, output []byte) (interface{}, error) { + if len(output)%32 != 0 { + return nil, fmt.Errorf("abi: improperly formatted output") + } // we need to treat slices differently if (t.Type.IsSlice || t.Type.IsArray) && t.Type.T != BytesTy && t.Type.T != StringTy && t.Type.T != FixedBytesTy && t.Type.T != FunctionTy { return toGoSlice(i, t, output) diff --git a/accounts/abi/unpack_test.go b/accounts/abi/unpack_test.go index 6f25284e24..3c3cdddb75 100644 --- a/accounts/abi/unpack_test.go +++ b/accounts/abi/unpack_test.go @@ -244,6 +244,13 @@ func TestArraysAndSlicesUnpack(t *testing.T) { []uint8{}, "", }, + { + `[ { "type": "uint8[][]" } ]`, + common.Hex2Bytes("00000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000000E0000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"), + [][]uint8{{1, 2}, {1, 2}}, + [][]uint8{{}}, + "", + }, { `[ { "type": "uint8[2]" } ]`, common.Hex2Bytes("00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002"), @@ -378,6 +385,7 @@ func TestArraysAndSlicesUnpack(t *testing.T) { "", }, } { + //t.Log(test.marshalledOutput) abiDefinition := fmt.Sprintf(`[{ "name" : "method", "outputs": %s}]`, test.def) abi, err := JSON(strings.NewReader(abiDefinition))