/src/boringssl/crypto/des/des.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
2 | | * All rights reserved. |
3 | | * |
4 | | * This package is an SSL implementation written |
5 | | * by Eric Young (eay@cryptsoft.com). |
6 | | * The implementation was written so as to conform with Netscapes SSL. |
7 | | * |
8 | | * This library is free for commercial and non-commercial use as long as |
9 | | * the following conditions are aheared to. The following conditions |
10 | | * apply to all code found in this distribution, be it the RC4, RSA, |
11 | | * lhash, DES, etc., code; not just the SSL code. The SSL documentation |
12 | | * included with this distribution is covered by the same copyright terms |
13 | | * except that the holder is Tim Hudson (tjh@cryptsoft.com). |
14 | | * |
15 | | * Copyright remains Eric Young's, and as such any Copyright notices in |
16 | | * the code are not to be removed. |
17 | | * If this package is used in a product, Eric Young should be given attribution |
18 | | * as the author of the parts of the library used. |
19 | | * This can be in the form of a textual message at program startup or |
20 | | * in documentation (online or textual) provided with the package. |
21 | | * |
22 | | * Redistribution and use in source and binary forms, with or without |
23 | | * modification, are permitted provided that the following conditions |
24 | | * are met: |
25 | | * 1. Redistributions of source code must retain the copyright |
26 | | * notice, this list of conditions and the following disclaimer. |
27 | | * 2. Redistributions in binary form must reproduce the above copyright |
28 | | * notice, this list of conditions and the following disclaimer in the |
29 | | * documentation and/or other materials provided with the distribution. |
30 | | * 3. All advertising materials mentioning features or use of this software |
31 | | * must display the following acknowledgement: |
32 | | * "This product includes cryptographic software written by |
33 | | * Eric Young (eay@cryptsoft.com)" |
34 | | * The word 'cryptographic' can be left out if the rouines from the library |
35 | | * being used are not cryptographic related :-). |
36 | | * 4. If you include any Windows specific code (or a derivative thereof) from |
37 | | * the apps directory (application code) you must include an acknowledgement: |
38 | | * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" |
39 | | * |
40 | | * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND |
41 | | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
42 | | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
43 | | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE |
44 | | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL |
45 | | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS |
46 | | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) |
47 | | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT |
48 | | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY |
49 | | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF |
50 | | * SUCH DAMAGE. |
51 | | * |
52 | | * The licence and distribution terms for any publically available version or |
53 | | * derivative of this code cannot be changed. i.e. this code cannot simply be |
54 | | * copied and put under another distribution licence |
55 | | * [including the GNU Public Licence.] */ |
56 | | |
57 | | #include <openssl/des.h> |
58 | | |
59 | | #include <stdlib.h> |
60 | | |
61 | | #include "internal.h" |
62 | | |
63 | | |
64 | | /* IP and FP |
65 | | * The problem is more of a geometric problem that random bit fiddling. |
66 | | 0 1 2 3 4 5 6 7 62 54 46 38 30 22 14 6 |
67 | | 8 9 10 11 12 13 14 15 60 52 44 36 28 20 12 4 |
68 | | 16 17 18 19 20 21 22 23 58 50 42 34 26 18 10 2 |
69 | | 24 25 26 27 28 29 30 31 to 56 48 40 32 24 16 8 0 |
70 | | |
71 | | 32 33 34 35 36 37 38 39 63 55 47 39 31 23 15 7 |
72 | | 40 41 42 43 44 45 46 47 61 53 45 37 29 21 13 5 |
73 | | 48 49 50 51 52 53 54 55 59 51 43 35 27 19 11 3 |
74 | | 56 57 58 59 60 61 62 63 57 49 41 33 25 17 9 1 |
75 | | |
76 | | The output has been subject to swaps of the form |
77 | | 0 1 -> 3 1 but the odd and even bits have been put into |
78 | | 2 3 2 0 |
79 | | different words. The main trick is to remember that |
80 | | t=((l>>size)^r)&(mask); |
81 | | r^=t; |
82 | | l^=(t<<size); |
83 | | can be used to swap and move bits between words. |
84 | | |
85 | | So l = 0 1 2 3 r = 16 17 18 19 |
86 | | 4 5 6 7 20 21 22 23 |
87 | | 8 9 10 11 24 25 26 27 |
88 | | 12 13 14 15 28 29 30 31 |
89 | | becomes (for size == 2 and mask == 0x3333) |
90 | | t = 2^16 3^17 -- -- l = 0 1 16 17 r = 2 3 18 19 |
91 | | 6^20 7^21 -- -- 4 5 20 21 6 7 22 23 |
92 | | 10^24 11^25 -- -- 8 9 24 25 10 11 24 25 |
93 | | 14^28 15^29 -- -- 12 13 28 29 14 15 28 29 |
94 | | |
95 | | Thanks for hints from Richard Outerbridge - he told me IP&FP |
96 | | could be done in 15 xor, 10 shifts and 5 ands. |
97 | | When I finally started to think of the problem in 2D |
98 | | I first got ~42 operations without xors. When I remembered |
99 | | how to use xors :-) I got it to its final state. |
100 | | */ |
101 | | #define PERM_OP(a, b, t, n, m) \ |
102 | 22.9k | do { \ |
103 | 22.9k | (t) = ((((a) >> (n)) ^ (b)) & (m)); \ |
104 | 22.9k | (b) ^= (t); \ |
105 | 22.9k | (a) ^= ((t) << (n)); \ |
106 | 22.9k | } while (0) |
107 | | |
108 | | #define IP(l, r) \ |
109 | 2.16k | do { \ |
110 | 2.16k | uint32_t tt; \ |
111 | 2.16k | PERM_OP(r, l, tt, 4, 0x0f0f0f0fL); \ |
112 | 2.16k | PERM_OP(l, r, tt, 16, 0x0000ffffL); \ |
113 | 2.16k | PERM_OP(r, l, tt, 2, 0x33333333L); \ |
114 | 2.16k | PERM_OP(l, r, tt, 8, 0x00ff00ffL); \ |
115 | 2.16k | PERM_OP(r, l, tt, 1, 0x55555555L); \ |
116 | 2.16k | } while (0) |
117 | | |
118 | | #define FP(l, r) \ |
119 | 2.16k | do { \ |
120 | 2.16k | uint32_t tt; \ |
121 | 2.16k | PERM_OP(l, r, tt, 1, 0x55555555L); \ |
122 | 2.16k | PERM_OP(r, l, tt, 8, 0x00ff00ffL); \ |
123 | 2.16k | PERM_OP(l, r, tt, 2, 0x33333333L); \ |
124 | 2.16k | PERM_OP(r, l, tt, 16, 0x0000ffffL); \ |
125 | 2.16k | PERM_OP(l, r, tt, 4, 0x0f0f0f0fL); \ |
126 | 2.16k | } while (0) |
127 | | |
128 | | #define LOAD_DATA(ks, R, S, u, t, E0, E1) \ |
129 | 103k | do { \ |
130 | 103k | (u) = (R) ^ (ks)->subkeys[S][0]; \ |
131 | 103k | (t) = (R) ^ (ks)->subkeys[S][1]; \ |
132 | 103k | } while (0) |
133 | | |
134 | | #define D_ENCRYPT(ks, LL, R, S) \ |
135 | 103k | do { \ |
136 | 103k | LOAD_DATA(ks, R, S, u, t, E0, E1); \ |
137 | 103k | t = CRYPTO_rotr_u32(t, 4); \ |
138 | 103k | (LL) ^= \ |
139 | 103k | DES_SPtrans[0][(u >> 2L) & 0x3f] ^ DES_SPtrans[2][(u >> 10L) & 0x3f] ^ \ |
140 | 103k | DES_SPtrans[4][(u >> 18L) & 0x3f] ^ \ |
141 | 103k | DES_SPtrans[6][(u >> 26L) & 0x3f] ^ DES_SPtrans[1][(t >> 2L) & 0x3f] ^ \ |
142 | 103k | DES_SPtrans[3][(t >> 10L) & 0x3f] ^ \ |
143 | 103k | DES_SPtrans[5][(t >> 18L) & 0x3f] ^ DES_SPtrans[7][(t >> 26L) & 0x3f]; \ |
144 | 103k | } while (0) |
145 | | |
146 | 5.62k | #define ITERATIONS 16 |
147 | | #define HALF_ITERATIONS 8 |
148 | | |
149 | | static const uint32_t des_skb[8][64] = { |
150 | | { // for C bits (numbered as per FIPS 46) 1 2 3 4 5 6 |
151 | | 0x00000000, 0x00000010, 0x20000000, 0x20000010, 0x00010000, |
152 | | 0x00010010, 0x20010000, 0x20010010, 0x00000800, 0x00000810, |
153 | | 0x20000800, 0x20000810, 0x00010800, 0x00010810, 0x20010800, |
154 | | 0x20010810, 0x00000020, 0x00000030, 0x20000020, 0x20000030, |
155 | | 0x00010020, 0x00010030, 0x20010020, 0x20010030, 0x00000820, |
156 | | 0x00000830, 0x20000820, 0x20000830, 0x00010820, 0x00010830, |
157 | | 0x20010820, 0x20010830, 0x00080000, 0x00080010, 0x20080000, |
158 | | 0x20080010, 0x00090000, 0x00090010, 0x20090000, 0x20090010, |
159 | | 0x00080800, 0x00080810, 0x20080800, 0x20080810, 0x00090800, |
160 | | 0x00090810, 0x20090800, 0x20090810, 0x00080020, 0x00080030, |
161 | | 0x20080020, 0x20080030, 0x00090020, 0x00090030, 0x20090020, |
162 | | 0x20090030, 0x00080820, 0x00080830, 0x20080820, 0x20080830, |
163 | | 0x00090820, 0x00090830, 0x20090820, 0x20090830, }, |
164 | | { // for C bits (numbered as per FIPS 46) 7 8 10 11 12 13 |
165 | | 0x00000000, 0x02000000, 0x00002000, 0x02002000, 0x00200000, |
166 | | 0x02200000, 0x00202000, 0x02202000, 0x00000004, 0x02000004, |
167 | | 0x00002004, 0x02002004, 0x00200004, 0x02200004, 0x00202004, |
168 | | 0x02202004, 0x00000400, 0x02000400, 0x00002400, 0x02002400, |
169 | | 0x00200400, 0x02200400, 0x00202400, 0x02202400, 0x00000404, |
170 | | 0x02000404, 0x00002404, 0x02002404, 0x00200404, 0x02200404, |
171 | | 0x00202404, 0x02202404, 0x10000000, 0x12000000, 0x10002000, |
172 | | 0x12002000, 0x10200000, 0x12200000, 0x10202000, 0x12202000, |
173 | | 0x10000004, 0x12000004, 0x10002004, 0x12002004, 0x10200004, |
174 | | 0x12200004, 0x10202004, 0x12202004, 0x10000400, 0x12000400, |
175 | | 0x10002400, 0x12002400, 0x10200400, 0x12200400, 0x10202400, |
176 | | 0x12202400, 0x10000404, 0x12000404, 0x10002404, 0x12002404, |
177 | | 0x10200404, 0x12200404, 0x10202404, 0x12202404, }, |
178 | | { // for C bits (numbered as per FIPS 46) 14 15 16 17 19 20 |
179 | | 0x00000000, 0x00000001, 0x00040000, 0x00040001, 0x01000000, |
180 | | 0x01000001, 0x01040000, 0x01040001, 0x00000002, 0x00000003, |
181 | | 0x00040002, 0x00040003, 0x01000002, 0x01000003, 0x01040002, |
182 | | 0x01040003, 0x00000200, 0x00000201, 0x00040200, 0x00040201, |
183 | | 0x01000200, 0x01000201, 0x01040200, 0x01040201, 0x00000202, |
184 | | 0x00000203, 0x00040202, 0x00040203, 0x01000202, 0x01000203, |
185 | | 0x01040202, 0x01040203, 0x08000000, 0x08000001, 0x08040000, |
186 | | 0x08040001, 0x09000000, 0x09000001, 0x09040000, 0x09040001, |
187 | | 0x08000002, 0x08000003, 0x08040002, 0x08040003, 0x09000002, |
188 | | 0x09000003, 0x09040002, 0x09040003, 0x08000200, 0x08000201, |
189 | | 0x08040200, 0x08040201, 0x09000200, 0x09000201, 0x09040200, |
190 | | 0x09040201, 0x08000202, 0x08000203, 0x08040202, 0x08040203, |
191 | | 0x09000202, 0x09000203, 0x09040202, 0x09040203, }, |
192 | | { // for C bits (numbered as per FIPS 46) 21 23 24 26 27 28 |
193 | | 0x00000000, 0x00100000, 0x00000100, 0x00100100, 0x00000008, |
194 | | 0x00100008, 0x00000108, 0x00100108, 0x00001000, 0x00101000, |
195 | | 0x00001100, 0x00101100, 0x00001008, 0x00101008, 0x00001108, |
196 | | 0x00101108, 0x04000000, 0x04100000, 0x04000100, 0x04100100, |
197 | | 0x04000008, 0x04100008, 0x04000108, 0x04100108, 0x04001000, |
198 | | 0x04101000, 0x04001100, 0x04101100, 0x04001008, 0x04101008, |
199 | | 0x04001108, 0x04101108, 0x00020000, 0x00120000, 0x00020100, |
200 | | 0x00120100, 0x00020008, 0x00120008, 0x00020108, 0x00120108, |
201 | | 0x00021000, 0x00121000, 0x00021100, 0x00121100, 0x00021008, |
202 | | 0x00121008, 0x00021108, 0x00121108, 0x04020000, 0x04120000, |
203 | | 0x04020100, 0x04120100, 0x04020008, 0x04120008, 0x04020108, |
204 | | 0x04120108, 0x04021000, 0x04121000, 0x04021100, 0x04121100, |
205 | | 0x04021008, 0x04121008, 0x04021108, 0x04121108, }, |
206 | | { // for D bits (numbered as per FIPS 46) 1 2 3 4 5 6 |
207 | | 0x00000000, 0x10000000, 0x00010000, 0x10010000, 0x00000004, |
208 | | 0x10000004, 0x00010004, 0x10010004, 0x20000000, 0x30000000, |
209 | | 0x20010000, 0x30010000, 0x20000004, 0x30000004, 0x20010004, |
210 | | 0x30010004, 0x00100000, 0x10100000, 0x00110000, 0x10110000, |
211 | | 0x00100004, 0x10100004, 0x00110004, 0x10110004, 0x20100000, |
212 | | 0x30100000, 0x20110000, 0x30110000, 0x20100004, 0x30100004, |
213 | | 0x20110004, 0x30110004, 0x00001000, 0x10001000, 0x00011000, |
214 | | 0x10011000, 0x00001004, 0x10001004, 0x00011004, 0x10011004, |
215 | | 0x20001000, 0x30001000, 0x20011000, 0x30011000, 0x20001004, |
216 | | 0x30001004, 0x20011004, 0x30011004, 0x00101000, 0x10101000, |
217 | | 0x00111000, 0x10111000, 0x00101004, 0x10101004, 0x00111004, |
218 | | 0x10111004, 0x20101000, 0x30101000, 0x20111000, 0x30111000, |
219 | | 0x20101004, 0x30101004, 0x20111004, 0x30111004, }, |
220 | | { // for D bits (numbered as per FIPS 46) 8 9 11 12 13 14 |
221 | | 0x00000000, 0x08000000, 0x00000008, 0x08000008, 0x00000400, |
222 | | 0x08000400, 0x00000408, 0x08000408, 0x00020000, 0x08020000, |
223 | | 0x00020008, 0x08020008, 0x00020400, 0x08020400, 0x00020408, |
224 | | 0x08020408, 0x00000001, 0x08000001, 0x00000009, 0x08000009, |
225 | | 0x00000401, 0x08000401, 0x00000409, 0x08000409, 0x00020001, |
226 | | 0x08020001, 0x00020009, 0x08020009, 0x00020401, 0x08020401, |
227 | | 0x00020409, 0x08020409, 0x02000000, 0x0A000000, 0x02000008, |
228 | | 0x0A000008, 0x02000400, 0x0A000400, 0x02000408, 0x0A000408, |
229 | | 0x02020000, 0x0A020000, 0x02020008, 0x0A020008, 0x02020400, |
230 | | 0x0A020400, 0x02020408, 0x0A020408, 0x02000001, 0x0A000001, |
231 | | 0x02000009, 0x0A000009, 0x02000401, 0x0A000401, 0x02000409, |
232 | | 0x0A000409, 0x02020001, 0x0A020001, 0x02020009, 0x0A020009, |
233 | | 0x02020401, 0x0A020401, 0x02020409, 0x0A020409, }, |
234 | | { // for D bits (numbered as per FIPS 46) 16 17 18 19 20 21 |
235 | | 0x00000000, 0x00000100, 0x00080000, 0x00080100, 0x01000000, |
236 | | 0x01000100, 0x01080000, 0x01080100, 0x00000010, 0x00000110, |
237 | | 0x00080010, 0x00080110, 0x01000010, 0x01000110, 0x01080010, |
238 | | 0x01080110, 0x00200000, 0x00200100, 0x00280000, 0x00280100, |
239 | | 0x01200000, 0x01200100, 0x01280000, 0x01280100, 0x00200010, |
240 | | 0x00200110, 0x00280010, 0x00280110, 0x01200010, 0x01200110, |
241 | | 0x01280010, 0x01280110, 0x00000200, 0x00000300, 0x00080200, |
242 | | 0x00080300, 0x01000200, 0x01000300, 0x01080200, 0x01080300, |
243 | | 0x00000210, 0x00000310, 0x00080210, 0x00080310, 0x01000210, |
244 | | 0x01000310, 0x01080210, 0x01080310, 0x00200200, 0x00200300, |
245 | | 0x00280200, 0x00280300, 0x01200200, 0x01200300, 0x01280200, |
246 | | 0x01280300, 0x00200210, 0x00200310, 0x00280210, 0x00280310, |
247 | | 0x01200210, 0x01200310, 0x01280210, 0x01280310, }, |
248 | | { // for D bits (numbered as per FIPS 46) 22 23 24 25 27 28 |
249 | | 0x00000000, 0x04000000, 0x00040000, 0x04040000, 0x00000002, |
250 | | 0x04000002, 0x00040002, 0x04040002, 0x00002000, 0x04002000, |
251 | | 0x00042000, 0x04042000, 0x00002002, 0x04002002, 0x00042002, |
252 | | 0x04042002, 0x00000020, 0x04000020, 0x00040020, 0x04040020, |
253 | | 0x00000022, 0x04000022, 0x00040022, 0x04040022, 0x00002020, |
254 | | 0x04002020, 0x00042020, 0x04042020, 0x00002022, 0x04002022, |
255 | | 0x00042022, 0x04042022, 0x00000800, 0x04000800, 0x00040800, |
256 | | 0x04040800, 0x00000802, 0x04000802, 0x00040802, 0x04040802, |
257 | | 0x00002800, 0x04002800, 0x00042800, 0x04042800, 0x00002802, |
258 | | 0x04002802, 0x00042802, 0x04042802, 0x00000820, 0x04000820, |
259 | | 0x00040820, 0x04040820, 0x00000822, 0x04000822, 0x00040822, |
260 | | 0x04040822, 0x00002820, 0x04002820, 0x00042820, 0x04042820, |
261 | | 0x00002822, 0x04002822, 0x00042822, 0x04042822, }}; |
262 | | |
263 | | static const uint32_t DES_SPtrans[8][64] = { |
264 | | { // nibble 0 |
265 | | 0x02080800, 0x00080000, 0x02000002, 0x02080802, 0x02000000, |
266 | | 0x00080802, 0x00080002, 0x02000002, 0x00080802, 0x02080800, |
267 | | 0x02080000, 0x00000802, 0x02000802, 0x02000000, 0x00000000, |
268 | | 0x00080002, 0x00080000, 0x00000002, 0x02000800, 0x00080800, |
269 | | 0x02080802, 0x02080000, 0x00000802, 0x02000800, 0x00000002, |
270 | | 0x00000800, 0x00080800, 0x02080002, 0x00000800, 0x02000802, |
271 | | 0x02080002, 0x00000000, 0x00000000, 0x02080802, 0x02000800, |
272 | | 0x00080002, 0x02080800, 0x00080000, 0x00000802, 0x02000800, |
273 | | 0x02080002, 0x00000800, 0x00080800, 0x02000002, 0x00080802, |
274 | | 0x00000002, 0x02000002, 0x02080000, 0x02080802, 0x00080800, |
275 | | 0x02080000, 0x02000802, 0x02000000, 0x00000802, 0x00080002, |
276 | | 0x00000000, 0x00080000, 0x02000000, 0x02000802, 0x02080800, |
277 | | 0x00000002, 0x02080002, 0x00000800, 0x00080802, }, |
278 | | { // nibble 1 |
279 | | 0x40108010, 0x00000000, 0x00108000, 0x40100000, 0x40000010, |
280 | | 0x00008010, 0x40008000, 0x00108000, 0x00008000, 0x40100010, |
281 | | 0x00000010, 0x40008000, 0x00100010, 0x40108000, 0x40100000, |
282 | | 0x00000010, 0x00100000, 0x40008010, 0x40100010, 0x00008000, |
283 | | 0x00108010, 0x40000000, 0x00000000, 0x00100010, 0x40008010, |
284 | | 0x00108010, 0x40108000, 0x40000010, 0x40000000, 0x00100000, |
285 | | 0x00008010, 0x40108010, 0x00100010, 0x40108000, 0x40008000, |
286 | | 0x00108010, 0x40108010, 0x00100010, 0x40000010, 0x00000000, |
287 | | 0x40000000, 0x00008010, 0x00100000, 0x40100010, 0x00008000, |
288 | | 0x40000000, 0x00108010, 0x40008010, 0x40108000, 0x00008000, |
289 | | 0x00000000, 0x40000010, 0x00000010, 0x40108010, 0x00108000, |
290 | | 0x40100000, 0x40100010, 0x00100000, 0x00008010, 0x40008000, |
291 | | 0x40008010, 0x00000010, 0x40100000, 0x00108000, }, |
292 | | { // nibble 2 |
293 | | 0x04000001, 0x04040100, 0x00000100, 0x04000101, 0x00040001, |
294 | | 0x04000000, 0x04000101, 0x00040100, 0x04000100, 0x00040000, |
295 | | 0x04040000, 0x00000001, 0x04040101, 0x00000101, 0x00000001, |
296 | | 0x04040001, 0x00000000, 0x00040001, 0x04040100, 0x00000100, |
297 | | 0x00000101, 0x04040101, 0x00040000, 0x04000001, 0x04040001, |
298 | | 0x04000100, 0x00040101, 0x04040000, 0x00040100, 0x00000000, |
299 | | 0x04000000, 0x00040101, 0x04040100, 0x00000100, 0x00000001, |
300 | | 0x00040000, 0x00000101, 0x00040001, 0x04040000, 0x04000101, |
301 | | 0x00000000, 0x04040100, 0x00040100, 0x04040001, 0x00040001, |
302 | | 0x04000000, 0x04040101, 0x00000001, 0x00040101, 0x04000001, |
303 | | 0x04000000, 0x04040101, 0x00040000, 0x04000100, 0x04000101, |
304 | | 0x00040100, 0x04000100, 0x00000000, 0x04040001, 0x00000101, |
305 | | 0x04000001, 0x00040101, 0x00000100, 0x04040000, }, |
306 | | { // nibble 3 |
307 | | 0x00401008, 0x10001000, 0x00000008, 0x10401008, 0x00000000, |
308 | | 0x10400000, 0x10001008, 0x00400008, 0x10401000, 0x10000008, |
309 | | 0x10000000, 0x00001008, 0x10000008, 0x00401008, 0x00400000, |
310 | | 0x10000000, 0x10400008, 0x00401000, 0x00001000, 0x00000008, |
311 | | 0x00401000, 0x10001008, 0x10400000, 0x00001000, 0x00001008, |
312 | | 0x00000000, 0x00400008, 0x10401000, 0x10001000, 0x10400008, |
313 | | 0x10401008, 0x00400000, 0x10400008, 0x00001008, 0x00400000, |
314 | | 0x10000008, 0x00401000, 0x10001000, 0x00000008, 0x10400000, |
315 | | 0x10001008, 0x00000000, 0x00001000, 0x00400008, 0x00000000, |
316 | | 0x10400008, 0x10401000, 0x00001000, 0x10000000, 0x10401008, |
317 | | 0x00401008, 0x00400000, 0x10401008, 0x00000008, 0x10001000, |
318 | | 0x00401008, 0x00400008, 0x00401000, 0x10400000, 0x10001008, |
319 | | 0x00001008, 0x10000000, 0x10000008, 0x10401000, }, |
320 | | { // nibble 4 |
321 | | 0x08000000, 0x00010000, 0x00000400, 0x08010420, 0x08010020, |
322 | | 0x08000400, 0x00010420, 0x08010000, 0x00010000, 0x00000020, |
323 | | 0x08000020, 0x00010400, 0x08000420, 0x08010020, 0x08010400, |
324 | | 0x00000000, 0x00010400, 0x08000000, 0x00010020, 0x00000420, |
325 | | 0x08000400, 0x00010420, 0x00000000, 0x08000020, 0x00000020, |
326 | | 0x08000420, 0x08010420, 0x00010020, 0x08010000, 0x00000400, |
327 | | 0x00000420, 0x08010400, 0x08010400, 0x08000420, 0x00010020, |
328 | | 0x08010000, 0x00010000, 0x00000020, 0x08000020, 0x08000400, |
329 | | 0x08000000, 0x00010400, 0x08010420, 0x00000000, 0x00010420, |
330 | | 0x08000000, 0x00000400, 0x00010020, 0x08000420, 0x00000400, |
331 | | 0x00000000, 0x08010420, 0x08010020, 0x08010400, 0x00000420, |
332 | | 0x00010000, 0x00010400, 0x08010020, 0x08000400, 0x00000420, |
333 | | 0x00000020, 0x00010420, 0x08010000, 0x08000020, }, |
334 | | { // nibble 5 |
335 | | 0x80000040, 0x00200040, 0x00000000, 0x80202000, 0x00200040, |
336 | | 0x00002000, 0x80002040, 0x00200000, 0x00002040, 0x80202040, |
337 | | 0x00202000, 0x80000000, 0x80002000, 0x80000040, 0x80200000, |
338 | | 0x00202040, 0x00200000, 0x80002040, 0x80200040, 0x00000000, |
339 | | 0x00002000, 0x00000040, 0x80202000, 0x80200040, 0x80202040, |
340 | | 0x80200000, 0x80000000, 0x00002040, 0x00000040, 0x00202000, |
341 | | 0x00202040, 0x80002000, 0x00002040, 0x80000000, 0x80002000, |
342 | | 0x00202040, 0x80202000, 0x00200040, 0x00000000, 0x80002000, |
343 | | 0x80000000, 0x00002000, 0x80200040, 0x00200000, 0x00200040, |
344 | | 0x80202040, 0x00202000, 0x00000040, 0x80202040, 0x00202000, |
345 | | 0x00200000, 0x80002040, 0x80000040, 0x80200000, 0x00202040, |
346 | | 0x00000000, 0x00002000, 0x80000040, 0x80002040, 0x80202000, |
347 | | 0x80200000, 0x00002040, 0x00000040, 0x80200040, }, |
348 | | { // nibble 6 |
349 | | 0x00004000, 0x00000200, 0x01000200, 0x01000004, 0x01004204, |
350 | | 0x00004004, 0x00004200, 0x00000000, 0x01000000, 0x01000204, |
351 | | 0x00000204, 0x01004000, 0x00000004, 0x01004200, 0x01004000, |
352 | | 0x00000204, 0x01000204, 0x00004000, 0x00004004, 0x01004204, |
353 | | 0x00000000, 0x01000200, 0x01000004, 0x00004200, 0x01004004, |
354 | | 0x00004204, 0x01004200, 0x00000004, 0x00004204, 0x01004004, |
355 | | 0x00000200, 0x01000000, 0x00004204, 0x01004000, 0x01004004, |
356 | | 0x00000204, 0x00004000, 0x00000200, 0x01000000, 0x01004004, |
357 | | 0x01000204, 0x00004204, 0x00004200, 0x00000000, 0x00000200, |
358 | | 0x01000004, 0x00000004, 0x01000200, 0x00000000, 0x01000204, |
359 | | 0x01000200, 0x00004200, 0x00000204, 0x00004000, 0x01004204, |
360 | | 0x01000000, 0x01004200, 0x00000004, 0x00004004, 0x01004204, |
361 | | 0x01000004, 0x01004200, 0x01004000, 0x00004004, }, |
362 | | { // nibble 7 |
363 | | 0x20800080, 0x20820000, 0x00020080, 0x00000000, 0x20020000, |
364 | | 0x00800080, 0x20800000, 0x20820080, 0x00000080, 0x20000000, |
365 | | 0x00820000, 0x00020080, 0x00820080, 0x20020080, 0x20000080, |
366 | | 0x20800000, 0x00020000, 0x00820080, 0x00800080, 0x20020000, |
367 | | 0x20820080, 0x20000080, 0x00000000, 0x00820000, 0x20000000, |
368 | | 0x00800000, 0x20020080, 0x20800080, 0x00800000, 0x00020000, |
369 | | 0x20820000, 0x00000080, 0x00800000, 0x00020000, 0x20000080, |
370 | | 0x20820080, 0x00020080, 0x20000000, 0x00000000, 0x00820000, |
371 | | 0x20800080, 0x20020080, 0x20020000, 0x00800080, 0x20820000, |
372 | | 0x00000080, 0x00800080, 0x20020000, 0x20820080, 0x00800000, |
373 | | 0x20800000, 0x20000080, 0x00820000, 0x00020080, 0x20020080, |
374 | | 0x20800000, 0x00000080, 0x20820000, 0x00820080, 0x00000000, |
375 | | 0x20000000, 0x20800080, 0x00020000, 0x00820080, }}; |
376 | | |
377 | | #define HPERM_OP(a, t, n, m) \ |
378 | 662 | ((t) = ((((a) << (16 - (n))) ^ (a)) & (m)), \ |
379 | 662 | (a) = (a) ^ (t) ^ ((t) >> (16 - (n)))) |
380 | | |
381 | 0 | void DES_set_key(const DES_cblock *key, DES_key_schedule *schedule) { |
382 | 0 | DES_set_key_ex(key->bytes, schedule); |
383 | 0 | } |
384 | | |
385 | 331 | void DES_set_key_ex(const uint8_t key[8], DES_key_schedule *schedule) { |
386 | 331 | static const int shifts2[16] = {0, 0, 1, 1, 1, 1, 1, 1, |
387 | 331 | 0, 1, 1, 1, 1, 1, 1, 0}; |
388 | 331 | uint32_t c, d, t, s, t2; |
389 | 331 | const uint8_t *in; |
390 | 331 | int i; |
391 | | |
392 | 331 | in = key; |
393 | | |
394 | 331 | c2l(in, c); |
395 | 331 | c2l(in, d); |
396 | | |
397 | | // do PC1 in 47 simple operations :-) |
398 | | // Thanks to John Fletcher (john_fletcher@lccmail.ocf.llnl.gov) |
399 | | // for the inspiration. :-) |
400 | 331 | PERM_OP(d, c, t, 4, 0x0f0f0f0f); |
401 | 331 | HPERM_OP(c, t, -2, 0xcccc0000); |
402 | 331 | HPERM_OP(d, t, -2, 0xcccc0000); |
403 | 331 | PERM_OP(d, c, t, 1, 0x55555555); |
404 | 331 | PERM_OP(c, d, t, 8, 0x00ff00ff); |
405 | 331 | PERM_OP(d, c, t, 1, 0x55555555); |
406 | 331 | d = (((d & 0x000000ff) << 16) | (d & 0x0000ff00) | |
407 | 331 | ((d & 0x00ff0000) >> 16) | ((c & 0xf0000000) >> 4)); |
408 | 331 | c &= 0x0fffffff; |
409 | | |
410 | 5.62k | for (i = 0; i < ITERATIONS; i++) { |
411 | 5.29k | if (shifts2[i]) { |
412 | 3.97k | c = ((c >> 2) | (c << 26)); |
413 | 3.97k | d = ((d >> 2) | (d << 26)); |
414 | 3.97k | } else { |
415 | 1.32k | c = ((c >> 1) | (c << 27)); |
416 | 1.32k | d = ((d >> 1) | (d << 27)); |
417 | 1.32k | } |
418 | 5.29k | c &= 0x0fffffff; |
419 | 5.29k | d &= 0x0fffffff; |
420 | | // could be a few less shifts but I am to lazy at this |
421 | | // point in time to investigate |
422 | 5.29k | s = des_skb[0][(c) & 0x3f] | |
423 | 5.29k | des_skb[1][((c >> 6) & 0x03) | ((c >> 7) & 0x3c)] | |
424 | 5.29k | des_skb[2][((c >> 13) & 0x0f) | ((c >> 14) & 0x30)] | |
425 | 5.29k | des_skb[3][((c >> 20) & 0x01) | ((c >> 21) & 0x06) | |
426 | 5.29k | ((c >> 22) & 0x38)]; |
427 | 5.29k | t = des_skb[4][(d) & 0x3f] | |
428 | 5.29k | des_skb[5][((d >> 7) & 0x03) | ((d >> 8) & 0x3c)] | |
429 | 5.29k | des_skb[6][(d >> 15) & 0x3f] | |
430 | 5.29k | des_skb[7][((d >> 21) & 0x0f) | ((d >> 22) & 0x30)]; |
431 | | |
432 | | // table contained 0213 4657 |
433 | 5.29k | t2 = ((t << 16) | (s & 0x0000ffff)) & 0xffffffff; |
434 | 5.29k | schedule->subkeys[i][0] = CRYPTO_rotr_u32(t2, 30); |
435 | | |
436 | 5.29k | t2 = ((s >> 16) | (t & 0xffff0000)); |
437 | 5.29k | schedule->subkeys[i][1] = CRYPTO_rotr_u32(t2, 26); |
438 | 5.29k | } |
439 | 331 | } |
440 | | |
441 | | static const uint8_t kOddParity[256] = { |
442 | | 1, 1, 2, 2, 4, 4, 7, 7, 8, 8, 11, 11, 13, 13, 14, |
443 | | 14, 16, 16, 19, 19, 21, 21, 22, 22, 25, 25, 26, 26, 28, 28, |
444 | | 31, 31, 32, 32, 35, 35, 37, 37, 38, 38, 41, 41, 42, 42, 44, |
445 | | 44, 47, 47, 49, 49, 50, 50, 52, 52, 55, 55, 56, 56, 59, 59, |
446 | | 61, 61, 62, 62, 64, 64, 67, 67, 69, 69, 70, 70, 73, 73, 74, |
447 | | 74, 76, 76, 79, 79, 81, 81, 82, 82, 84, 84, 87, 87, 88, 88, |
448 | | 91, 91, 93, 93, 94, 94, 97, 97, 98, 98, 100, 100, 103, 103, 104, |
449 | | 104, 107, 107, 109, 109, 110, 110, 112, 112, 115, 115, 117, 117, 118, 118, |
450 | | 121, 121, 122, 122, 124, 124, 127, 127, 128, 128, 131, 131, 133, 133, 134, |
451 | | 134, 137, 137, 138, 138, 140, 140, 143, 143, 145, 145, 146, 146, 148, 148, |
452 | | 151, 151, 152, 152, 155, 155, 157, 157, 158, 158, 161, 161, 162, 162, 164, |
453 | | 164, 167, 167, 168, 168, 171, 171, 173, 173, 174, 174, 176, 176, 179, 179, |
454 | | 181, 181, 182, 182, 185, 185, 186, 186, 188, 188, 191, 191, 193, 193, 194, |
455 | | 194, 196, 196, 199, 199, 200, 200, 203, 203, 205, 205, 206, 206, 208, 208, |
456 | | 211, 211, 213, 213, 214, 214, 217, 217, 218, 218, 220, 220, 223, 223, 224, |
457 | | 224, 227, 227, 229, 229, 230, 230, 233, 233, 234, 234, 236, 236, 239, 239, |
458 | | 241, 241, 242, 242, 244, 244, 247, 247, 248, 248, 251, 251, 253, 253, 254, |
459 | | 254 |
460 | | }; |
461 | | |
462 | 0 | void DES_set_odd_parity(DES_cblock *key) { |
463 | 0 | unsigned i; |
464 | |
|
465 | 0 | for (i = 0; i < DES_KEY_SZ; i++) { |
466 | 0 | key->bytes[i] = kOddParity[key->bytes[i]]; |
467 | 0 | } |
468 | 0 | } |
469 | | |
470 | | static void DES_encrypt1(uint32_t data[2], const DES_key_schedule *ks, |
471 | 2 | int enc) { |
472 | 2 | uint32_t l, r, t, u; |
473 | | |
474 | 2 | r = data[0]; |
475 | 2 | l = data[1]; |
476 | | |
477 | 2 | IP(r, l); |
478 | | // Things have been modified so that the initial rotate is done outside |
479 | | // the loop. This required the DES_SPtrans values in sp.h to be |
480 | | // rotated 1 bit to the right. One perl script later and things have a |
481 | | // 5% speed up on a sparc2. Thanks to Richard Outerbridge |
482 | | // <71755.204@CompuServe.COM> for pointing this out. |
483 | | // clear the top bits on machines with 8byte longs |
484 | | // shift left by 2 |
485 | 2 | r = CRYPTO_rotr_u32(r, 29); |
486 | 2 | l = CRYPTO_rotr_u32(l, 29); |
487 | | |
488 | | // I don't know if it is worth the effort of loop unrolling the |
489 | | // inner loop |
490 | 2 | if (enc) { |
491 | 0 | D_ENCRYPT(ks, l, r, 0); |
492 | 0 | D_ENCRYPT(ks, r, l, 1); |
493 | 0 | D_ENCRYPT(ks, l, r, 2); |
494 | 0 | D_ENCRYPT(ks, r, l, 3); |
495 | 0 | D_ENCRYPT(ks, l, r, 4); |
496 | 0 | D_ENCRYPT(ks, r, l, 5); |
497 | 0 | D_ENCRYPT(ks, l, r, 6); |
498 | 0 | D_ENCRYPT(ks, r, l, 7); |
499 | 0 | D_ENCRYPT(ks, l, r, 8); |
500 | 0 | D_ENCRYPT(ks, r, l, 9); |
501 | 0 | D_ENCRYPT(ks, l, r, 10); |
502 | 0 | D_ENCRYPT(ks, r, l, 11); |
503 | 0 | D_ENCRYPT(ks, l, r, 12); |
504 | 0 | D_ENCRYPT(ks, r, l, 13); |
505 | 0 | D_ENCRYPT(ks, l, r, 14); |
506 | 0 | D_ENCRYPT(ks, r, l, 15); |
507 | 2 | } else { |
508 | 2 | D_ENCRYPT(ks, l, r, 15); |
509 | 2 | D_ENCRYPT(ks, r, l, 14); |
510 | 2 | D_ENCRYPT(ks, l, r, 13); |
511 | 2 | D_ENCRYPT(ks, r, l, 12); |
512 | 2 | D_ENCRYPT(ks, l, r, 11); |
513 | 2 | D_ENCRYPT(ks, r, l, 10); |
514 | 2 | D_ENCRYPT(ks, l, r, 9); |
515 | 2 | D_ENCRYPT(ks, r, l, 8); |
516 | 2 | D_ENCRYPT(ks, l, r, 7); |
517 | 2 | D_ENCRYPT(ks, r, l, 6); |
518 | 2 | D_ENCRYPT(ks, l, r, 5); |
519 | 2 | D_ENCRYPT(ks, r, l, 4); |
520 | 2 | D_ENCRYPT(ks, l, r, 3); |
521 | 2 | D_ENCRYPT(ks, r, l, 2); |
522 | 2 | D_ENCRYPT(ks, l, r, 1); |
523 | 2 | D_ENCRYPT(ks, r, l, 0); |
524 | 2 | } |
525 | | |
526 | | // rotate and clear the top bits on machines with 8byte longs |
527 | 2 | l = CRYPTO_rotr_u32(l, 3); |
528 | 2 | r = CRYPTO_rotr_u32(r, 3); |
529 | | |
530 | 2 | FP(r, l); |
531 | 2 | data[0] = l; |
532 | 2 | data[1] = r; |
533 | 2 | } |
534 | | |
535 | | static void DES_encrypt2(uint32_t data[2], const DES_key_schedule *ks, |
536 | 6.48k | int enc) { |
537 | 6.48k | uint32_t l, r, t, u; |
538 | | |
539 | 6.48k | r = data[0]; |
540 | 6.48k | l = data[1]; |
541 | | |
542 | | // Things have been modified so that the initial rotate is done outside the |
543 | | // loop. This required the DES_SPtrans values in sp.h to be rotated 1 bit to |
544 | | // the right. One perl script later and things have a 5% speed up on a |
545 | | // sparc2. Thanks to Richard Outerbridge <71755.204@CompuServe.COM> for |
546 | | // pointing this out. |
547 | | // clear the top bits on machines with 8byte longs |
548 | 6.48k | r = CRYPTO_rotr_u32(r, 29); |
549 | 6.48k | l = CRYPTO_rotr_u32(l, 29); |
550 | | |
551 | | // I don't know if it is worth the effort of loop unrolling the |
552 | | // inner loop |
553 | 6.48k | if (enc) { |
554 | 4.17k | D_ENCRYPT(ks, l, r, 0); |
555 | 4.17k | D_ENCRYPT(ks, r, l, 1); |
556 | 4.17k | D_ENCRYPT(ks, l, r, 2); |
557 | 4.17k | D_ENCRYPT(ks, r, l, 3); |
558 | 4.17k | D_ENCRYPT(ks, l, r, 4); |
559 | 4.17k | D_ENCRYPT(ks, r, l, 5); |
560 | 4.17k | D_ENCRYPT(ks, l, r, 6); |
561 | 4.17k | D_ENCRYPT(ks, r, l, 7); |
562 | 4.17k | D_ENCRYPT(ks, l, r, 8); |
563 | 4.17k | D_ENCRYPT(ks, r, l, 9); |
564 | 4.17k | D_ENCRYPT(ks, l, r, 10); |
565 | 4.17k | D_ENCRYPT(ks, r, l, 11); |
566 | 4.17k | D_ENCRYPT(ks, l, r, 12); |
567 | 4.17k | D_ENCRYPT(ks, r, l, 13); |
568 | 4.17k | D_ENCRYPT(ks, l, r, 14); |
569 | 4.17k | D_ENCRYPT(ks, r, l, 15); |
570 | 4.17k | } else { |
571 | 2.30k | D_ENCRYPT(ks, l, r, 15); |
572 | 2.30k | D_ENCRYPT(ks, r, l, 14); |
573 | 2.30k | D_ENCRYPT(ks, l, r, 13); |
574 | 2.30k | D_ENCRYPT(ks, r, l, 12); |
575 | 2.30k | D_ENCRYPT(ks, l, r, 11); |
576 | 2.30k | D_ENCRYPT(ks, r, l, 10); |
577 | 2.30k | D_ENCRYPT(ks, l, r, 9); |
578 | 2.30k | D_ENCRYPT(ks, r, l, 8); |
579 | 2.30k | D_ENCRYPT(ks, l, r, 7); |
580 | 2.30k | D_ENCRYPT(ks, r, l, 6); |
581 | 2.30k | D_ENCRYPT(ks, l, r, 5); |
582 | 2.30k | D_ENCRYPT(ks, r, l, 4); |
583 | 2.30k | D_ENCRYPT(ks, l, r, 3); |
584 | 2.30k | D_ENCRYPT(ks, r, l, 2); |
585 | 2.30k | D_ENCRYPT(ks, l, r, 1); |
586 | 2.30k | D_ENCRYPT(ks, r, l, 0); |
587 | 2.30k | } |
588 | | // rotate and clear the top bits on machines with 8byte longs |
589 | 6.48k | data[0] = CRYPTO_rotr_u32(l, 3); |
590 | 6.48k | data[1] = CRYPTO_rotr_u32(r, 3); |
591 | 6.48k | } |
592 | | |
593 | | void DES_encrypt3(uint32_t data[2], const DES_key_schedule *ks1, |
594 | 2.01k | const DES_key_schedule *ks2, const DES_key_schedule *ks3) { |
595 | 2.01k | uint32_t l, r; |
596 | | |
597 | 2.01k | l = data[0]; |
598 | 2.01k | r = data[1]; |
599 | 2.01k | IP(l, r); |
600 | 2.01k | data[0] = l; |
601 | 2.01k | data[1] = r; |
602 | 2.01k | DES_encrypt2(data, ks1, DES_ENCRYPT); |
603 | 2.01k | DES_encrypt2(data, ks2, DES_DECRYPT); |
604 | 2.01k | DES_encrypt2(data, ks3, DES_ENCRYPT); |
605 | 2.01k | l = data[0]; |
606 | 2.01k | r = data[1]; |
607 | 2.01k | FP(r, l); |
608 | 2.01k | data[0] = l; |
609 | 2.01k | data[1] = r; |
610 | 2.01k | } |
611 | | |
612 | | void DES_decrypt3(uint32_t data[2], const DES_key_schedule *ks1, |
613 | 144 | const DES_key_schedule *ks2, const DES_key_schedule *ks3) { |
614 | 144 | uint32_t l, r; |
615 | | |
616 | 144 | l = data[0]; |
617 | 144 | r = data[1]; |
618 | 144 | IP(l, r); |
619 | 144 | data[0] = l; |
620 | 144 | data[1] = r; |
621 | 144 | DES_encrypt2(data, ks3, DES_DECRYPT); |
622 | 144 | DES_encrypt2(data, ks2, DES_ENCRYPT); |
623 | 144 | DES_encrypt2(data, ks1, DES_DECRYPT); |
624 | 144 | l = data[0]; |
625 | 144 | r = data[1]; |
626 | 144 | FP(r, l); |
627 | 144 | data[0] = l; |
628 | 144 | data[1] = r; |
629 | 144 | } |
630 | | |
631 | | void DES_ecb_encrypt(const DES_cblock *in_block, DES_cblock *out_block, |
632 | 0 | const DES_key_schedule *schedule, int is_encrypt) { |
633 | 0 | DES_ecb_encrypt_ex(in_block->bytes, out_block->bytes, schedule, is_encrypt); |
634 | 0 | } |
635 | | |
636 | | void DES_ecb_encrypt_ex(const uint8_t in[8], uint8_t out[8], |
637 | 0 | const DES_key_schedule *schedule, int is_encrypt) { |
638 | 0 | uint32_t ll[2]; |
639 | 0 | ll[0] = CRYPTO_load_u32_le(in); |
640 | 0 | ll[1] = CRYPTO_load_u32_le(in + 4); |
641 | 0 | DES_encrypt1(ll, schedule, is_encrypt); |
642 | 0 | CRYPTO_store_u32_le(out, ll[0]); |
643 | 0 | CRYPTO_store_u32_le(out + 4, ll[1]); |
644 | 0 | } |
645 | | |
646 | | void DES_ncbc_encrypt(const uint8_t *in, uint8_t *out, size_t len, |
647 | | const DES_key_schedule *schedule, DES_cblock *ivec, |
648 | 0 | int enc) { |
649 | 0 | DES_ncbc_encrypt_ex(in, out, len, schedule, ivec->bytes, enc); |
650 | 0 | } |
651 | | |
652 | | void DES_ncbc_encrypt_ex(const uint8_t *in, uint8_t *out, size_t len, |
653 | | const DES_key_schedule *schedule, uint8_t ivec[8], |
654 | 2 | int enc) { |
655 | 2 | uint32_t tin0, tin1; |
656 | 2 | uint32_t tout0, tout1, xor0, xor1; |
657 | 2 | uint32_t tin[2]; |
658 | 2 | unsigned char *iv; |
659 | | |
660 | 2 | iv = ivec; |
661 | | |
662 | 2 | if (enc) { |
663 | 0 | c2l(iv, tout0); |
664 | 0 | c2l(iv, tout1); |
665 | 0 | for (; len >= 8; len -= 8) { |
666 | 0 | c2l(in, tin0); |
667 | 0 | c2l(in, tin1); |
668 | 0 | tin0 ^= tout0; |
669 | 0 | tin[0] = tin0; |
670 | 0 | tin1 ^= tout1; |
671 | 0 | tin[1] = tin1; |
672 | 0 | DES_encrypt1(tin, schedule, DES_ENCRYPT); |
673 | 0 | tout0 = tin[0]; |
674 | 0 | l2c(tout0, out); |
675 | 0 | tout1 = tin[1]; |
676 | 0 | l2c(tout1, out); |
677 | 0 | } |
678 | 0 | if (len != 0) { |
679 | 0 | c2ln(in, tin0, tin1, len); |
680 | 0 | tin0 ^= tout0; |
681 | 0 | tin[0] = tin0; |
682 | 0 | tin1 ^= tout1; |
683 | 0 | tin[1] = tin1; |
684 | 0 | DES_encrypt1(tin, schedule, DES_ENCRYPT); |
685 | 0 | tout0 = tin[0]; |
686 | 0 | l2c(tout0, out); |
687 | 0 | tout1 = tin[1]; |
688 | 0 | l2c(tout1, out); |
689 | 0 | } |
690 | 0 | iv = ivec; |
691 | 0 | l2c(tout0, iv); |
692 | 0 | l2c(tout1, iv); |
693 | 2 | } else { |
694 | 2 | c2l(iv, xor0); |
695 | 2 | c2l(iv, xor1); |
696 | 4 | for (; len >= 8; len -= 8) { |
697 | 2 | c2l(in, tin0); |
698 | 2 | tin[0] = tin0; |
699 | 2 | c2l(in, tin1); |
700 | 2 | tin[1] = tin1; |
701 | 2 | DES_encrypt1(tin, schedule, DES_DECRYPT); |
702 | 2 | tout0 = tin[0] ^ xor0; |
703 | 2 | tout1 = tin[1] ^ xor1; |
704 | 2 | l2c(tout0, out); |
705 | 2 | l2c(tout1, out); |
706 | 2 | xor0 = tin0; |
707 | 2 | xor1 = tin1; |
708 | 2 | } |
709 | 2 | if (len != 0) { |
710 | 0 | c2l(in, tin0); |
711 | 0 | tin[0] = tin0; |
712 | 0 | c2l(in, tin1); |
713 | 0 | tin[1] = tin1; |
714 | 0 | DES_encrypt1(tin, schedule, DES_DECRYPT); |
715 | 0 | tout0 = tin[0] ^ xor0; |
716 | 0 | tout1 = tin[1] ^ xor1; |
717 | 0 | l2cn(tout0, tout1, out, len); |
718 | 0 | xor0 = tin0; |
719 | 0 | xor1 = tin1; |
720 | 0 | } |
721 | 2 | iv = ivec; |
722 | 2 | l2c(xor0, iv); |
723 | 2 | l2c(xor1, iv); |
724 | 2 | } |
725 | 2 | tin[0] = tin[1] = 0; |
726 | 2 | } |
727 | | |
728 | | void DES_ecb3_encrypt(const DES_cblock *input, DES_cblock *output, |
729 | | const DES_key_schedule *ks1, const DES_key_schedule *ks2, |
730 | | const DES_key_schedule *ks3, int enc) { |
731 | | DES_ecb3_encrypt_ex(input->bytes, output->bytes, ks1, ks2, ks3, enc); |
732 | | } |
733 | | |
734 | | void DES_ecb3_encrypt_ex(const uint8_t in[8], uint8_t out[8], |
735 | | const DES_key_schedule *ks1, |
736 | | const DES_key_schedule *ks2, |
737 | 0 | const DES_key_schedule *ks3, int enc) { |
738 | 0 | uint32_t ll[2]; |
739 | 0 | ll[0] = CRYPTO_load_u32_le(in); |
740 | 0 | ll[1] = CRYPTO_load_u32_le(in + 4); |
741 | 0 | if (enc) { |
742 | 0 | DES_encrypt3(ll, ks1, ks2, ks3); |
743 | 0 | } else { |
744 | 0 | DES_decrypt3(ll, ks1, ks2, ks3); |
745 | 0 | } |
746 | 0 | CRYPTO_store_u32_le(out, ll[0]); |
747 | 0 | CRYPTO_store_u32_le(out + 4, ll[1]); |
748 | 0 | } |
749 | | |
750 | | void DES_ede3_cbc_encrypt(const uint8_t *in, uint8_t *out, size_t len, |
751 | | const DES_key_schedule *ks1, |
752 | | const DES_key_schedule *ks2, |
753 | | const DES_key_schedule *ks3, DES_cblock *ivec, |
754 | 0 | int enc) { |
755 | 0 | DES_ede3_cbc_encrypt_ex(in, out, len, ks1, ks2, ks3, ivec->bytes, enc); |
756 | 0 | } |
757 | | |
758 | | void DES_ede3_cbc_encrypt_ex(const uint8_t *in, uint8_t *out, size_t len, |
759 | | const DES_key_schedule *ks1, |
760 | | const DES_key_schedule *ks2, |
761 | | const DES_key_schedule *ks3, uint8_t ivec[8], |
762 | 2.14k | int enc) { |
763 | 2.14k | uint32_t tin0, tin1; |
764 | 2.14k | uint32_t tout0, tout1, xor0, xor1; |
765 | 2.14k | uint32_t tin[2]; |
766 | 2.14k | uint8_t *iv; |
767 | | |
768 | 2.14k | iv = ivec; |
769 | | |
770 | 2.14k | if (enc) { |
771 | 2.01k | c2l(iv, tout0); |
772 | 2.01k | c2l(iv, tout1); |
773 | 4.03k | for (; len >= 8; len -= 8) { |
774 | 2.01k | c2l(in, tin0); |
775 | 2.01k | c2l(in, tin1); |
776 | 2.01k | tin0 ^= tout0; |
777 | 2.01k | tin1 ^= tout1; |
778 | | |
779 | 2.01k | tin[0] = tin0; |
780 | 2.01k | tin[1] = tin1; |
781 | 2.01k | DES_encrypt3(tin, ks1, ks2, ks3); |
782 | 2.01k | tout0 = tin[0]; |
783 | 2.01k | tout1 = tin[1]; |
784 | | |
785 | 2.01k | l2c(tout0, out); |
786 | 2.01k | l2c(tout1, out); |
787 | 2.01k | } |
788 | 2.01k | if (len != 0) { |
789 | 0 | c2ln(in, tin0, tin1, len); |
790 | 0 | tin0 ^= tout0; |
791 | 0 | tin1 ^= tout1; |
792 | |
|
793 | 0 | tin[0] = tin0; |
794 | 0 | tin[1] = tin1; |
795 | 0 | DES_encrypt3(tin, ks1, ks2, ks3); |
796 | 0 | tout0 = tin[0]; |
797 | 0 | tout1 = tin[1]; |
798 | |
|
799 | 0 | l2c(tout0, out); |
800 | 0 | l2c(tout1, out); |
801 | 0 | } |
802 | 2.01k | iv = ivec; |
803 | 2.01k | l2c(tout0, iv); |
804 | 2.01k | l2c(tout1, iv); |
805 | 2.01k | } else { |
806 | 123 | uint32_t t0, t1; |
807 | | |
808 | 123 | c2l(iv, xor0); |
809 | 123 | c2l(iv, xor1); |
810 | 267 | for (; len >= 8; len -= 8) { |
811 | 144 | c2l(in, tin0); |
812 | 144 | c2l(in, tin1); |
813 | | |
814 | 144 | t0 = tin0; |
815 | 144 | t1 = tin1; |
816 | | |
817 | 144 | tin[0] = tin0; |
818 | 144 | tin[1] = tin1; |
819 | 144 | DES_decrypt3(tin, ks1, ks2, ks3); |
820 | 144 | tout0 = tin[0]; |
821 | 144 | tout1 = tin[1]; |
822 | | |
823 | 144 | tout0 ^= xor0; |
824 | 144 | tout1 ^= xor1; |
825 | 144 | l2c(tout0, out); |
826 | 144 | l2c(tout1, out); |
827 | 144 | xor0 = t0; |
828 | 144 | xor1 = t1; |
829 | 144 | } |
830 | 123 | if (len != 0) { |
831 | 0 | c2l(in, tin0); |
832 | 0 | c2l(in, tin1); |
833 | |
|
834 | 0 | t0 = tin0; |
835 | 0 | t1 = tin1; |
836 | |
|
837 | 0 | tin[0] = tin0; |
838 | 0 | tin[1] = tin1; |
839 | 0 | DES_decrypt3(tin, ks1, ks2, ks3); |
840 | 0 | tout0 = tin[0]; |
841 | 0 | tout1 = tin[1]; |
842 | |
|
843 | 0 | tout0 ^= xor0; |
844 | 0 | tout1 ^= xor1; |
845 | 0 | l2cn(tout0, tout1, out, len); |
846 | 0 | xor0 = t0; |
847 | 0 | xor1 = t1; |
848 | 0 | } |
849 | | |
850 | 123 | iv = ivec; |
851 | 123 | l2c(xor0, iv); |
852 | 123 | l2c(xor1, iv); |
853 | 123 | } |
854 | | |
855 | 2.14k | tin[0] = tin[1] = 0; |
856 | 2.14k | } |
857 | | |
858 | | void DES_ede2_cbc_encrypt(const uint8_t *in, uint8_t *out, size_t len, |
859 | | const DES_key_schedule *ks1, |
860 | | const DES_key_schedule *ks2, |
861 | | DES_cblock *ivec, |
862 | 0 | int enc) { |
863 | 0 | DES_ede3_cbc_encrypt(in, out, len, ks1, ks2, ks1, ivec, enc); |
864 | 0 | } |
865 | | |
866 | | |
867 | | // Deprecated functions. |
868 | | |
869 | | void DES_set_key_unchecked(const DES_cblock *key, DES_key_schedule *schedule) { |
870 | | DES_set_key(key, schedule); |
871 | | } |