Skip to content
This repository has been archived by the owner on Dec 15, 2023. It is now read-only.

#176 - Fix dynamic tuple encoding #183

Merged
merged 4 commits into from
Feb 26, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
212 changes: 212 additions & 0 deletions Example/Tests/ABI/EncodedABIFunctionTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,61 @@ final class EncodedABIFunctionTests: XCTestCase {
description: "Selector + address[2] is expected to be encoded correctly"
)
}

func testTwoAddressFixedArraysOfTwo() {
expect{
try EncodedABIFunction(
signature: SimpleString(
string: "baz(uint32,bool)"
),
parameters: [
ABITuple(
parameters: [
ABITuple(
parameters: [
ABIAddress(
address: EthAddress(
hex: "0x407d73d8a49eeb85d32cf465507dd71d507100c1"
)
),
ABIAddress(
address: EthAddress(
hex: "0x407d73d8a49eeb85d32cf465507dd71d507100c2"
)
)
]
),
ABITuple(
parameters: [
ABIAddress(
address: EthAddress(
hex: "0x407d73d8a49eeb85d32cf465507dd71d507100c3"
)
),
ABIAddress(
address: EthAddress(
hex: "0x407d73d8a49eeb85d32cf465507dd71d507100c4"
)
)
]
)
]
)
]
).value()
}.to(
equal(
Data(
hex: "cdcd77c0" +
"000000000000000000000000407d73d8a49eeb85d32cf465507dd71d507100c1" +
"000000000000000000000000407d73d8a49eeb85d32cf465507dd71d507100c2" +
"000000000000000000000000407d73d8a49eeb85d32cf465507dd71d507100c3" +
"000000000000000000000000407d73d8a49eeb85d32cf465507dd71d507100c4"
)
),
description: "Selector + address[2][2] is expected to be encoded correctly"
)
}

