|
|
1.1.1.3 root 1: /* The source code contained in this file has been derived from the source code
2: of Encryption for the Masses 2.02a by Paul Le Roux. Modifications and
3: additions to that source code contained in this file are Copyright (c) 2004
1.1.1.4 ! root 4: TrueCrypt Foundation and Copyright (c) 2004 TrueCrypt Team. Unmodified
1.1.1.3 root 5: parts are Copyright (c) 1998-99 Paul Le Roux. This is a TrueCrypt Foundation
6: release. Please see the file license.txt for full license details. */
1.1 root 7:
8: #include "TCdefs.h"
9:
10: #include <fcntl.h>
11: #include <sys/types.h>
12: #include <sys/stat.h>
13: #include <io.h>
14: #include <time.h>
15:
16: #include "crypto.h"
17: #include "random.h"
18: #include "endian.h"
19: #include "fat.h"
20: #include "volumes.h"
21:
1.1.1.4 ! root 22: #include "Aes.h"
1.1 root 23: #include "pkcs5.h"
24: #include "crc.h"
25:
26:
1.1.1.4 ! root 27: /* When FALSE, hidden volumes will not be attempted to mount. This variable could be used in future.
! 28: Should a large number of new ciphers be implemented, setting this to FALSE (via program prefs) might
! 29: speed mounting up. */
! 30: BOOL mountingHiddenVolumesAllowed = TRUE;
1.1 root 31:
32:
33: // Volume header structure:
34: //
35: // Offset Length Description
36: // ------------------------------------------
37: // Unencrypted:
38: // 0 64 Key salt
39: // Encrypted:
1.1.1.4 ! root 40: // 64 4 ASCII string 'TRUE'
1.1 root 41: // 68 2 Header version
42: // 70 2 Required program version
43: // 72 4 CRC32 of disk IV and key
44: // 76 8 Volume creation time
45: // 84 8 Header creation time
1.1.1.4 ! root 46: // 92 8 Size of hidden volume in bytes (0 = normal volume)
! 47: // 100 156 Unused
1.1 root 48: // 256 32 Disk IV
49: // 288 224 Disk key
50:
51: int
1.1.1.4 ! root 52: VolumeReadHeader (char *encryptedHeader, char *encryptedHeaderHiddenVol, char *lpszPassword, PCRYPTO_INFO *retInfo)
1.1 root 53: {
54: char header[SECTOR_SIZE];
55: unsigned char *input = (unsigned char *) header;
56: KEY_INFO keyInfo;
1.1.1.4 ! root 57: KEY_INFO keyInfoHiddenVol;
1.1 root 58: PCRYPTO_INFO cryptoInfo;
59: int nStatus = 0, nKeyLen;
60: char dk[DISKKEY_SIZE];
1.1.1.4 ! root 61: char dkHiddenVol[DISKKEY_SIZE];
1.1 root 62: int pkcs5;
63: int headerVersion, requiredVersion;
1.1.1.4 ! root 64: int volType, lastVolType = NORMAL_VOLUME;
1.1 root 65:
66: cryptoInfo = *retInfo = crypto_open ();
67: if (cryptoInfo == NULL)
68: return ERR_OUTOFMEMORY;
69:
70: crypto_loadkey (&keyInfo, lpszPassword, strlen (lpszPassword));
71:
72: // PKCS5 is used to derive header key and IV from user password
73: memcpy (keyInfo.key_salt, encryptedHeader + HEADER_USERKEY_SALT, USERKEY_SALT_SIZE);
1.1.1.4 ! root 74:
! 75: if (mountingHiddenVolumesAllowed && encryptedHeaderHiddenVol != 0)
! 76: {
! 77: // Salt for a possible hidden volume
! 78: memcpy (keyInfoHiddenVol.key_salt, encryptedHeaderHiddenVol + HEADER_USERKEY_SALT, USERKEY_SALT_SIZE);
! 79: lastVolType = HIDDEN_VOLUME;
! 80: }
! 81:
1.1 root 82: keyInfo.noIterations = USERKEY_ITERATIONS;
83:
1.1.1.3 root 84: // Test all available PKCS5 PRFs
85: for (pkcs5 = 1; pkcs5 <= LAST_PRF_ID; pkcs5++)
1.1 root 86: {
1.1.1.3 root 87: if (pkcs5 == SHA1)
88: {
89: derive_sha_key (keyInfo.userKey, keyInfo.keyLength, keyInfo.key_salt,
1.1.1.4 ! root 90: USERKEY_SALT_SIZE, keyInfo.noIterations, dk, DISK_IV_SIZE + EAGetLargestKey());
! 91: if (mountingHiddenVolumesAllowed)
! 92: {
! 93: // Derive header for a possible hidden volume (HMAC-SHA-1)
! 94: derive_sha_key (keyInfo.userKey, keyInfo.keyLength, keyInfoHiddenVol.key_salt,
! 95: USERKEY_SALT_SIZE, keyInfo.noIterations, dkHiddenVol, DISK_IV_SIZE + EAGetLargestKey());
! 96: }
! 97: }
! 98: else if (pkcs5 == RIPEMD160)
1.1.1.3 root 99: {
100: derive_rmd160_key (keyInfo.userKey, keyInfo.keyLength, keyInfo.key_salt,
1.1.1.4 ! root 101: USERKEY_SALT_SIZE, keyInfo.noIterations, dk, DISK_IV_SIZE + EAGetLargestKey());
! 102: if (mountingHiddenVolumesAllowed)
! 103: {
! 104: // Derive header for a possible hidden volume (HMAC-RIPEMD-160)
! 105: derive_rmd160_key (keyInfo.userKey, keyInfo.keyLength, keyInfoHiddenVol.key_salt,
! 106: USERKEY_SALT_SIZE, keyInfo.noIterations, dkHiddenVol, DISK_IV_SIZE + EAGetLargestKey());
! 107: }
1.1.1.3 root 108: }
1.1 root 109:
1.1.1.4 ! root 110: // Test all available encryption algorithms
! 111: for (cryptoInfo->ea = EAGetFirst (); cryptoInfo->ea != 0; cryptoInfo->ea = EAGetNext (cryptoInfo->ea))
1.1.1.3 root 112: {
1.1.1.4 ! root 113: // Test all volume types
! 114: for (volType = NORMAL_VOLUME; volType <= lastVolType; volType++)
1.1.1.3 root 115: {
1.1.1.4 ! root 116: // Copy header for decryption and init an encryption algorithm
! 117: if (volType == NORMAL_VOLUME)
! 118: {
! 119: memcpy (header, encryptedHeader, SECTOR_SIZE);
! 120: memcpy (cryptoInfo->iv, dk, DISK_IV_SIZE);
! 121: EAInit (cryptoInfo->ea, dk + DISK_IV_SIZE, cryptoInfo->ks);
! 122: }
! 123: else if (volType == HIDDEN_VOLUME)
! 124: {
! 125: memcpy (header, encryptedHeaderHiddenVol, SECTOR_SIZE);
! 126: memcpy (cryptoInfo->iv, dkHiddenVol, DISK_IV_SIZE);
! 127: EAInit (cryptoInfo->ea, dkHiddenVol + DISK_IV_SIZE, cryptoInfo->ks);
! 128: }
! 129:
! 130: input = header;
! 131:
! 132: // Try to decrypt header
! 133:
! 134: DecryptBuffer ((unsigned long *) (header + HEADER_ENCRYPTEDDATA), HEADER_ENCRYPTEDDATASIZE,
! 135: cryptoInfo->ks, cryptoInfo->iv, &cryptoInfo->iv[8], cryptoInfo->ea);
! 136:
! 137: input += HEADER_ENCRYPTEDDATA;
! 138:
! 139: // Magic
! 140: if (mgetLong (input) != 'TRUE')
! 141: continue;
! 142:
! 143: // Header version
! 144: headerVersion = mgetWord (input);
! 145:
! 146: // Required program version
! 147: requiredVersion = mgetWord (input);
! 148:
! 149: // Check CRC of disk IV and key
! 150: if (mgetLong (input) != crc32 (header + HEADER_DISKKEY, DISKKEY_SIZE))
! 151: continue;
! 152:
! 153: // Now we have the correct password, cipher, hash algorithm, and volume type
! 154:
! 155: // Check the version required to handle this volume
! 156: if (requiredVersion > VERSION_NUM)
! 157: return ERR_NEW_VERSION_REQUIRED;
! 158:
! 159: // Volume creation time
! 160: cryptoInfo->volume_creation_time = mgetInt64 (input);
! 161:
! 162: // Header creation time
! 163: cryptoInfo->header_creation_time = mgetInt64 (input);
! 164:
! 165: // Hidden volume
! 166: cryptoInfo->hiddenVolumeSize = mgetInt64 (input);
! 167:
! 168: if (volType == HIDDEN_VOLUME) // If mounted as a hidden volume
! 169: {
! 170: cryptoInfo->hiddenVolume = TRUE;
! 171: }
! 172: else
! 173: {
! 174: cryptoInfo->hiddenVolume = FALSE;
! 175: cryptoInfo->hiddenVolumeSize = 0;
! 176: }
! 177:
! 178: // Disk key
! 179: nKeyLen = DISKKEY_SIZE;
! 180: memcpy (keyInfo.key, header + HEADER_DISKKEY, nKeyLen);
! 181:
! 182: memcpy (cryptoInfo->master_decrypted_key, keyInfo.key, nKeyLen);
! 183: memcpy (cryptoInfo->key_salt, keyInfo.key_salt, USERKEY_SALT_SIZE);
! 184: cryptoInfo->pkcs5 = pkcs5;
! 185: cryptoInfo->noIterations = keyInfo.noIterations;
! 186:
! 187: // Init the encryption algorithm with the decrypted master key
! 188: EAInit (cryptoInfo->ea, keyInfo.key + DISK_IV_SIZE, cryptoInfo->ks);
! 189:
! 190: // Disk IV
! 191: memcpy (cryptoInfo->iv, keyInfo.key, DISK_IV_SIZE);
! 192:
! 193: // Clear out the temp. key buffers
! 194: burn (dk, sizeof(dk));
! 195: burn (dkHiddenVol, sizeof(dkHiddenVol));
1.1.1.3 root 196:
1.1.1.4 ! root 197: return 0;
! 198: }
1.1.1.2 root 199: }
1.1 root 200: }
201:
202: crypto_close(cryptoInfo);
203: burn (&keyInfo, sizeof (keyInfo));
1.1.1.4 ! root 204: burn (&keyInfoHiddenVol, sizeof (keyInfoHiddenVol));
1.1 root 205: return ERR_PASSWORD_WRONG;
206: }
207:
208: #ifndef DEVICE_DRIVER
209:
210: #ifdef VOLFORMAT
1.1.1.3 root 211: extern BOOL showKeys;
1.1 root 212: extern HWND hDiskKey;
1.1.1.3 root 213: extern HWND hHeaderKey;
1.1 root 214: #endif
215:
216: // VolumeWriteHeader:
217: // Creates volume header in memory
218: int
1.1.1.4 ! root 219: VolumeWriteHeader (char *header, int ea, char *lpszPassword,
! 220: int pkcs5, char *masterKey, unsigned __int64 volumeCreationTime, PCRYPTO_INFO * retInfo,
! 221: unsigned __int64 hiddenVolumeSize)
1.1 root 222: {
223: unsigned char *p = (unsigned char *) header;
224: KEY_INFO keyInfo;
225:
226: int nUserKeyLen = strlen(lpszPassword);
227: PCRYPTO_INFO cryptoInfo = crypto_open ();
228: char dk[DISKKEY_SIZE];
229: int x;
230:
231: if (cryptoInfo == NULL)
232: return ERR_OUTOFMEMORY;
233:
234: memset (header, 0, SECTOR_SIZE);
1.1.1.2 root 235: VirtualLock (&keyInfo, sizeof (keyInfo));
1.1 root 236:
237: //// Encryption setup
238:
1.1.1.2 root 239: // Generate disk key and IV
240: if(masterKey == 0)
241: RandgetBytes (keyInfo.key, DISKKEY_SIZE, TRUE);
242: else
243: memcpy (keyInfo.key, masterKey, DISKKEY_SIZE);
244:
1.1 root 245: // User key
246: memcpy (keyInfo.userKey, lpszPassword, nUserKeyLen);
247: keyInfo.keyLength = nUserKeyLen;
248: keyInfo.noIterations = USERKEY_ITERATIONS;
249:
250: // User selected encryption algorithm
1.1.1.4 ! root 251: cryptoInfo->ea = ea;
1.1 root 252:
253: // Salt for header key derivation
1.1.1.2 root 254: RandgetBytes (keyInfo.key_salt, USERKEY_SALT_SIZE, TRUE);
1.1 root 255:
1.1.1.4 ! root 256: // PKCS5 is used to derive the header key and IV from the password
1.1 root 257: if (pkcs5 == SHA1)
258: {
259: derive_sha_key (keyInfo.userKey, keyInfo.keyLength, keyInfo.key_salt,
1.1.1.4 ! root 260: USERKEY_SALT_SIZE, keyInfo.noIterations, dk, DISK_IV_SIZE + EAGetLargestKey() );
1.1 root 261: }
1.1.1.3 root 262: else if (pkcs5 == RIPEMD160)
263: {
264: derive_rmd160_key (keyInfo.userKey, keyInfo.keyLength, keyInfo.key_salt,
1.1.1.4 ! root 265: USERKEY_SALT_SIZE, keyInfo.noIterations, dk, DISK_IV_SIZE + EAGetLargestKey() );
1.1.1.3 root 266: }
1.1 root 267:
268:
269: //// Header setup
270:
271: // Salt
272: mputBytes (p, keyInfo.key_salt, USERKEY_SALT_SIZE);
273:
274: // Magic
275: mputLong (p, 'TRUE');
276:
277: // Header version
1.1.1.4 ! root 278: mputWord (p, VOLUME_HEADER_VERSION);
1.1 root 279:
280: // Required program version to handle this volume
1.1.1.4 ! root 281: mputWord (p, VOL_REQ_PROG_VERSION);
1.1 root 282:
283: // CRC of disk key
284: x = crc32(keyInfo.key, DISKKEY_SIZE);
285: mputLong (p, x);
286:
287: // Time
288: {
289: SYSTEMTIME st;
290: FILETIME ft;
291:
292: // Volume creation time
293: if (volumeCreationTime == 0)
294: {
295: GetLocalTime (&st);
296: SystemTimeToFileTime (&st, &ft);
297: }
298: else
299: {
300: ft.dwHighDateTime = (DWORD)(volumeCreationTime >> 32);
301: ft.dwLowDateTime = (DWORD)volumeCreationTime;
302: }
303: mputLong (p, ft.dwHighDateTime);
304: mputLong (p, ft.dwLowDateTime);
305:
306: // Password change time
307: GetLocalTime (&st);
308: SystemTimeToFileTime (&st, &ft);
309: mputLong (p, ft.dwHighDateTime);
310: mputLong (p, ft.dwLowDateTime);
311: }
312:
1.1.1.4 ! root 313: // Hidden volume size
! 314: cryptoInfo->hiddenVolumeSize = hiddenVolumeSize;
! 315: mputInt64 (p, cryptoInfo->hiddenVolumeSize);
! 316:
1.1 root 317: // Disk key and IV
318: memcpy (header + HEADER_DISKKEY, keyInfo.key, DISKKEY_SIZE);
319:
320:
321: //// Header encryption
322:
323: memcpy (cryptoInfo->iv, dk, DISK_IV_SIZE);
1.1.1.4 ! root 324: EAInit (cryptoInfo->ea, dk + DISK_IV_SIZE, cryptoInfo->ks);
1.1 root 325:
1.1.1.4 ! root 326: EncryptBuffer ((unsigned long *) (header + HEADER_ENCRYPTEDDATA), HEADER_ENCRYPTEDDATASIZE,
! 327: cryptoInfo->ks, cryptoInfo->iv, &cryptoInfo->iv[8], cryptoInfo->ea);
1.1 root 328:
329:
330: //// cryptoInfo setup for further use (disk format)
331:
332: // Init with master disk key for sector decryption
1.1.1.4 ! root 333: EAInit (cryptoInfo->ea, keyInfo.key + DISK_IV_SIZE, cryptoInfo->ks);
1.1 root 334:
335: // Disk IV
336: memcpy (cryptoInfo->iv, keyInfo.key, DISK_IV_SIZE);
337:
1.1.1.2 root 338:
1.1 root 339: #ifdef VOLFORMAT
1.1.1.3 root 340: if (showKeys)
1.1 root 341: {
342: char tmp[64];
343: BOOL dots3 = FALSE;
344: int i, j;
345:
1.1.1.4 ! root 346: j = EAGetKeySize (ea);
1.1 root 347:
1.1.1.3 root 348: if (j > 14)
1.1 root 349: {
350: dots3 = TRUE;
1.1.1.3 root 351: j = 14;
1.1 root 352: }
353:
354: tmp[0] = 0;
355: for (i = 0; i < j; i++)
356: {
357: char tmp2[8] =
358: {0};
359: sprintf (tmp2, "%02X", (int) (unsigned char) keyInfo.key[i + DISK_IV_SIZE]);
360: strcat (tmp, tmp2);
361: }
362:
363: if (dots3 == TRUE)
364: {
365: strcat (tmp, "...");
366: }
367:
368:
369: SetWindowText (hDiskKey, tmp);
370:
371: tmp[0] = 0;
1.1.1.3 root 372: for (i = 0; i < 14; i++)
1.1 root 373: {
374: char tmp2[8];
1.1.1.3 root 375: sprintf (tmp2, "%02X", (int) (unsigned char) dk[DISK_IV_SIZE + i]);
1.1 root 376: strcat (tmp, tmp2);
377: }
378:
1.1.1.3 root 379: if (dots3 == TRUE)
380: {
381: strcat (tmp, "...");
382: }
383:
384: SetWindowText (hHeaderKey, tmp);
1.1 root 385: }
386: #endif
387:
1.1.1.3 root 388: burn (dk, sizeof(dk));
1.1 root 389: burn (&keyInfo, sizeof (keyInfo));
1.1.1.2 root 390: VirtualUnlock (&keyInfo, sizeof (keyInfo));
1.1 root 391:
392: *retInfo = cryptoInfo;
393: return 0;
394: }
395:
396: #endif /* !NT4_DRIVER */
1.1.1.4 ! root 397:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.