diff --git a/nitro/abi.nim b/nitro/abi.nim index ef2dea3..9b5c1bd 100644 --- a/nitro/abi.nim +++ b/nitro/abi.nim @@ -13,6 +13,8 @@ type head: Slice[int] tail: seq[byte] +{.push raises:[].} + proc write*[T](encoder: var AbiEncoder, value: T) proc encode*[T](_: type AbiEncoder, value: T): seq[byte] diff --git a/nitro/channel.nim b/nitro/channel.nim index 6fefc33..c8fa443 100644 --- a/nitro/channel.nim +++ b/nitro/channel.nim @@ -10,6 +10,8 @@ type participants*: seq[EthAddress] chainId*: UInt256 +{.push raises:[].} + proc getChannelId*(channel: Channel): array[32, byte] = var encoder= AbiEncoder.init() encoder.startTuple() diff --git a/nitro/helpers.nim b/nitro/helpers.nim new file mode 100644 index 0000000..c1c7315 --- /dev/null +++ b/nitro/helpers.nim @@ -0,0 +1,13 @@ +import std/options +import pkg/stew/results + +export options +export results + +{.push raises:[].} + +proc toOption*[T, E](res: Result[T, E]): Option[T] = + if res.isOk: + res.value.some + else: + T.none diff --git a/nitro/outcome.nim b/nitro/outcome.nim index c988ccf..a21fa87 100644 --- a/nitro/outcome.nim +++ b/nitro/outcome.nim @@ -25,6 +25,8 @@ type targetChannelId*: array[32, byte] destinations*: seq[array[32, byte]] +{.push raises:[].} + proc encode*(encoder: var AbiEncoder, guarantee: Guarantee) = encoder.startTuple() encoder.startTuple() diff --git a/nitro/signature.nim b/nitro/signature.nim index 1cb01f8..5fbde38 100644 --- a/nitro/signature.nim +++ b/nitro/signature.nim @@ -1,8 +1,11 @@ +import std/options import pkg/nimcrypto import pkg/secp256k1 import pkg/stew/byteutils import ./state +import ./helpers +export options export toPublicKey type @@ -10,6 +13,8 @@ type PublicKey* = SkPublicKey Signature* = SkRecoverableSignature +{.push raises:[].} + proc rng(data: var openArray[byte]): bool = randomBytes(data) == data.len @@ -19,8 +24,8 @@ proc random*(_: type PrivateKey): PrivateKey = proc `$`*(key: PrivateKey): string = key.toHex() -proc parse*(_: type PrivateKey, s: string): PrivateKey = - SkSecretKey.fromHex(s).tryGet() +proc parse*(_: type PrivateKey, s: string): Option[PrivateKey] = + SkSecretKey.fromHex(s).toOption() proc sign(key: PrivateKey, data: openArray[byte]): Signature = let hash = keccak256.digest(data).data @@ -42,7 +47,10 @@ proc `$`*(signature: Signature): string = bytes[64] += 27 bytes.toHex() -proc parse*(_: type Signature, s: string): Signature = - var bytes = array[65, byte].fromHex(s) - bytes[64] -= 27 - SkRecoverableSignature.fromRaw(bytes).tryGet() +proc parse*(_: type Signature, s: string): Option[Signature] = + try: + var bytes = array[65, byte].fromHex(s) + bytes[64] = bytes[64] - 27 + SkRecoverableSignature.fromRaw(bytes).toOption() + except ValueError: + Signature.none diff --git a/nitro/state.nim b/nitro/state.nim index f70ce60..4f2aa4b 100644 --- a/nitro/state.nim +++ b/nitro/state.nim @@ -27,6 +27,8 @@ type outcome*: seq[byte] appdata*: seq[byte] +{.push raises:[].} + proc fixedPart*(state: State): FixedPart = FixedPart( chainId: state.channel.chainId, diff --git a/nitro/types.nim b/nitro/types.nim index 0f95800..3713816 100644 --- a/nitro/types.nim +++ b/nitro/types.nim @@ -1,17 +1,24 @@ import std/math +import std/options import pkg/stint import pkg/stew/byteutils export stint +export options type UInt48* = range[0'u64..2'u64^48-1] EthAddress* = distinct array[20, byte] +{.push raises:[].} + proc toArray*(address: EthAddress): array[20, byte] = array[20, byte](address) -proc fromHex*(_: type EthAddress, hex: string): EthAddress = - EthAddress(array[20, byte].fromHex(hex)) +proc fromHex*(_: type EthAddress, hex: string): Option[EthAddress] = + try: + EthAddress(array[20, byte].fromHex(hex)).some + except ValueError: + EthAddress.none proc `==`*(a, b: EthAddress): bool {.borrow.} diff --git a/tests/nitro/testChannel.nim b/tests/nitro/testChannel.nim index a41f49d..3cfa917 100644 --- a/tests/nitro/testChannel.nim +++ b/tests/nitro/testChannel.nim @@ -25,7 +25,7 @@ suite "channel": chainId: 9001.u256, nonce: 1, participants: @[ - EthAddress.fromHex("24b905Dcc8A11C0FE57C2592f3D25f0447402C10") + EthAddress.fromHex("24b905Dcc8A11C0FE57C2592f3D25f0447402C10").get() ] ) let expected = array[32, byte].fromHex( diff --git a/tests/nitro/testOutcome.nim b/tests/nitro/testOutcome.nim index 945c9d6..cfe6315 100644 --- a/tests/nitro/testOutcome.nim +++ b/tests/nitro/testOutcome.nim @@ -94,7 +94,7 @@ suite "outcome": kind: allocationType, assetHolder: EthAddress.fromHex( "1E90B49563da16D2537CA1Ddd9b1285279103D93" - ), + ).get(), allocation: Allocation(@[ AllocationItem( destination: array[32, byte].fromHex( @@ -108,7 +108,7 @@ suite "outcome": kind: guaranteeType, assetHolder: EthAddress.fromHex( "1E90B49563da16D2537CA1Ddd9b1285279103D93" - ), + ).get(), guarantee: Guarantee( targetChannelId: array[32, byte].fromHex( "cac1bb71f0a97c8ac94ca9546b43178a9ad254c7b757ac07433aa6df35cd8089" diff --git a/tests/nitro/testSignature.nim b/tests/nitro/testSignature.nim index 0ad4f2d..3cc5d08 100644 --- a/tests/nitro/testSignature.nim +++ b/tests/nitro/testSignature.nim @@ -26,7 +26,7 @@ suite "signature": chainId: 0x1.u256, nonce: 1, participants: @[ - EthAddress.fromHex("0x8a64E10FF40Bc9C90EA5750313dB5e036495c10E") + EthAddress.fromHex("0x8a64E10FF40Bc9C90EA5750313dB5e036495c10E").get() ] ), outcome: Outcome(@[]), @@ -38,10 +38,10 @@ suite "signature": ) let seckey = PrivateKey.parse( "41b0f5f91967dded8af487277874f95116094cc6004ac2b2169b5b6a87608f3e" - ) + ).get() let expected = Signature.parse( "9b966cf0065586d59c8b9eb475ac763c96ad8316b81061238f32968a631f9e21" & "251363c193c78c89b3eb2fec23f0ea5c3c72acff7d1f27430cfb84b9da9831fb" & "1c" - ) + ).get() check seckey.sign(state) == expected diff --git a/tests/nitro/testState.nim b/tests/nitro/testState.nim index 199c5f8..be0bdb6 100644 --- a/tests/nitro/testState.nim +++ b/tests/nitro/testState.nim @@ -55,7 +55,7 @@ suite "state": chainId: 0x1.u256, nonce: 1, participants: @[ - EthAddress.fromHex("DBE821484648c73C1996Da25f2355342B9803eBD") + EthAddress.fromHex("DBE821484648c73C1996Da25f2355342B9803eBD").get() ] ), outcome: Outcome(@[]),