1 /* $OpenBSD: des3.c,v 1.9 2014/08/15 15:13:38 mikeb Exp $ */ 2 3 /* 4 * Copyright (c) 2002 Markus Friedl. 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 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 17 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 18 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 20 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 24 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26 27 #include <sys/param.h> 28 #include <openssl/des.h> 29 #include <err.h> 30 #include <fcntl.h> 31 #include <stdio.h> 32 #include <stdlib.h> 33 #include <string.h> 34 #include <unistd.h> 35 36 /* Stubs */ 37 38 u_int32_t deflate_global(u_int8_t *, u_int32_t, int, u_int8_t **); 39 40 u_int32_t 41 deflate_global(u_int8_t *data, u_int32_t size, int comp, u_int8_t **out) 42 { 43 return 0; 44 } 45 46 void explicit_bzero(void *, size_t); 47 48 void 49 explicit_bzero(void *b, size_t len) 50 { 51 bzero(b, len); 52 } 53 54 55 /* Simulate CBC mode */ 56 57 static int 58 docrypt(const unsigned char *key, size_t klen, const unsigned char *iv0, 59 const unsigned char *in, unsigned char *out, size_t len, int encrypt) 60 { 61 u_int8_t block[8], iv[8], iv2[8], *ivp = iv, *nivp; 62 u_int8_t ctx[384]; 63 int i, j, error = 0; 64 65 memcpy(iv, iv0, 8); 66 memset(ctx, 0, sizeof(ctx)); 67 error = des3_setkey(ctx, key, klen); 68 if (error) 69 return -1; 70 for (i = 0; i < len / 8; i ++) { 71 bcopy(in, block, 8); 72 in += 8; 73 if (encrypt) { 74 for (j = 0; j < 8; j++) 75 block[j] ^= ivp[j]; 76 des3_encrypt(ctx, block); 77 memcpy(ivp, block, 8); 78 } else { 79 nivp = ivp == iv ? iv2 : iv; 80 memcpy(nivp, block, 8); 81 des3_decrypt(ctx, block); 82 for (j = 0; j < 8; j++) 83 block[j] ^= ivp[j]; 84 ivp = nivp; 85 } 86 bcopy(block, out, 8); 87 out += 8; 88 } 89 return 0; 90 } 91 92 static int 93 match(unsigned char *a, unsigned char *b, size_t len) 94 { 95 int i; 96 97 if (memcmp(a, b, len) == 0) 98 return (1); 99 100 warnx("decrypt/plaintext mismatch"); 101 102 for (i = 0; i < len; i++) 103 printf("%2.2x", a[i]); 104 printf("\n"); 105 for (i = 0; i < len; i++) 106 printf("%2.2x", b[i]); 107 printf("\n"); 108 109 return (0); 110 } 111 112 #define SZ 16 113 114 int 115 main(int argc, char **argv) 116 { 117 DES_key_schedule ks1, ks2, ks3; 118 unsigned char iv0[8], iv[8], key[24] = "012345670123456701234567"; 119 unsigned char b1[SZ], b2[SZ]; 120 int i, fail = 0; 121 u_int32_t rand = 0; 122 123 /* setup data and iv */ 124 for (i = 0; i < sizeof(b1); i++ ) { 125 if (i % 4 == 0) 126 rand = arc4random(); 127 b1[i] = rand; 128 rand >>= 8; 129 } 130 for (i = 0; i < sizeof(iv0); i++ ) { 131 if (i % 4 == 0) 132 rand = arc4random(); 133 iv0[i] = rand; 134 rand >>= 8; 135 } 136 memset(b2, 0, sizeof(b2)); 137 138 /* keysetup for software */ 139 DES_set_key((void *) key, &ks1); 140 DES_set_key((void *) (key+8), &ks2); 141 DES_set_key((void *) (key+16), &ks3); 142 143 /* encrypt with software, decrypt with /dev/crypto */ 144 memcpy(iv, iv0, sizeof(iv0)); 145 DES_ede3_cbc_encrypt((void *)b1, (void*)b2, sizeof(b1), &ks1, &ks2, 146 &ks3, (void*)iv, DES_ENCRYPT); 147 memcpy(iv, iv0, sizeof(iv0)); 148 if (docrypt(key, sizeof(key), iv, b2, b2, sizeof(b1), 0) < 0) { 149 warnx("decryption failed"); 150 fail++; 151 } 152 if (!match(b1, b2, sizeof(b1))) 153 fail++; 154 else 155 printf("ok, decrypted\n"); 156 157 /* encrypt with kernel functions, decrypt with openssl */ 158 memset(b2, 0, sizeof(b2)); 159 memcpy(iv, iv0, sizeof(iv0)); 160 if (docrypt(key, sizeof(key), iv, b1, b2, sizeof(b1), 1) < 0) { 161 warnx("encryption failed"); 162 fail++; 163 } 164 memcpy(iv, iv0, sizeof(iv0)); 165 DES_ede3_cbc_encrypt((void *)b2, (void*)b2, sizeof(b1), &ks1, &ks2, 166 &ks3, (void*)iv, DES_DECRYPT); 167 if (!match(b1, b2, sizeof(b1))) 168 fail++; 169 else 170 printf("ok, encrypted\n"); 171 172 exit((fail > 0) ? 1 : 0); 173 } 174