Skip to content

Commit aa076ba

Browse files
Merge branch 'develop' into feature/EIP-1559
2 parents 938a4ce + b267da1 commit aa076ba

File tree

12 files changed

+150
-220
lines changed

12 files changed

+150
-220
lines changed

.github/workflows/ci.yml

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,9 @@ jobs:
2323
spm:
2424
name: Swift Package Manager 5.4
2525
runs-on: macOS-11
26-
concurrency: spm
26+
concurrency:
27+
group: spm-${{ github.run_id }}
28+
cancel-in-progress: false
2729
env:
2830
DEVELOPER_DIR: /Applications/Xcode_12.5.1.app/Contents/Developer
2931
steps:
@@ -45,7 +47,9 @@ jobs:
4547
carthage:
4648
name: Carthage
4749
runs-on: macOS-11
48-
concurrency: carthage
50+
concurrency:
51+
group: carthage-${{ github.run_id }}
52+
cancel-in-progress: false
4953
env:
5054
DEVELOPER_DIR: /Applications/Xcode_12.5.1.app/Contents/Developer
5155
strategy:

Sources/web3swift/Convenience/Data+Extension.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ public extension Data {
4848
let result = data.withUnsafeMutableBytes { (body: UnsafeMutableRawBufferPointer) -> Int32? in
4949
if let bodyAddress = body.baseAddress, body.count > 0 {
5050
let pointer = bodyAddress.assumingMemoryBound(to: UInt8.self)
51-
return SecRandomCopyBytes(kSecRandomDefault, 32, pointer)
51+
return SecRandomCopyBytes(kSecRandomDefault, length, pointer)
5252
} else {
5353
return nil
5454
}

Sources/web3swift/Convenience/SECP256k1.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -341,7 +341,7 @@ extension SECP256K1 {
341341
let result = data.withUnsafeMutableBytes { (mutableRBBytes) -> Int32? in
342342
if let mutableRBytes = mutableRBBytes.baseAddress, mutableRBBytes.count > 0 {
343343
let mutableBytes = mutableRBytes.assumingMemoryBound(to: UInt8.self)
344-
return SecRandomCopyBytes(kSecRandomDefault, 32, mutableBytes)
344+
return SecRandomCopyBytes(kSecRandomDefault, length, mutableBytes)
345345
} else {
346346
return nil
347347
}

Sources/web3swift/EthereumABI/ABIDecoding.swift

Lines changed: 27 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ extension ABIDecoder {
2121
var toReturn = [AnyObject]()
2222
var consumed: UInt64 = 0
2323
for i in 0 ..< types.count {
24-
let (v, c) = decodeSignleType(type: types[i], data: data, pointer: consumed)
24+
let (v, c) = decodeSingleType(type: types[i], data: data, pointer: consumed)
2525
guard let valueUnwrapped = v, let consumedUnwrapped = c else {return nil}
2626
toReturn.append(valueUnwrapped)
2727
consumed = consumed + consumedUnwrapped
@@ -30,7 +30,7 @@ extension ABIDecoder {
3030
return toReturn
3131
}
3232

33-
public static func decodeSignleType(type: ABI.Element.ParameterType, data: Data, pointer: UInt64 = 0) -> (value: AnyObject?, bytesConsumed: UInt64?) {
33+
public static func decodeSingleType(type: ABI.Element.ParameterType, data: Data, pointer: UInt64 = 0) -> (value: AnyObject?, bytesConsumed: UInt64?) {
3434
let (elData, nextPtr) = followTheData(type: type, data: data, pointer: pointer)
3535
guard let elementItself = elData, let nextElementPointer = nextPtr else {
3636
return (nil, nil)
@@ -115,7 +115,7 @@ extension ABIDecoder {
115115
var subpointer: UInt64 = 32
116116
var toReturn = [AnyObject]()
117117
for _ in 0 ..< length {
118-
let (v, c) = decodeSignleType(type: subType, data: elementItself, pointer: subpointer)
118+
let (v, c) = decodeSingleType(type: subType, data: elementItself, pointer: subpointer)
119119
guard let valueUnwrapped = v, let consumedUnwrapped = c else {break}
120120
toReturn.append(valueUnwrapped)
121121
subpointer = subpointer + consumedUnwrapped
@@ -132,7 +132,7 @@ extension ABIDecoder {
132132
var toReturn = [AnyObject]()
133133
// print("Dynamic array sub element itself: \n" + dataSlice.toHexString())
134134
for _ in 0 ..< length {
135-
let (v, c) = decodeSignleType(type: subType, data: dataSlice, pointer: subpointer)
135+
let (v, c) = decodeSingleType(type: subType, data: dataSlice, pointer: subpointer)
136136
guard let valueUnwrapped = v, let consumedUnwrapped = c else {break}
137137
toReturn.append(valueUnwrapped)
138138
if (subType.isStatic) {
@@ -150,7 +150,7 @@ extension ABIDecoder {
150150
var toReturn = [AnyObject]()
151151
var consumed: UInt64 = 0
152152
for _ in 0 ..< length {
153-
let (v, c) = decodeSignleType(type: subType, data: elementItself, pointer: consumed)
153+
let (v, c) = decodeSingleType(type: subType, data: elementItself, pointer: consumed)
154154
guard let valueUnwrapped = v, let consumedUnwrapped = c else {return (nil, nil)}
155155
toReturn.append(valueUnwrapped)
156156
consumed = consumed + consumedUnwrapped
@@ -168,10 +168,28 @@ extension ABIDecoder {
168168
var toReturn = [AnyObject]()
169169
var consumed: UInt64 = 0
170170
for i in 0 ..< subTypes.count {
171-
let (v, c) = decodeSignleType(type: subTypes[i], data: elementItself, pointer: consumed)
171+
let (v, c) = decodeSingleType(type: subTypes[i], data: elementItself, pointer: consumed)
172172
guard let valueUnwrapped = v, let consumedUnwrapped = c else {return (nil, nil)}
173173
toReturn.append(valueUnwrapped)
174-
consumed = consumed + consumedUnwrapped
174+
/*
175+
When decoding a tuple that is not static or an array with a subtype that is not static, the second value in the tuple returned by decodeSignleType is a pointer to the next element, NOT the length of the consumed element. So when decoding such an element, consumed should be set to consumedUnwrapped, NOT incremented by consumedUnwrapped.
176+
*/
177+
switch subTypes[i] {
178+
case .array(type: let subType, length: _):
179+
if !subType.isStatic {
180+
consumed = consumedUnwrapped
181+
} else {
182+
consumed = consumed + consumedUnwrapped
183+
}
184+
case .tuple(types: _):
185+
if !subTypes[i].isStatic {
186+
consumed = consumedUnwrapped
187+
} else {
188+
consumed = consumed + consumedUnwrapped
189+
}
190+
default:
191+
consumed = consumed + consumedUnwrapped
192+
}
175193
}
176194
// print("Tuple element is: \n" + String(describing: toReturn))
177195
if type.isStatic {
@@ -251,11 +269,11 @@ extension ABIDecoder {
251269
let data = logs[i+1]
252270
let input = indexedInputs[i]
253271
if !input.type.isStatic || input.type.isArray || input.type.memoryUsage != 32 {
254-
let (v, _) = ABIDecoder.decodeSignleType(type: .bytes(length: 32), data: data)
272+
let (v, _) = ABIDecoder.decodeSingleType(type: .bytes(length: 32), data: data)
255273
guard let valueUnwrapped = v else {return nil}
256274
indexedValues.append(valueUnwrapped)
257275
} else {
258-
let (v, _) = ABIDecoder.decodeSignleType(type: input.type, data: data)
276+
let (v, _) = ABIDecoder.decodeSingleType(type: input.type, data: data)
259277
guard let valueUnwrapped = v else {return nil}
260278
indexedValues.append(valueUnwrapped)
261279
}

Sources/web3swift/HookedFunctions/Web3+BrowserFunctions.swift

Lines changed: 44 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -70,15 +70,18 @@ extension web3.BrowserFunctions {
7070
}
7171

7272
public func sendTransaction(_ transactionJSON: [String: Any], password: String = "web3swift") -> [String: Any]? {
73-
guard let transaction = EthereumTransaction.fromJSON(transactionJSON) else {return nil}
74-
guard let options = TransactionOptions.fromJSON(transactionJSON) else {return nil}
75-
var transactionOptions = TransactionOptions()
76-
transactionOptions.from = options.from
77-
transactionOptions.to = options.to
78-
transactionOptions.value = options.value != nil ? options.value! : BigUInt(0)
79-
transactionOptions.gasLimit = options.gasLimit != nil ? options.gasLimit! : .automatic
80-
transactionOptions.gasPrice = options.gasPrice != nil ? options.gasPrice! : .automatic
81-
return self.sendTransaction(transaction, transactionOptions: transactionOptions, password: password)
73+
do {
74+
let jsonData: Data = try JSONSerialization.data(withJSONObject: transactionJSON, options: [])
75+
let transaction: EthereumTransaction = try JSONDecoder().decode(EthereumTransaction.self, from: jsonData)
76+
let options: TransactionOptions = try JSONDecoder().decode(TransactionOptions.self, from: jsonData)
77+
var transactionOptions = TransactionOptions()
78+
transactionOptions.from = options.from
79+
transactionOptions.to = options.to
80+
transactionOptions.value = options.value ?? 0
81+
transactionOptions.gasLimit = options.gasLimit ?? .automatic
82+
transactionOptions.gasPrice = options.gasPrice ?? .automatic
83+
return self.sendTransaction(transaction, transactionOptions: transactionOptions, password: password)
84+
} catch { return nil }
8285
}
8386

8487
public func sendTransaction(_ transaction: EthereumTransaction, transactionOptions: TransactionOptions, password: String = "web3swift") -> [String: Any]? {
@@ -91,15 +94,18 @@ extension web3.BrowserFunctions {
9194
}
9295

9396
public func estimateGas(_ transactionJSON: [String: Any]) -> BigUInt? {
94-
guard let transaction = EthereumTransaction.fromJSON(transactionJSON) else {return nil}
95-
guard let options = TransactionOptions.fromJSON(transactionJSON) else {return nil}
96-
var transactionOptions = TransactionOptions()
97-
transactionOptions.from = options.from
98-
transactionOptions.to = options.to
99-
transactionOptions.value = options.value != nil ? options.value! : BigUInt(0)
100-
transactionOptions.gasLimit = .automatic
101-
transactionOptions.gasPrice = options.gasPrice != nil ? options.gasPrice! : .automatic
102-
return self.estimateGas(transaction, transactionOptions: transactionOptions)
97+
do {
98+
let jsonData: Data = try JSONSerialization.data(withJSONObject: transactionJSON, options: [])
99+
let transaction: EthereumTransaction = try JSONDecoder().decode(EthereumTransaction.self, from: jsonData)
100+
let options: TransactionOptions = try JSONDecoder().decode(TransactionOptions.self, from: jsonData)
101+
var transactionOptions = TransactionOptions()
102+
transactionOptions.from = options.from
103+
transactionOptions.to = options.to
104+
transactionOptions.value = options.value ?? 0
105+
transactionOptions.gasLimit = .automatic
106+
transactionOptions.gasPrice = options.gasPrice ?? .automatic
107+
return self.estimateGas(transaction, transactionOptions: transactionOptions)
108+
} catch { return nil }
103109
}
104110

105111
public func estimateGas(_ transaction: EthereumTransaction, transactionOptions: TransactionOptions) -> BigUInt? {
@@ -112,9 +118,10 @@ extension web3.BrowserFunctions {
112118
}
113119

114120
public func prepareTxForApproval(_ transactionJSON: [String: Any]) -> (transaction: EthereumTransaction?, options: TransactionOptions?) {
115-
guard let transaction = EthereumTransaction.fromJSON(transactionJSON) else {return (nil, nil)}
116-
guard let options = TransactionOptions.fromJSON(transactionJSON) else {return (nil, nil)}
117121
do {
122+
let jsonData: Data = try JSONSerialization.data(withJSONObject: transactionJSON, options: [])
123+
let transaction: EthereumTransaction = try JSONDecoder().decode(EthereumTransaction.self, from: jsonData)
124+
let options: TransactionOptions = try JSONDecoder().decode(TransactionOptions.self, from: jsonData)
118125
return try self.prepareTxForApproval(transaction, options: options)
119126
} catch {
120127
return (nil, nil)
@@ -140,20 +147,23 @@ extension web3.BrowserFunctions {
140147
}
141148

142149
public func signTransaction(_ transactionJSON: [String: Any], password: String = "web3swift") -> String? {
143-
guard let transaction = EthereumTransaction.fromJSON(transactionJSON) else {return nil}
144-
guard let options = TransactionOptions.fromJSON(transactionJSON) else {return nil}
145-
var transactionOptions = TransactionOptions()
146-
transactionOptions.from = options.from
147-
transactionOptions.to = options.to
148-
transactionOptions.value = options.value != nil ? options.value! : BigUInt(0)
149-
transactionOptions.gasLimit = options.gasLimit != nil ? options.gasLimit! : .automatic
150-
transactionOptions.gasPrice = options.gasPrice != nil ? options.gasPrice! : .automatic
151-
if let nonceString = transactionJSON["nonce"] as? String, let nonce = BigUInt(nonceString.stripHexPrefix(), radix: 16) {
152-
transactionOptions.nonce = .manual(nonce)
153-
} else {
154-
transactionOptions.nonce = .pending
155-
}
156-
return self.signTransaction(transaction, transactionOptions: transactionOptions, password: password)
150+
do {
151+
let jsonData: Data = try JSONSerialization.data(withJSONObject: transactionJSON, options: [])
152+
let transaction: EthereumTransaction = try JSONDecoder().decode(EthereumTransaction.self, from: jsonData)
153+
let options: TransactionOptions = try JSONDecoder().decode(TransactionOptions.self, from: jsonData)
154+
var transactionOptions = TransactionOptions()
155+
transactionOptions.from = options.from
156+
transactionOptions.to = options.to
157+
transactionOptions.value = options.value ?? 0
158+
transactionOptions.gasLimit = options.gasLimit ?? .automatic
159+
transactionOptions.gasPrice = options.gasPrice ?? .automatic
160+
if let nonceString = transactionJSON["nonce"] as? String, let nonce = BigUInt(nonceString.stripHexPrefix(), radix: 16) {
161+
transactionOptions.nonce = .manual(nonce)
162+
} else {
163+
transactionOptions.nonce = .pending
164+
}
165+
return self.signTransaction(transaction, transactionOptions: transactionOptions, password: password)
166+
} catch { return nil }
157167
}
158168

159169
public func signTransaction(_ trans: EthereumTransaction, transactionOptions: TransactionOptions, password: String = "web3swift") -> String? {

Sources/web3swift/Promises/Promise+Web3+Contract+GetIndexedEvents.swift

Lines changed: 0 additions & 7 deletions
This file was deleted.

Sources/web3swift/Transaction/EthereumTransaction.swift

Lines changed: 6 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ public struct EthereumTransaction: CustomStringConvertible {
3131
get {
3232
if (self.r == BigUInt(0) && self.s == BigUInt(0)) {
3333
return self.v
34-
} else if (self.v == BigUInt(27) || self.v == BigUInt(28)) {
34+
} else if (self.v == BigUInt(27) || self.v == BigUInt(28) || self.v < BigUInt(35)) {
3535
return nil
3636
} else {
3737
return ((self.v - BigUInt(1)) / BigUInt(2)) - BigUInt(17)
@@ -102,11 +102,12 @@ public struct EthereumTransaction: CustomStringConvertible {
102102
} else if self.v >= 27 && self.v <= 30 {
103103
d = 27
104104
}
105-
if (chainID != nil && chainID != 0) {
106-
normalizedV = self.v - d - self.chainID! - self.chainID!
107-
} else if (inferedChainID != nil) {
108-
normalizedV = self.v - d - inferedChainID! - inferedChainID!
105+
if let testID = self.chainID, testID != BigUInt(0) && self.v >= (d + testID + testID) {
106+
normalizedV = self.v - d - testID - testID
107+
} else if let testID = inferedChainID, self.v >= (d + testID + testID) {
108+
normalizedV = self.v - d - testID - testID
109109
} else {
110+
if(d > v) { d = 0 }
110111
normalizedV = self.v - d
111112
}
112113
guard let vData = normalizedV.serialize().setLengthLeft(1) else {return nil}
@@ -336,49 +337,4 @@ public extension EthereumTransaction {
336337
return tx
337338
}
338339

339-
static func fromJSON(_ json: [String: Any]) -> EthereumTransaction? {
340-
guard let options = TransactionOptions.fromJSON(json) else {return nil}
341-
guard let toString = json["to"] as? String else {return nil}
342-
var to: EthereumAddress
343-
if toString == "0x" || toString == "0x0" {
344-
to = EthereumAddress.contractDeploymentAddress()
345-
} else {
346-
guard let ethAddr = EthereumAddress(toString) else {return nil}
347-
to = ethAddr
348-
}
349-
// if (!to.isValid) {
350-
// return nil
351-
// }
352-
var dataString = json["data"] as? String
353-
if (dataString == nil) {
354-
dataString = json["input"] as? String
355-
}
356-
guard dataString != nil, let data = Data.fromHex(dataString!) else {return nil}
357-
var transaction = EthereumTransaction(to: to, data: data, options: options)
358-
if let nonceString = json["nonce"] as? String {
359-
guard let nonce = BigUInt(nonceString.stripHexPrefix(), radix: 16) else {return nil}
360-
transaction.nonce = nonce
361-
}
362-
if let vString = json["v"] as? String {
363-
guard let v = BigUInt(vString.stripHexPrefix(), radix: 16) else {return nil}
364-
transaction.v = v
365-
}
366-
if let rString = json["r"] as? String {
367-
guard let r = BigUInt(rString.stripHexPrefix(), radix: 16) else {return nil}
368-
transaction.r = r
369-
}
370-
if let sString = json["s"] as? String {
371-
guard let s = BigUInt(sString.stripHexPrefix(), radix: 16) else {return nil}
372-
transaction.s = s
373-
}
374-
if let valueString = json["value"] as? String {
375-
guard let value = BigUInt(valueString.stripHexPrefix(), radix: 16) else {return nil}
376-
transaction.value = value
377-
}
378-
let inferedChainID = transaction.inferedChainID
379-
if (transaction.inferedChainID != nil && transaction.v >= BigUInt(37)) {
380-
transaction.chainID = inferedChainID
381-
}
382-
return transaction
383-
}
384340
}

Sources/web3swift/Transaction/TransactionSigner.swift

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ public struct Web3Signer {
4949
guard let unmarshalledSignature = SECP256K1.unmarshalSignature(signatureData: serializedSignature) else {
5050
return false
5151
}
52-
let originalPublicKey = SECP256K1.privateToPublic(privateKey: privateKey)
52+
guard let originalPublicKey = SECP256K1.privateToPublic(privateKey: privateKey) else { return false }
5353
var d = BigUInt(0)
5454
if unmarshalledSignature.v >= 0 && unmarshalledSignature.v <= 3 {
5555
d = BigUInt(35)
@@ -62,7 +62,7 @@ public struct Web3Signer {
6262
transaction.r = BigUInt(Data(unmarshalledSignature.r))
6363
transaction.s = BigUInt(Data(unmarshalledSignature.s))
6464
let recoveredPublicKey = transaction.recoverPublicKey()
65-
if (!(originalPublicKey!.constantTimeComparisonTo(recoveredPublicKey))) {
65+
if !(originalPublicKey.constantTimeComparisonTo(recoveredPublicKey)) {
6666
return false
6767
}
6868
return true
@@ -87,7 +87,7 @@ public struct Web3Signer {
8787
guard let unmarshalledSignature = SECP256K1.unmarshalSignature(signatureData: serializedSignature) else {
8888
return false
8989
}
90-
let originalPublicKey = SECP256K1.privateToPublic(privateKey: privateKey)
90+
guard let originalPublicKey = SECP256K1.privateToPublic(privateKey: privateKey) else { return false }
9191
transaction.chainID = nil
9292
var d = BigUInt(0)
9393
var a = BigUInt(0)
@@ -102,7 +102,7 @@ public struct Web3Signer {
102102
transaction.r = BigUInt(Data(unmarshalledSignature.r))
103103
transaction.s = BigUInt(Data(unmarshalledSignature.s))
104104
let recoveredPublicKey = transaction.recoverPublicKey()
105-
if (!(originalPublicKey!.constantTimeComparisonTo(recoveredPublicKey))) {
105+
if !(originalPublicKey.constantTimeComparisonTo(recoveredPublicKey)) {
106106
return false
107107
}
108108
return true

0 commit comments

Comments
 (0)