func testAddressDynamicArrayOfTwo() {
expect{
Expand Down Expand Up @@ -549,4 +604,161 @@ final class EncodedABIFunctionTests: XCTestCase {
)
}

func test0xContractCallEncoding() {
let kittiesContract = EthAddress(
hex: "0x06012c8cf97bead5deae237070f9587f8e7a266d"
)
let sender = EthAddress(
hex: "0x0aD9Fb61a07BAC25625382B63693644497f1B204"
)
let receiver = EthAddress(
hex: "0x4dB6d56Bbb49DD66abC7be5D671fDdF9a5255Cc5"
)
let zero = EthAddress(
hex: "0x0000000000000000000000000000000000000000"
)
let makerAssetData = RightZeroesPaddedBytes(
origin: EncodedABIFunction(
signature: SimpleString(
string: "ERC721Token(address,uint256)"
),
parameters: [
ABIAddress(
address: kittiesContract
),
ABIUnsignedNumber(
origin: EthNumber(value: 478404)
)
]
),
padding: 32
)
let takerAssetData = RightZeroesPaddedBytes(
origin: EncodedABIFunction(
signature: SimpleString(
string: "ERC721Token(address,uint256)"
),
parameters: [
ABIAddress(
address: kittiesContract
),
ABIUnsignedNumber(
origin: EthNumber(value: 392919)
)
]
),
padding: 32
)
let orderInfo = EncodedABIFunction(
signature: SimpleString(
string: "getOrderInfo((" +
"address," +
"address," +
"address," +
"address," +
"uint256," +
"uint256," +
"uint256," +
"uint256," +
"uint256," +
"uint256," +
"bytes," +
"bytes))"
),
parameters: [
ABITuple(
parameters: [
// makerAddress
ABIAddress(
address: sender
),
// takerAddress
ABIAddress(
address: receiver
),
// feeRecipientAddress
ABIAddress(
address: zero
),
// senderAddress
ABIAddress(
address: zero
),
// makerAssetAmount
ABIUnsignedNumber(
origin: EthNumber(value: 1)
),
// takerAssetAmount
ABIUnsignedNumber(
origin: EthNumber(value: 1)
),
// makerFee
ABIUnsignedNumber(
origin: EthNumber(value: 0)
),
// takerFee
ABIUnsignedNumber(
origin: EthNumber(value: 0)
),
// expiration timestamp
ABIUnsignedNumber(
origin: EthNumber(
hex: "5c5f8a23"
)
),
// salt
ABIFixedBytes(
origin: BytesFromHexString(
hex: "745a4c682985f13b4f6935e129e895a70737172437c4296d900c7b0a1b19354e"
)
),
// makerAssetData
ABIVariableBytes(
origin: RightZeroesPaddedBytes(
origin: makerAssetData,
padding: 32
)
),
// takerAssetData
ABIVariableBytes(
origin: RightZeroesPaddedBytes(
origin: takerAssetData,
padding: 32
)
)
]
)
]
)
expect{
try PrefixedHexString(bytes: orderInfo).value()
}.to(
equal(
"0xc75e0a81" +
"0000000000000000000000000000000000000000000000000000000000000020" +
"0000000000000000000000000ad9fb61a07bac25625382b63693644497f1b204" +
"0000000000000000000000004db6d56bbb49dd66abc7be5d671fddf9a5255cc5" +
"0000000000000000000000000000000000000000000000000000000000000000" +
"0000000000000000000000000000000000000000000000000000000000000000" +
"0000000000000000000000000000000000000000000000000000000000000001" +
"0000000000000000000000000000000000000000000000000000000000000001" +
"0000000000000000000000000000000000000000000000000000000000000000" +
"0000000000000000000000000000000000000000000000000000000000000000" +
"000000000000000000000000000000000000000000000000000000005c5f8a23" +
"745a4c682985f13b4f6935e129e895a70737172437c4296d900c7b0a1b19354e" +
"0000000000000000000000000000000000000000000000000000000000000180" +
"0000000000000000000000000000000000000000000000000000000000000200" +
"0000000000000000000000000000000000000000000000000000000000000060" +
"0257179200000000000000000000000006012c8cf97bead5deae237070f9587f" +
"8e7a266d00000000000000000000000000000000000000000000000000000000" +
"00074cc400000000000000000000000000000000000000000000000000000000" +
"0000000000000000000000000000000000000000000000000000000000000060" +
"0257179200000000000000000000000006012c8cf97bead5deae237070f9587f" +
"8e7a266d00000000000000000000000000000000000000000000000000000000" +
"0005fed700000000000000000000000000000000000000000000000000000000"
),
description: "0x contract call is expected to be encoded correctly"
)
}

}
4 changes: 2 additions & 2 deletions Example/Tests/ABI/Parameters/ABITupleTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -32,13 +32,13 @@ final class ABITupleTests: XCTestCase {
origin: true
)
]
).heads(offset: 1)
).tails(offset: 1)
).value()
}.to(
equal(
Data(
hex: "0000000000000000000000000000000000000000000000000000000000000001" +
"0000000000000000000000000000000000000000000000000000000000000080" +
"0000000000000000000000000000000000000000000000000000000000000060" +
"0000000000000000000000000000000000000000000000000000000000000001" +
"0000000000000000000000000000000000000000000000000000000000000010" +
"62617A2875696E7433322C626F6F6C2900000000000000000000000000000000"
Expand Down
16 changes: 8 additions & 8 deletions Web3Swift/ABI/EncodedABITuple.swift
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import Foundation
/** Bytes of the encoded abi tuple */
public final class EncodedABITuple: BytesScalar {

private let parameters: [ABIEncodedParameter]
private let encoding: BytesScalar

/**
Ctor
Expand All @@ -22,7 +22,11 @@ public final class EncodedABITuple: BytesScalar {
- parameters: parameters of the tuple
*/
public init(parameters: [ABIEncodedParameter]) {
self.parameters = parameters
encoding = ConcatenatedBytes(
bytes: ABITupleEncoding(
parameters: parameters
)
)
}

/**
Expand All @@ -33,11 +37,7 @@ public final class EncodedABITuple: BytesScalar {
`DescribedError` if something went wrong.
*/
public func value() throws -> Data {
return try ConcatenatedBytes(
bytes: ABITuple(
parameters: parameters
).heads(offset: 0)
).value()
return try encoding.value()
}

}
16 changes: 16 additions & 0 deletions Web3Swift/ABI/Parameters/ABIAddress.swift
Original file line number Diff line number Diff line change
Expand Up @@ -64,4 +64,20 @@ public final class ABIAddress: ABIEncodedParameter {
return try address.tails(offset: offset)
}

/**
- returns:
true
*/
public func isDynamic() -> Bool {
return address.isDynamic()
}

/**
- returns:
1
*/
public func headsCount() -> Int {
return 1
}

}
16 changes: 16 additions & 0 deletions Web3Swift/ABI/Parameters/ABIBoolean.swift
Original file line number Diff line number Diff line change
Expand Up @@ -62,4 +62,20 @@ public final class ABIBoolean: ABIEncodedParameter {
return try origin.tails(offset: offset)
}

/**
- returns:
true
*/
public func isDynamic() -> Bool {
return origin.isDynamic()
}

/**
- returns:
1
*/
public func headsCount() -> Int {
return 1
}

}
29 changes: 21 additions & 8 deletions Web3Swift/ABI/Parameters/ABIDynamicCollection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import Foundation
public final class ABIDynamicCollection: ABIEncodedParameter {

private let parameters: [ABIEncodedParameter]
private let encoding: ABITupleEncoding

/**
Ctor
Expand All @@ -23,6 +24,7 @@ public final class ABIDynamicCollection: ABIEncodedParameter {
*/
public init(parameters: [ABIEncodedParameter]) {
self.parameters = parameters
encoding = ABITupleEncoding(parameters: parameters)
}

/**
Expand Down Expand Up @@ -50,24 +52,35 @@ public final class ABIDynamicCollection: ABIEncodedParameter {
- offset: number of elements preceding the dynamic collection tails

- returns:
A collection of the parameters encodings prefixed by the parameters count. Parameters encodings are offset by the previous offset plus a 1 for the count prefix.
A collection of the parameters encodings prefixed by the parameters count.
*/
public func tails(offset: Int) throws -> [BytesScalar] {
let parameters = self.parameters
return try [
LeftZeroesPaddedBytes(
origin: SimpleBytes{
origin: SimpleBytes{ [parameters] in
try EthNumber(
value: parameters.count
).value()
},
length: 32
)
] + ABITuple(
parameters: parameters
).heads(
offset: 0
)
] + encoding.value()
}

/**
- returns:
true
*/
public func isDynamic() -> Bool {
return true
}

/**
- returns:
1
*/
public func headsCount() -> Int {
return 1
}

}
12 changes: 12 additions & 0 deletions Web3Swift/ABI/Parameters/ABIEncodedParameter.swift
Original file line number Diff line number Diff line change
Expand Up @@ -36,5 +36,17 @@ public protocol ABIEncodedParameter {
`DescribedError` if something went wrong
*/
func tails(offset: Int) throws -> [BytesScalar]

/**
- returns:
True if parameter is dynamic according to the ABI specification. False otherwise.
*/
func isDynamic() -> Bool

/**
- returns:
A count of heads elements of the parameter
*/
func headsCount() -> Int

}
Loading