src/crypto/blake/blake2b/sized.bend
bend-collections-laws-crypto@1.0.0.0 · 88 lines · 13 definitions
1import Base
2import bend-collections-laws-crypto@1.0.0.0/src/crypto/blake/blake2b/types.bend as T
3import bend-collections-laws-crypto@1.0.0.0/src/crypto/blake/blake2b/blake2b.bend as B
4
5
6
7
8
9
10
11
12def word(+b0: U32, +b1: U32, +b2: U32, +b3: U32) -> U32:
13 U32.or(U32.or(b0, U32.shln(b1, 8n)), U32.or(U32.shln(b2, 16n), U32.shln(b3, 24n)))
14
15
16def words(bs: List<&2, U32>) -> List<&2, U32>:
17 match bs:
18 case Nil{}:
19 Nil{}
20 case b0 <> Nil{}:
21 [word(b0, 0, 0, 0)]
22 case b0 <> b1 <> Nil{}:
23 [word(b0, b1, 0, 0)]
24 case b0 <> b1 <> b2 <> Nil{}:
25 [word(b0, b1, b2, 0)]
26 case b0 <> b1 <> b2 <> b3 <> rest:
27 word(b0, b1, b2, b3) <> words(rest)
28
29def fill(ws: List<&2, U32>, +i: U32, a: Array<U32>) -> Array<U32>:
30 match ws:
31 case Nil{}:
32 a
33 case w <> rest:
34 fill(rest, U32.inc(i), Array.set(U32, a, i, w))
35
36def pw(k: Nat) -> Nat:
37 match k:
38 case 0n:
39 1n
40 case 1n+p:
41 Nat.double(pw(p))
42
43
44def depth_go(fuel: Nat, +n: Nat, +d: Nat, done: Bool) -> Nat:
45 match fuel done:
46 case _ True{}:
47 d
48 case 0n False{}:
49 d
50 case 1n+f False{}:
51 depth_go(f, n, 1n+d, Nat.is_le(n, pw(1n+d)))
52
53def depth(+n: Nat) -> Nat:
54 depth_go(32n, n, 0n, Nat.is_le(n, 1n))
55
56
57def pack(bs: List<&2, U32>) -> Array<U32>:
58 +ws = words(bs)
59 fill(ws, 0, Array.new(U32, depth(List.length(&2, U32, ws)), 0))
60
61
62def initial(+nn: U32) -> T.Chain:
63 T.H{T.W{U32.xor(4089235720, U32.or(16842752, nn)), 1779033703}, T.W{2227873595, 3144134277}, T.W{4271175723, 1013904242}, T.W{1595750129, 2773480762}, T.W{2917565137, 1359893119}, T.W{725511199, 2600822924}, T.W{4215389547, 528734635}, T.W{327033209, 1541459225}}
64
65def le(+w: U32) -> List<&2, U32>:
66 [U32.and(w, 255), U32.and(U32.shrn(w, 8n), 255), U32.and(U32.shrn(w, 16n), 255), U32.shrn(w, 24n)]
67
68def lane_bytes(l: T.Lane) -> List<&2, U32>:
69 match l:
70 case T.W{lo, hi}:
71 List.append(&2, U32, le(lo), le(hi))
72
73
74def chain_bytes(h: T.Chain) -> List<&2, U32>:
75 match h:
76 case T.H{h0, h1, h2, h3, h4, h5, h6, h7}:
77 List.concat(&2, U32, [lane_bytes(h0), lane_bytes(h1), lane_bytes(h2), lane_bytes(h3), lane_bytes(h4), lane_bytes(h5), lane_bytes(h6), lane_bytes(h7)])
78
79
80
81def chain(+nn: Nat, a: Array<U32>, +ll: Nat) -> T.Chain:
82 +n = Nat.div(Nat.sub(ll, 1n), 128n)
83 B.blocks(n, 0, Nat.sub(ll, Nat.mul(n, 128n)), T.C{0, 0, 0, 0}, (a, initial(U32.from_nat(nn))))
84
85
86def hash(+nn: Nat, +bs: List<&2, U32>) -> List<&2, U32>:
87 +ll = List.length(&2, U32, bs)
88 List.take(&2, U32, chain_bytes(chain(nn, pack(bs), ll)), nn)