mirror of
https://github.com/status-im/nim-eth.git
synced 2025-01-22 04:22:01 +00:00
6bd6bae86c
Since these types were written, we've gained an executable spec: https://github.com/ethereum/execution-specs This PR aligns some of the types we use with this spec to simplify comparisons and cross-referencing. Using a `distinct` type is a tradeoff between nim ergonomics, type safety and the ability to work around nim quirks and stdlib weaknesses. In particular, it allows us to overload common functions such as `hash` with correct and performant versions as well as maintain control over string conversions etc at the cost of a little bit of ceremony when instantiating them. Apart from distinct byte types, `Hash32`, is introduced in lieu of the existing `Hash256`, again aligning this commonly used type with the spec which picks bytes rather than bits in the name.
46 lines
1.2 KiB
Nim
46 lines
1.2 KiB
Nim
import stint, ./common/[addresses, base, hashes]
|
|
|
|
type UInt2048 = StUint[2048]
|
|
|
|
iterator chunksForBloom(h: Hash32): array[2, uint8] =
|
|
yield [h.data[0], h.data[1]]
|
|
yield [h.data[2], h.data[3]]
|
|
yield [h.data[4], h.data[5]]
|
|
|
|
proc chunkToBloomBits(chunk: array[2, uint8]): UInt2048 =
|
|
let h = chunk[0].int
|
|
let l = chunk[1].int
|
|
one(UInt2048) shl ((l + (h shl 8)) and 2047)
|
|
|
|
iterator bloomBits(h: Hash32): UInt2048 =
|
|
for chunk in chunksForBloom(h):
|
|
yield chunkToBloomBits(chunk)
|
|
|
|
type BloomFilter* = object
|
|
value*: UInt2048
|
|
|
|
proc incl*(f: var BloomFilter, h: Hash32) =
|
|
for bits in bloomBits(h):
|
|
f.value = f.value or bits
|
|
|
|
proc init*(_: type BloomFilter, h: Hash32): BloomFilter =
|
|
result.incl(h)
|
|
|
|
proc incl*[T: byte|char](f: var BloomFilter, v: openArray[T]) =
|
|
f.incl(keccak256(v))
|
|
|
|
proc incl*(f: var BloomFilter, v: Address | Bytes32) =
|
|
f.incl(v.data)
|
|
|
|
proc contains*(f: BloomFilter, h: Hash32): bool =
|
|
for bits in bloomBits(h):
|
|
if (f.value and bits).isZero:
|
|
return false
|
|
return true
|
|
|
|
template contains*(f: BloomFilter, v: openArray): bool =
|
|
f.contains(keccak256(v))
|
|
|
|
proc contains*(f: BloomFilter, v: Address | Bytes32): bool =
|
|
f.contains(v.data)
|