s4:torture: Adapt KDC canon test to Heimdal upstream changes
[samba.git] / third_party / heimdal / lib / krb5 / crypto-des.c
1 /*
2  * Copyright (c) 1997 - 2008 Kungliga Tekniska Högskolan
3  * (Royal Institute of Technology, Stockholm, Sweden).
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  *
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  *
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * 3. Neither the name of the Institute nor the names of its contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33
34 #include "krb5_locl.h"
35
36 #ifdef HEIM_WEAK_CRYPTO
37
38
39 static void
40 krb5_DES_random_key(krb5_context context,
41                     krb5_keyblock *key)
42 {
43     DES_cblock *k = key->keyvalue.data;
44     do {
45         krb5_generate_random_block(k, sizeof(DES_cblock));
46         DES_set_odd_parity(k);
47     } while(DES_is_weak_key(k));
48 }
49
50 static void
51 krb5_DES_schedule_old(krb5_context context,
52                       struct _krb5_key_type *kt,
53                       struct _krb5_key_data *key)
54 {
55     DES_set_key_unchecked(key->key->keyvalue.data, key->schedule->data);
56 }
57
58 static void
59 krb5_DES_random_to_key(krb5_context context,
60                        krb5_keyblock *key,
61                        const void *data,
62                        size_t size)
63 {
64     DES_cblock *k = key->keyvalue.data;
65     memcpy(k, data, key->keyvalue.length);
66     DES_set_odd_parity(k);
67     if(DES_is_weak_key(k))
68         _krb5_xor8(*k, (const unsigned char*)"\0\0\0\0\0\0\0\xf0");
69 }
70
71 static struct _krb5_key_type keytype_des_old = {
72     ETYPE_DES_CBC_CRC,
73     "des-old",
74     56,
75     8,
76     sizeof(DES_key_schedule),
77     krb5_DES_random_key,
78     krb5_DES_schedule_old,
79     _krb5_des_salt,
80     krb5_DES_random_to_key,
81     NULL,
82     NULL
83 };
84
85 static struct _krb5_key_type keytype_des = {
86     ETYPE_DES_CBC_CRC,
87     "des",
88     56,
89     8,
90     sizeof(struct _krb5_evp_schedule),
91     krb5_DES_random_key,
92     _krb5_evp_schedule,
93     _krb5_des_salt,
94     krb5_DES_random_to_key,
95     _krb5_evp_cleanup,
96     EVP_des_cbc
97 };
98
99 static krb5_error_code
100 CRC32_checksum(krb5_context context,
101                krb5_crypto crypto,
102                struct _krb5_key_data *key,
103                unsigned usage,
104                const struct krb5_crypto_iov *iov,
105                int niov,
106                Checksum *C)
107 {
108     uint32_t crc = 0;
109     unsigned char *r = C->checksum.data;
110     int i;
111
112     _krb5_crc_init_table ();
113
114     for (i = 0; i < niov; i++) {
115         if (_krb5_crypto_iov_should_sign(&iov[i]))
116             crc = _krb5_crc_update(iov[i].data.data, iov[i].data.length, crc);
117     }
118
119     r[0] = crc & 0xff;
120     r[1] = (crc >> 8)  & 0xff;
121     r[2] = (crc >> 16) & 0xff;
122     r[3] = (crc >> 24) & 0xff;
123     return 0;
124 }
125
126 static krb5_error_code
127 RSA_MD4_checksum(krb5_context context,
128                  krb5_crypto crypto,
129                  struct _krb5_key_data *key,
130                  unsigned usage,
131                  const struct krb5_crypto_iov *iov,
132                  int niov,
133                  Checksum *C)
134 {
135     if (_krb5_evp_digest_iov(crypto, iov, niov, C->checksum.data,
136                              NULL, EVP_md4(), NULL) != 1)
137         krb5_abortx(context, "md4 checksum failed");
138     return 0;
139 }
140
141 static krb5_error_code
142 RSA_MD4_DES_checksum(krb5_context context,
143                      krb5_crypto crypto,
144                      struct _krb5_key_data *key,
145                      unsigned usage,
146                      const struct krb5_crypto_iov *iov,
147                      int niov,
148                      Checksum *cksum)
149 {
150     return _krb5_des_checksum(context, EVP_md4(), key, iov, niov, cksum);
151 }
152
153 static krb5_error_code
154 RSA_MD4_DES_verify(krb5_context context,
155                    krb5_crypto crypto,
156                    struct _krb5_key_data *key,
157                    unsigned usage,
158                    const struct krb5_crypto_iov *iov,
159                    int niov,
160                    Checksum *C)
161 {
162     return _krb5_des_verify(context, EVP_md4(), key, iov, niov, C);
163 }
164
165 static krb5_error_code
166 RSA_MD5_DES_checksum(krb5_context context,
167                      krb5_crypto crypto,
168                      struct _krb5_key_data *key,
169                      unsigned usage,
170                      const struct krb5_crypto_iov *iov,
171                      int niov,
172                      Checksum *C)
173 {
174     return _krb5_des_checksum(context, EVP_md5(), key, iov, niov, C);
175 }
176
177 static krb5_error_code
178 RSA_MD5_DES_verify(krb5_context context,
179                    krb5_crypto crypto,
180                    struct _krb5_key_data *key,
181                    unsigned usage,
182                    const struct krb5_crypto_iov *iov,
183                    int niov,
184                    Checksum *C)
185 {
186     return _krb5_des_verify(context, EVP_md5(), key, iov, niov, C);
187 }
188
189 struct _krb5_checksum_type _krb5_checksum_crc32 = {
190     CKSUMTYPE_CRC32,
191     "crc32",
192     1,
193     4,
194     0,
195     CRC32_checksum,
196     NULL
197 };
198
199 struct _krb5_checksum_type _krb5_checksum_rsa_md4 = {
200     CKSUMTYPE_RSA_MD4,
201     "rsa-md4",
202     64,
203     16,
204     F_CPROOF,
205     RSA_MD4_checksum,
206     NULL
207 };
208
209 struct _krb5_checksum_type _krb5_checksum_rsa_md4_des = {
210     CKSUMTYPE_RSA_MD4_DES,
211     "rsa-md4-des",
212     64,
213     24,
214     F_KEYED | F_CPROOF | F_VARIANT,
215     RSA_MD4_DES_checksum,
216     RSA_MD4_DES_verify
217 };
218
219 struct _krb5_checksum_type _krb5_checksum_rsa_md5_des = {
220     CKSUMTYPE_RSA_MD5_DES,
221     "rsa-md5-des",
222     64,
223     24,
224     F_KEYED | F_CPROOF | F_VARIANT,
225     RSA_MD5_DES_checksum,
226     RSA_MD5_DES_verify
227 };
228
229 static krb5_error_code
230 evp_des_encrypt_null_ivec(krb5_context context,
231                           struct _krb5_key_data *key,
232                           void *data,
233                           size_t len,
234                           krb5_boolean encryptp,
235                           int usage,
236                           void *ignore_ivec)
237 {
238     struct _krb5_evp_schedule *ctx = key->schedule->data;
239     EVP_CIPHER_CTX *c;
240     DES_cblock ivec;
241     memset(&ivec, 0, sizeof(ivec));
242     c = encryptp ? &ctx->ectx : &ctx->dctx;
243     EVP_CipherInit_ex(c, NULL, NULL, NULL, (void *)&ivec, -1);
244     EVP_Cipher(c, data, data, len);
245     return 0;
246 }
247
248 static krb5_error_code
249 evp_des_encrypt_key_ivec(krb5_context context,
250                          struct _krb5_key_data *key,
251                          void *data,
252                          size_t len,
253                          krb5_boolean encryptp,
254                          int usage,
255                          void *ignore_ivec)
256 {
257     struct _krb5_evp_schedule *ctx = key->schedule->data;
258     EVP_CIPHER_CTX *c;
259     DES_cblock ivec;
260     memcpy(&ivec, key->key->keyvalue.data, sizeof(ivec));
261     c = encryptp ? &ctx->ectx : &ctx->dctx;
262     EVP_CipherInit_ex(c, NULL, NULL, NULL, (void *)&ivec, -1);
263     EVP_Cipher(c, data, data, len);
264     return 0;
265 }
266
267 static krb5_error_code
268 DES_CFB64_encrypt_null_ivec(krb5_context context,
269                             struct _krb5_key_data *key,
270                             void *data,
271                             size_t len,
272                             krb5_boolean encryptp,
273                             int usage,
274                             void *ignore_ivec)
275 {
276     DES_cblock ivec;
277     int num = 0;
278     DES_key_schedule *s = key->schedule->data;
279     memset(&ivec, 0, sizeof(ivec));
280
281     DES_cfb64_encrypt(data, data, len, s, &ivec, &num, encryptp);
282     return 0;
283 }
284
285 static krb5_error_code
286 DES_PCBC_encrypt_key_ivec(krb5_context context,
287                           struct _krb5_key_data *key,
288                           void *data,
289                           size_t len,
290                           krb5_boolean encryptp,
291                           int usage,
292                           void *ignore_ivec)
293 {
294     DES_cblock ivec;
295     DES_key_schedule *s = key->schedule->data;
296     memcpy(&ivec, key->key->keyvalue.data, sizeof(ivec));
297
298     DES_pcbc_encrypt(data, data, len, s, &ivec, encryptp);
299     return 0;
300 }
301
302 struct _krb5_encryption_type _krb5_enctype_des_cbc_crc = {
303     ETYPE_DES_CBC_CRC,
304     "des-cbc-crc",
305     NULL,
306     8,
307     8,
308     8,
309     &keytype_des,
310     &_krb5_checksum_crc32,
311     NULL,
312     F_DISABLED|F_WEAK|F_OLD,
313     evp_des_encrypt_key_ivec,
314     NULL,
315     0,
316     NULL
317 };
318
319 struct _krb5_encryption_type _krb5_enctype_des_cbc_md4 = {
320     ETYPE_DES_CBC_MD4,
321     "des-cbc-md4",
322     NULL,
323     8,
324     8,
325     8,
326     &keytype_des,
327     &_krb5_checksum_rsa_md4,
328     &_krb5_checksum_rsa_md4_des,
329     F_DISABLED|F_WEAK|F_OLD,
330     evp_des_encrypt_null_ivec,
331     NULL,
332     0,
333     NULL
334 };
335
336 struct _krb5_encryption_type _krb5_enctype_des_cbc_md5 = {
337     ETYPE_DES_CBC_MD5,
338     "des-cbc-md5",
339     NULL,
340     8,
341     8,
342     8,
343     &keytype_des,
344     &_krb5_checksum_rsa_md5,
345     &_krb5_checksum_rsa_md5_des,
346     F_DISABLED|F_WEAK|F_OLD,
347     evp_des_encrypt_null_ivec,
348     NULL,
349     0,
350     NULL
351 };
352
353 struct _krb5_encryption_type _krb5_enctype_des_cbc_none = {
354     ETYPE_DES_CBC_NONE,
355     "des-cbc-none",
356     NULL,
357     8,
358     8,
359     0,
360     &keytype_des,
361     &_krb5_checksum_none,
362     NULL,
363     F_PSEUDO|F_DISABLED|F_WEAK|F_OLD,
364     evp_des_encrypt_null_ivec,
365     NULL,
366     0,
367     NULL
368 };
369
370 struct _krb5_encryption_type _krb5_enctype_des_cfb64_none = {
371     ETYPE_DES_CFB64_NONE,
372     "des-cfb64-none",
373     NULL,
374     1,
375     1,
376     0,
377     &keytype_des_old,
378     &_krb5_checksum_none,
379     NULL,
380     F_PSEUDO|F_DISABLED|F_WEAK|F_OLD,
381     DES_CFB64_encrypt_null_ivec,
382     NULL,
383     0,
384     NULL
385 };
386
387 struct _krb5_encryption_type _krb5_enctype_des_pcbc_none = {
388     ETYPE_DES_PCBC_NONE,
389     "des-pcbc-none",
390     NULL,
391     8,
392     8,
393     0,
394     &keytype_des_old,
395     &_krb5_checksum_none,
396     NULL,
397     F_PSEUDO|F_DISABLED|F_WEAK|F_OLD,
398     DES_PCBC_encrypt_key_ivec,
399     NULL,
400     0,
401     NULL
402 };
403 #endif /* HEIM_WEAK_CRYPTO */