41561
|
1 |
package body RMD is
|
|
2 |
|
|
3 |
|
|
4 |
|
|
5 |
function F(J : Round_Index; X,Y,Z : Word) return Word
|
|
6 |
is
|
|
7 |
Result: Word;
|
|
8 |
begin
|
|
9 |
if 0 <= J and J <= 15 then Result := X xor Y xor Z;
|
|
10 |
elsif 16 <= J and J <= 31 then Result := (X and Y) or (not X and Z);
|
|
11 |
elsif 32 <= J and J <= 47 then Result := (X or not Y) xor Z;
|
|
12 |
elsif 48 <= J and J <= 63 then Result := (X and Z) or (Y and not Z);
|
|
13 |
else Result := X xor (Y or not Z);
|
|
14 |
end if;
|
|
15 |
return Result;
|
|
16 |
end F;
|
|
17 |
|
|
18 |
|
|
19 |
|
|
20 |
function K_L(J : Round_Index) return Word
|
|
21 |
is
|
|
22 |
K: Word;
|
|
23 |
begin
|
|
24 |
if 0 <= J and J <= 15 then K := 16#0000_0000#;
|
|
25 |
elsif 16 <= J and J <= 31 then K := 16#5A82_7999#;
|
|
26 |
elsif 32 <= J and J <= 47 then K := 16#6ED9_EBA1#;
|
|
27 |
elsif 48 <= J and J <= 63 then K := 16#8F1B_BCDC#;
|
|
28 |
else K := 16#A953_FD4E#;
|
|
29 |
end if;
|
|
30 |
return K;
|
|
31 |
end K_L;
|
|
32 |
|
|
33 |
|
|
34 |
function K_R(J : Round_Index) return Word
|
|
35 |
is
|
|
36 |
K: Word;
|
|
37 |
begin
|
|
38 |
if 0 <= J and J <= 15 then K := 16#50A2_8BE6#;
|
|
39 |
elsif 16 <= J and J <= 31 then K := 16#5C4D_D124#;
|
|
40 |
elsif 32 <= J and J <= 47 then K := 16#6D70_3EF3#;
|
|
41 |
elsif 48 <= J and J <= 63 then K := 16#7A6D_76E9#;
|
|
42 |
else K := 16#0000_0000#;
|
|
43 |
end if;
|
|
44 |
return K;
|
|
45 |
end K_R;
|
|
46 |
|
|
47 |
|
|
48 |
|
|
49 |
function R_L(J : Round_Index) return Block_Index
|
|
50 |
is
|
|
51 |
R_Values : constant Block_Permutation := Block_Permutation'
|
|
52 |
(0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
|
|
53 |
7, 4, 13, 1, 10, 6, 15, 3, 12, 0, 9, 5, 2, 14, 11, 8,
|
|
54 |
3, 10, 14, 4, 9, 15, 8, 1, 2, 7, 0, 6, 13, 11, 5, 12,
|
|
55 |
1, 9, 11, 10, 0, 8, 12, 4, 13, 3, 7, 15, 14, 5, 6, 2,
|
|
56 |
4, 0, 5, 9, 7, 12, 2, 10, 14, 1, 3, 8, 11, 6, 15, 13);
|
|
57 |
--# for R_Values declare rule;
|
|
58 |
begin
|
|
59 |
return R_Values(J);
|
|
60 |
end R_L;
|
|
61 |
|
|
62 |
|
|
63 |
function R_R(J : Round_Index) return Block_Index
|
|
64 |
is
|
|
65 |
R_Values : constant Block_Permutation := Block_Permutation'
|
|
66 |
(5, 14, 7, 0, 9, 2, 11, 4, 13, 6, 15, 8, 1, 10, 3, 12,
|
|
67 |
6, 11, 3, 7, 0, 13, 5, 10, 14, 15, 8, 12, 4, 9, 1, 2,
|
|
68 |
15, 5, 1, 3, 7, 14, 6, 9, 11, 8, 12, 2, 10, 0, 4, 13,
|
|
69 |
8, 6, 4, 1, 3, 11, 15, 0, 5, 12, 2, 13, 9, 7, 10, 14,
|
|
70 |
12, 15, 10, 4, 1, 5, 8, 7, 6, 2, 13, 14, 0, 3, 9, 11);
|
|
71 |
--# for R_Values declare rule;
|
|
72 |
begin
|
|
73 |
return R_Values(J);
|
|
74 |
end R_R;
|
|
75 |
|
|
76 |
|
|
77 |
function S_L(J : Round_Index) return Rotate_Amount
|
|
78 |
is
|
|
79 |
S_Values : constant Rotate_Definition := Rotate_Definition'
|
|
80 |
(11, 14, 15, 12, 5, 8, 7, 9, 11, 13, 14, 15, 6, 7, 9, 8,
|
|
81 |
7, 6, 8, 13, 11, 9, 7, 15, 7, 12, 15, 9, 11, 7, 13, 12,
|
|
82 |
11, 13, 6, 7, 14, 9, 13, 15, 14, 8, 13, 6, 5, 12, 7, 5,
|
|
83 |
11, 12, 14, 15, 14, 15, 9, 8, 9, 14, 5, 6, 8, 6, 5, 12,
|
|
84 |
9, 15, 5, 11, 6, 8, 13, 12, 5, 12, 13, 14, 11, 8, 5, 6);
|
|
85 |
--# for S_Values declare rule;
|
|
86 |
begin
|
|
87 |
return S_Values(J);
|
|
88 |
end S_L;
|
|
89 |
|
|
90 |
|
|
91 |
function S_R(J : Round_Index) return Rotate_Amount
|
|
92 |
is
|
|
93 |
S_Values : constant Rotate_Definition := Rotate_Definition'
|
|
94 |
(8, 9, 9, 11, 13, 15, 15, 5, 7, 7, 8, 11, 14, 14, 12, 6,
|
|
95 |
9, 13, 15, 7, 12, 8, 9, 11, 7, 7, 12, 7, 6, 15, 13, 11,
|
|
96 |
9, 7, 15, 11, 8, 6, 6, 14, 12, 13, 5, 14, 13, 13, 7, 5,
|
|
97 |
15, 5, 8, 11, 14, 14, 6, 14, 6, 9, 12, 9, 12, 5, 15, 8,
|
|
98 |
8, 5, 12, 9, 12, 5, 14, 6, 8, 13, 6, 5, 15, 13, 11, 11);
|
|
99 |
--# for S_Values declare rule;
|
|
100 |
begin
|
|
101 |
return S_Values(J);
|
|
102 |
end S_R;
|
|
103 |
|
|
104 |
|
|
105 |
|
|
106 |
procedure Round(CA, CB, CC, CD, CE : in out Word; X : in Block)
|
|
107 |
is
|
|
108 |
CLA, CLB, CLC, CLD, CLE, CRA, CRB, CRC, CRD, CRE : Word;
|
|
109 |
T : Word;
|
|
110 |
begin
|
|
111 |
CLA := CA;
|
|
112 |
CLB := CB;
|
|
113 |
CLC := CC;
|
|
114 |
CLD := CD;
|
|
115 |
CLE := CE;
|
|
116 |
CRA := CA;
|
|
117 |
CRB := CB;
|
|
118 |
CRC := CC;
|
|
119 |
CRD := CD;
|
|
120 |
CRE := CE;
|
|
121 |
for J in Round_Index range 0..79
|
|
122 |
loop
|
|
123 |
-- left
|
|
124 |
T := Wordops.Rotate(S_L(J),
|
|
125 |
CLA +
|
|
126 |
F(J, CLB, CLC, CLD) +
|
|
127 |
X(R_L(J)) +
|
|
128 |
K_L(J)) +
|
|
129 |
CLE;
|
|
130 |
CLA := CLE;
|
|
131 |
CLE := CLD;
|
|
132 |
CLD := Wordops.Rotate(10, CLC);
|
|
133 |
CLC := CLB;
|
|
134 |
CLB := T;
|
|
135 |
-- right
|
|
136 |
T := Wordops.Rotate(S_R(J),
|
|
137 |
CRA +
|
|
138 |
F(79 - J, CRB, CRC, CRD) +
|
|
139 |
X(R_R(J)) +
|
|
140 |
K_R(J)) +
|
|
141 |
CRE;
|
|
142 |
CRA := CRE;
|
|
143 |
CRE := CRD;
|
|
144 |
CRD := Wordops.Rotate(10, CRC);
|
|
145 |
CRC := CRB;
|
|
146 |
CRB := T;
|
|
147 |
--# assert Chain_Pair'(Chain'(CLA, CLB, CLC, CLD, CLE),
|
|
148 |
--# Chain'(CRA, CRB, CRC, CRD, CRE)) =
|
|
149 |
--# steps(Chain_Pair'(Chain'(CA~, CB~, CC~, CD~, CE~),
|
|
150 |
--# Chain'(CA~, CB~, CC~, CD~, CE~)), J + 1, X)
|
|
151 |
--# and CA = CA~ and CB = CB~ and CC = CC~ and CD = CD~ and CE = CE~;
|
|
152 |
end loop;
|
|
153 |
T := CB + CLC + CRD;
|
|
154 |
CB := CC + CLD + CRE;
|
|
155 |
CC := CD + CLE + CRA;
|
|
156 |
CD := CE + CLA + CRB;
|
|
157 |
CE := CA + CLB + CRC;
|
|
158 |
CA := T;
|
|
159 |
end Round;
|
|
160 |
|
|
161 |
function Hash(X : Message) return Chain
|
|
162 |
is
|
|
163 |
CA_Init : constant Word := 16#6745_2301#;
|
|
164 |
CB_Init : constant Word := 16#EFCD_AB89#;
|
|
165 |
CC_Init : constant Word := 16#98BA_DCFE#;
|
|
166 |
CD_Init : constant Word := 16#1032_5476#;
|
|
167 |
CE_Init : constant Word := 16#C3D2_E1F0#;
|
|
168 |
CA, CB, CC, CD, CE : Word;
|
|
169 |
begin
|
|
170 |
CA := CA_Init;
|
|
171 |
CB := CB_Init;
|
|
172 |
CC := CC_Init;
|
|
173 |
CD := CD_Init;
|
|
174 |
CE := CE_Init;
|
|
175 |
for I in Message_Index range X'First..X'Last
|
|
176 |
loop
|
|
177 |
Round(CA, CB, CC, CD, CE, X(I));
|
|
178 |
--# assert Chain'(CA, CB, CC, CD, CE) = rounds(
|
|
179 |
--# Chain'(CA_Init, CB_Init, CC_Init, CD_Init, CE_Init),
|
|
180 |
--# I + 1,
|
|
181 |
--# X);
|
|
182 |
end loop;
|
|
183 |
return Chain'(CA, CB, CC, CD, CE);
|
|
184 |
end Hash;
|
|
185 |
|
|
186 |
end RMD;
|
|
187 |
|