Imported Upstream version 2.6.1
[platform/upstream/cryptsetup.git] / lib / tcrypt / tcrypt.c
1 /*
2  * TCRYPT (TrueCrypt-compatible) and VeraCrypt volume handling
3  *
4  * Copyright (C) 2012-2023 Red Hat, Inc. All rights reserved.
5  * Copyright (C) 2012-2023 Milan Broz
6  *
7  * This file is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * This file is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with this file; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20  */
21
22 #include <errno.h>
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26
27 #include "libcryptsetup.h"
28 #include "tcrypt.h"
29 #include "internal.h"
30
31 /* TCRYPT PBKDF variants */
32 static const struct {
33         unsigned int legacy:1;
34         unsigned int veracrypt:1;
35         const char *name;
36         const char *hash;
37         unsigned int iterations;
38         uint32_t veracrypt_pim_const;
39         uint32_t veracrypt_pim_mult;
40 } tcrypt_kdf[] = {
41         { 0, 0, "pbkdf2", "ripemd160",   2000, 0, 0 },
42         { 0, 0, "pbkdf2", "ripemd160",   1000, 0, 0 },
43         { 0, 0, "pbkdf2", "sha512",      1000, 0, 0 },
44         { 0, 0, "pbkdf2", "whirlpool",   1000, 0, 0 },
45         { 1, 0, "pbkdf2", "sha1",        2000, 0, 0 },
46         { 0, 1, "pbkdf2", "sha512",    500000, 15000, 1000 },
47         { 0, 1, "pbkdf2", "whirlpool", 500000, 15000, 1000 },
48         { 0, 1, "pbkdf2", "sha256",    500000, 15000, 1000 }, // VeraCrypt 1.0f
49         { 0, 1, "pbkdf2", "sha256",    200000,     0, 2048 }, // boot only
50         { 0, 1, "pbkdf2", "ripemd160", 655331, 15000, 1000 },
51         { 0, 1, "pbkdf2", "ripemd160", 327661,     0, 2048 }, // boot only
52         { 0, 1, "pbkdf2", "stribog512",500000, 15000, 1000 },
53 //      { 0, 1, "pbkdf2", "stribog512",200000,     0, 2048 }, // boot only
54         { 0, 0,     NULL,        NULL,      0,     0,    0 }
55 };
56
57 struct tcrypt_alg {
58                 const char *name;
59                 unsigned int key_size;
60                 unsigned int iv_size;
61                 unsigned int key_offset;
62                 unsigned int iv_offset; /* or tweak key offset */
63                 unsigned int key_extra_size;
64 };
65
66 struct tcrypt_algs {
67         unsigned int legacy:1;
68         unsigned int chain_count;
69         unsigned int chain_key_size;
70         const char *long_name;
71         const char *mode;
72         struct tcrypt_alg cipher[3];
73 };
74
75 /* TCRYPT cipher variants */
76 static struct tcrypt_algs tcrypt_cipher[] = {
77 /* XTS mode */
78 {0,1,64,"aes","xts-plain64",
79         {{"aes",    64,16,0,32,0}}},
80 {0,1,64,"serpent","xts-plain64",
81         {{"serpent",64,16,0,32,0}}},
82 {0,1,64,"twofish","xts-plain64",
83         {{"twofish",64,16,0,32,0}}},
84 {0,2,128,"twofish-aes","xts-plain64",
85         {{"twofish",64,16, 0,64,0},
86          {"aes",    64,16,32,96,0}}},
87 {0,3,192,"serpent-twofish-aes","xts-plain64",
88         {{"serpent",64,16, 0, 96,0},
89          {"twofish",64,16,32,128,0},
90          {"aes",    64,16,64,160,0}}},
91 {0,2,128,"aes-serpent","xts-plain64",
92         {{"aes",    64,16, 0,64,0},
93          {"serpent",64,16,32,96,0}}},
94 {0,3,192,"aes-twofish-serpent","xts-plain64",
95         {{"aes",    64,16, 0, 96,0},
96          {"twofish",64,16,32,128,0},
97          {"serpent",64,16,64,160,0}}},
98 {0,2,128,"serpent-twofish","xts-plain64",
99         {{"serpent",64,16, 0,64,0},
100          {"twofish",64,16,32,96,0}}},
101 {0,1,64,"camellia","xts-plain64",
102         {{"camellia",    64,16,0,32,0}}},
103 {0,1,64,"kuznyechik","xts-plain64",
104         {{"kuznyechik",  64,16,0,32,0}}},
105 {0,2,128,"kuznyechik-camellia","xts-plain64",
106         {{"kuznyechik",64,16, 0,64,0},
107          {"camellia",  64,16,32,96,0}}},
108 {0,2,128,"twofish-kuznyechik","xts-plain64",
109         {{"twofish",   64,16, 0,64,0},
110          {"kuznyechik",64,16,32,96,0}}},
111 {0,2,128,"serpent-camellia","xts-plain64",
112         {{"serpent",   64,16, 0,64,0},
113          {"camellia",  64,16,32,96,0}}},
114 {0,2,128,"aes-kuznyechik","xts-plain64",
115         {{"aes",       64,16, 0,64,0},
116          {"kuznyechik",64,16,32,96,0}}},
117 {0,3,192,"camellia-serpent-kuznyechik","xts-plain64",
118         {{"camellia",  64,16, 0, 96,0},
119          {"serpent",   64,16,32,128,0},
120          {"kuznyechik",64,16,64,160,0}}},
121
122 /* LRW mode */
123 {0,1,48,"aes","lrw-benbi",
124         {{"aes",    48,16,32,0,0}}},
125 {0,1,48,"serpent","lrw-benbi",
126         {{"serpent",48,16,32,0,0}}},
127 {0,1,48,"twofish","lrw-benbi",
128         {{"twofish",48,16,32,0,0}}},
129 {0,2,96,"twofish-aes","lrw-benbi",
130         {{"twofish",48,16,32,0,0},
131          {"aes",    48,16,64,0,0}}},
132 {0,3,144,"serpent-twofish-aes","lrw-benbi",
133         {{"serpent",48,16,32,0,0},
134          {"twofish",48,16,64,0,0},
135          {"aes",    48,16,96,0,0}}},
136 {0,2,96,"aes-serpent","lrw-benbi",
137         {{"aes",    48,16,32,0,0},
138          {"serpent",48,16,64,0,0}}},
139 {0,3,144,"aes-twofish-serpent","lrw-benbi",
140         {{"aes",    48,16,32,0,0},
141          {"twofish",48,16,64,0,0},
142          {"serpent",48,16,96,0,0}}},
143 {0,2,96,"serpent-twofish", "lrw-benbi",
144         {{"serpent",48,16,32,0,0},
145          {"twofish",48,16,64,0,0}}},
146
147 /* Kernel LRW block size is fixed to 16 bytes for GF(2^128)
148  * thus cannot be used with blowfish where block is 8 bytes.
149  * There also no GF(2^64) support.
150 {1,1,64,"blowfish_le","lrw-benbi",
151          {{"blowfish_le",64,8,32,0,0}}},
152 {1,2,112,"blowfish_le-aes","lrw-benbi",
153          {{"blowfish_le",64, 8,32,0,0},
154           {"aes",        48,16,88,0,0}}},
155 {1,3,160,"serpent-blowfish_le-aes","lrw-benbi",
156           {{"serpent",    48,16, 32,0,0},
157            {"blowfish_le",64, 8, 64,0,0},
158            {"aes",        48,16,120,0,0}}},*/
159
160 /*
161  * CBC + "outer" CBC (both with whitening)
162  * chain_key_size: alg_keys_bytes + IV_seed_bytes + whitening_bytes
163  */
164 {1,1,32+16+16,"aes","cbc-tcw",
165         {{"aes",    32,16,32,0,32}}},
166 {1,1,32+16+16,"serpent","cbc-tcw",
167         {{"serpent",32,16,32,0,32}}},
168 {1,1,32+16+16,"twofish","cbc-tcw",
169         {{"twofish",32,16,32,0,32}}},
170 {1,2,64+16+16,"twofish-aes","cbci-tcrypt",
171         {{"twofish",32,16,32,0,0},
172          {"aes",    32,16,64,0,32}}},
173 {1,3,96+16+16,"serpent-twofish-aes","cbci-tcrypt",
174         {{"serpent",32,16,32,0,0},
175          {"twofish",32,16,64,0,0},
176          {"aes",    32,16,96,0,32}}},
177 {1,2,64+16+16,"aes-serpent","cbci-tcrypt",
178         {{"aes",    32,16,32,0,0},
179          {"serpent",32,16,64,0,32}}},
180 {1,3,96+16+16,"aes-twofish-serpent", "cbci-tcrypt",
181         {{"aes",    32,16,32,0,0},
182          {"twofish",32,16,64,0,0},
183          {"serpent",32,16,96,0,32}}},
184 {1,2,64+16+16,"serpent-twofish", "cbci-tcrypt",
185         {{"serpent",32,16,32,0,0},
186          {"twofish",32,16,64,0,32}}},
187 {1,1,16+8+16,"cast5","cbc-tcw",
188         {{"cast5",   16,8,32,0,24}}},
189 {1,1,24+8+16,"des3_ede","cbc-tcw",
190         {{"des3_ede",24,8,32,0,24}}},
191 {1,1,56+8+16,"blowfish_le","cbc-tcrypt",
192         {{"blowfish_le",56,8,32,0,24}}},
193 {1,2,88+16+16,"blowfish_le-aes","cbc-tcrypt",
194         {{"blowfish_le",56, 8,32,0,0},
195          {"aes",        32,16,88,0,32}}},
196 {1,3,120+16+16,"serpent-blowfish_le-aes","cbc-tcrypt",
197         {{"serpent",    32,16, 32,0,0},
198          {"blowfish_le",56, 8, 64,0,0},
199          {"aes",        32,16,120,0,32}}},
200 {}
201 };
202
203 static int TCRYPT_hdr_from_disk(struct crypt_device *cd,
204                                 struct tcrypt_phdr *hdr,
205                                 struct crypt_params_tcrypt *params,
206                                 int kdf_index, int cipher_index)
207 {
208         uint32_t crc32;
209         size_t size;
210
211         /* Check CRC32 of header */
212         size = TCRYPT_HDR_LEN - sizeof(hdr->d.keys) - sizeof(hdr->d.header_crc32);
213         crc32 = crypt_crc32(~0, (unsigned char*)&hdr->d, size) ^ ~0;
214         if (be16_to_cpu(hdr->d.version) > 3 &&
215             crc32 != be32_to_cpu(hdr->d.header_crc32)) {
216                 log_dbg(cd, "TCRYPT header CRC32 mismatch.");
217                 return -EINVAL;
218         }
219
220         /* Check CRC32 of keys */
221         crc32 = crypt_crc32(~0, (unsigned char*)hdr->d.keys, sizeof(hdr->d.keys)) ^ ~0;
222         if (crc32 != be32_to_cpu(hdr->d.keys_crc32)) {
223                 log_dbg(cd, "TCRYPT keys CRC32 mismatch.");
224                 return -EINVAL;
225         }
226
227         /* Convert header to cpu format */
228         hdr->d.version  =  be16_to_cpu(hdr->d.version);
229         hdr->d.version_tc = be16_to_cpu(hdr->d.version_tc);
230
231         hdr->d.keys_crc32 = be32_to_cpu(hdr->d.keys_crc32);
232
233         hdr->d.hidden_volume_size = be64_to_cpu(hdr->d.hidden_volume_size);
234         hdr->d.volume_size        = be64_to_cpu(hdr->d.volume_size);
235
236         hdr->d.mk_offset = be64_to_cpu(hdr->d.mk_offset);
237         if (!hdr->d.mk_offset)
238                 hdr->d.mk_offset = 512;
239
240         hdr->d.mk_size = be64_to_cpu(hdr->d.mk_size);
241
242         hdr->d.flags = be32_to_cpu(hdr->d.flags);
243
244         hdr->d.sector_size = be32_to_cpu(hdr->d.sector_size);
245         if (!hdr->d.sector_size)
246                 hdr->d.sector_size = 512;
247
248         hdr->d.header_crc32 = be32_to_cpu(hdr->d.header_crc32);
249
250         /* Set params */
251         params->passphrase = NULL;
252         params->passphrase_size = 0;
253         params->hash_name  = tcrypt_kdf[kdf_index].hash;
254         params->key_size = tcrypt_cipher[cipher_index].chain_key_size;
255         params->cipher = tcrypt_cipher[cipher_index].long_name;
256         params->mode = tcrypt_cipher[cipher_index].mode;
257
258         return 0;
259 }
260
261 /*
262  * Kernel implements just big-endian version of blowfish, hack it here
263  */
264 static void TCRYPT_swab_le(char *buf)
265 {
266         uint32_t *l = VOIDP_CAST(uint32_t*)&buf[0];
267         uint32_t *r = VOIDP_CAST(uint32_t*)&buf[4];
268         *l = swab32(*l);
269         *r = swab32(*r);
270 }
271
272 static int decrypt_blowfish_le_cbc(struct tcrypt_alg *alg,
273                                    const char *key, char *buf)
274 {
275         int bs = alg->iv_size;
276         char iv[8], iv_old[8];
277         struct crypt_cipher *cipher = NULL;
278         int i, j, r;
279
280         assert(bs == 8);
281
282         r = crypt_cipher_init(&cipher, "blowfish", "ecb",
283                               &key[alg->key_offset], alg->key_size);
284         if (r < 0)
285                 return r;
286
287         memcpy(iv, &key[alg->iv_offset], alg->iv_size);
288         for (i = 0; i < TCRYPT_HDR_LEN; i += bs) {
289                 memcpy(iv_old, &buf[i], bs);
290                 TCRYPT_swab_le(&buf[i]);
291                 r = crypt_cipher_decrypt(cipher, &buf[i], &buf[i],
292                                           bs, NULL, 0);
293                 TCRYPT_swab_le(&buf[i]);
294                 if (r < 0)
295                         break;
296                 for (j = 0; j < bs; j++)
297                         buf[i + j] ^= iv[j];
298                 memcpy(iv, iv_old, bs);
299         }
300
301         crypt_cipher_destroy(cipher);
302         crypt_safe_memzero(iv, bs);
303         crypt_safe_memzero(iv_old, bs);
304         return r;
305 }
306
307 static void TCRYPT_remove_whitening(char *buf, const char *key)
308 {
309         int j;
310
311         for (j = 0; j < TCRYPT_HDR_LEN; j++)
312                 buf[j] ^= key[j % 8];
313 }
314
315 static void TCRYPT_copy_key(struct tcrypt_alg *alg, const char *mode,
316                              char *out_key, const char *key)
317 {
318         int ks2;
319         if (!strncmp(mode, "xts", 3)) {
320                 ks2 = alg->key_size / 2;
321                 memcpy(out_key, &key[alg->key_offset], ks2);
322                 memcpy(&out_key[ks2], &key[alg->iv_offset], ks2);
323         } else if (!strncmp(mode, "lrw", 3)) {
324                 ks2 = alg->key_size - TCRYPT_LRW_IKEY_LEN;
325                 memcpy(out_key, &key[alg->key_offset], ks2);
326                 memcpy(&out_key[ks2], key, TCRYPT_LRW_IKEY_LEN);
327         } else if (!strncmp(mode, "cbc", 3)) {
328                 memcpy(out_key, &key[alg->key_offset], alg->key_size);
329                 /* IV + whitening */
330                 memcpy(&out_key[alg->key_size], &key[alg->iv_offset],
331                        alg->key_extra_size);
332         }
333 }
334
335 static int TCRYPT_decrypt_hdr_one(struct tcrypt_alg *alg, const char *mode,
336                                    const char *key,struct tcrypt_phdr *hdr)
337 {
338         char backend_key[TCRYPT_HDR_KEY_LEN];
339         char iv[TCRYPT_HDR_IV_LEN] = {};
340         char mode_name[MAX_CIPHER_LEN + 1];
341         struct crypt_cipher *cipher;
342         char *c, *buf = (char*)&hdr->e;
343         int r;
344
345         /* Remove IV if present */
346         mode_name[MAX_CIPHER_LEN] = '\0';
347         strncpy(mode_name, mode, MAX_CIPHER_LEN);
348         c = strchr(mode_name, '-');
349         if (c)
350                 *c = '\0';
351
352         if (!strncmp(mode, "lrw", 3))
353                 iv[alg->iv_size - 1] = 1;
354         else if (!strncmp(mode, "cbc", 3)) {
355                 TCRYPT_remove_whitening(buf, &key[8]);
356                 if (!strcmp(alg->name, "blowfish_le"))
357                         return decrypt_blowfish_le_cbc(alg, key, buf);
358                 memcpy(iv, &key[alg->iv_offset], alg->iv_size);
359         }
360
361         TCRYPT_copy_key(alg, mode, backend_key, key);
362         r = crypt_cipher_init(&cipher, alg->name, mode_name,
363                               backend_key, alg->key_size);
364         if (!r) {
365                 r = crypt_cipher_decrypt(cipher, buf, buf, TCRYPT_HDR_LEN,
366                                          iv, alg->iv_size);
367                 crypt_cipher_destroy(cipher);
368         }
369
370         crypt_safe_memzero(backend_key, sizeof(backend_key));
371         crypt_safe_memzero(iv, TCRYPT_HDR_IV_LEN);
372         return r;
373 }
374
375 /*
376  * For chained ciphers and CBC mode we need "outer" decryption.
377  * Backend doesn't provide this, so implement it here directly using ECB.
378  */
379 static int TCRYPT_decrypt_cbci(struct tcrypt_algs *ciphers,
380                                 const char *key, struct tcrypt_phdr *hdr)
381 {
382         struct crypt_cipher *cipher[3];
383         unsigned int bs = ciphers->cipher[0].iv_size;
384         char *buf = (char*)&hdr->e, iv[16], iv_old[16];
385         unsigned int i, j;
386         int r = -EINVAL;
387
388         assert(ciphers->chain_count <= 3);
389         assert(bs <= 16);
390
391         TCRYPT_remove_whitening(buf, &key[8]);
392
393         memcpy(iv, &key[ciphers->cipher[0].iv_offset], bs);
394
395         /* Initialize all ciphers in chain in ECB mode */
396         for (j = 0; j < ciphers->chain_count; j++)
397                 cipher[j] = NULL;
398         for (j = 0; j < ciphers->chain_count; j++) {
399                 r = crypt_cipher_init(&cipher[j], ciphers->cipher[j].name, "ecb",
400                                       &key[ciphers->cipher[j].key_offset],
401                                       ciphers->cipher[j].key_size);
402                 if (r < 0)
403                         goto out;
404         }
405
406         /* Implements CBC with chained ciphers in loop inside */
407         for (i = 0; i < TCRYPT_HDR_LEN; i += bs) {
408                 memcpy(iv_old, &buf[i], bs);
409                 for (j = ciphers->chain_count; j > 0; j--) {
410                         r = crypt_cipher_decrypt(cipher[j - 1], &buf[i], &buf[i],
411                                                   bs, NULL, 0);
412                         if (r < 0)
413                                 goto out;
414                 }
415                 for (j = 0; j < bs; j++)
416                         buf[i + j] ^= iv[j];
417                 memcpy(iv, iv_old, bs);
418         }
419 out:
420         for (j = 0; j < ciphers->chain_count; j++)
421                 if (cipher[j])
422                         crypt_cipher_destroy(cipher[j]);
423
424         crypt_safe_memzero(iv, bs);
425         crypt_safe_memzero(iv_old, bs);
426         return r;
427 }
428
429 static int TCRYPT_decrypt_hdr(struct crypt_device *cd, struct tcrypt_phdr *hdr,
430                                const char *key, struct crypt_params_tcrypt *params)
431 {
432         struct tcrypt_phdr hdr2;
433         int i, j, r = -EINVAL;
434
435         for (i = 0; tcrypt_cipher[i].chain_count; i++) {
436                 if (params->cipher && !strstr(tcrypt_cipher[i].long_name, params->cipher))
437                         continue;
438                 if (!(params->flags & CRYPT_TCRYPT_LEGACY_MODES) && tcrypt_cipher[i].legacy)
439                         continue;
440                 log_dbg(cd, "TCRYPT:  trying cipher %s-%s",
441                         tcrypt_cipher[i].long_name, tcrypt_cipher[i].mode);
442
443                 memcpy(&hdr2.e, &hdr->e, TCRYPT_HDR_LEN);
444
445                 if (!strncmp(tcrypt_cipher[i].mode, "cbci", 4))
446                         r = TCRYPT_decrypt_cbci(&tcrypt_cipher[i], key, &hdr2);
447                 else for (j = tcrypt_cipher[i].chain_count - 1; j >= 0 ; j--) {
448                         if (!tcrypt_cipher[i].cipher[j].name)
449                                 continue;
450                         r = TCRYPT_decrypt_hdr_one(&tcrypt_cipher[i].cipher[j],
451                                             tcrypt_cipher[i].mode, key, &hdr2);
452                         if (r < 0)
453                                 break;
454                 }
455
456                 if (r < 0) {
457                         log_dbg(cd, "TCRYPT:   returned error %d, skipped.", r);
458                         if (r == -ENOTSUP)
459                                 break;
460                         r = -ENOENT;
461                         continue;
462                 }
463
464                 if (!strncmp(hdr2.d.magic, TCRYPT_HDR_MAGIC, TCRYPT_HDR_MAGIC_LEN)) {
465                         log_dbg(cd, "TCRYPT: Signature magic detected.");
466                         memcpy(&hdr->e, &hdr2.e, TCRYPT_HDR_LEN);
467                         r = i;
468                         break;
469                 }
470                 if ((params->flags & CRYPT_TCRYPT_VERA_MODES) &&
471                      !strncmp(hdr2.d.magic, VCRYPT_HDR_MAGIC, TCRYPT_HDR_MAGIC_LEN)) {
472                         log_dbg(cd, "TCRYPT: Signature magic detected (Veracrypt).");
473                         memcpy(&hdr->e, &hdr2.e, TCRYPT_HDR_LEN);
474                         r = i;
475                         break;
476                 }
477                 r = -EPERM;
478         }
479
480         crypt_safe_memzero(&hdr2, sizeof(hdr2));
481         return r;
482 }
483
484 static int TCRYPT_pool_keyfile(struct crypt_device *cd,
485                                 unsigned char pool[VCRYPT_KEY_POOL_LEN],
486                                 const char *keyfile, int keyfiles_pool_length)
487 {
488         unsigned char *data;
489         int i, j, fd, data_size, r = -EIO;
490         uint32_t crc;
491
492         log_dbg(cd, "TCRYPT: using keyfile %s.", keyfile);
493
494         data = malloc(TCRYPT_KEYFILE_LEN);
495         if (!data)
496                 return -ENOMEM;
497         memset(data, 0, TCRYPT_KEYFILE_LEN);
498
499         fd = open(keyfile, O_RDONLY);
500         if (fd < 0) {
501                 log_err(cd, _("Failed to open key file."));
502                 goto out;
503         }
504
505         data_size = read_buffer(fd, data, TCRYPT_KEYFILE_LEN);
506         close(fd);
507         if (data_size < 0) {
508                 log_err(cd, _("Error reading keyfile %s."), keyfile);
509                 goto out;
510         }
511
512         for (i = 0, j = 0, crc = ~0U; i < data_size; i++) {
513                 crc = crypt_crc32(crc, &data[i], 1);
514                 pool[j++] += (unsigned char)(crc >> 24);
515                 pool[j++] += (unsigned char)(crc >> 16);
516                 pool[j++] += (unsigned char)(crc >>  8);
517                 pool[j++] += (unsigned char)(crc);
518                 j %= keyfiles_pool_length;
519         }
520         r = 0;
521 out:
522         crypt_safe_memzero(&crc, sizeof(crc));
523         crypt_safe_memzero(data, TCRYPT_KEYFILE_LEN);
524         free(data);
525
526         return r;
527 }
528
529 static int TCRYPT_init_hdr(struct crypt_device *cd,
530                            struct tcrypt_phdr *hdr,
531                            struct crypt_params_tcrypt *params)
532 {
533         unsigned char pwd[VCRYPT_KEY_POOL_LEN] = {};
534         size_t passphrase_size, max_passphrase_size;
535         char *key;
536         unsigned int i, skipped = 0, iterations;
537         int r = -EPERM, keyfiles_pool_length;
538
539         if (posix_memalign((void*)&key, crypt_getpagesize(), TCRYPT_HDR_KEY_LEN))
540                 return -ENOMEM;
541
542         if (params->flags & CRYPT_TCRYPT_VERA_MODES &&
543             params->passphrase_size > TCRYPT_KEY_POOL_LEN) {
544                 /* Really. Keyfile pool length depends on passphrase size in Veracrypt. */
545                 max_passphrase_size = VCRYPT_KEY_POOL_LEN;
546                 keyfiles_pool_length = VCRYPT_KEY_POOL_LEN;
547         } else {
548                 max_passphrase_size = TCRYPT_KEY_POOL_LEN;
549                 keyfiles_pool_length = TCRYPT_KEY_POOL_LEN;
550         }
551
552         if (params->keyfiles_count)
553                 passphrase_size = max_passphrase_size;
554         else
555                 passphrase_size = params->passphrase_size;
556
557         if (params->passphrase_size > max_passphrase_size) {
558                 log_err(cd, _("Maximum TCRYPT passphrase length (%zu) exceeded."),
559                               max_passphrase_size);
560                 goto out;
561         }
562
563         /* Calculate pool content from keyfiles */
564         for (i = 0; i < params->keyfiles_count; i++) {
565                 r = TCRYPT_pool_keyfile(cd, pwd, params->keyfiles[i], keyfiles_pool_length);
566                 if (r < 0)
567                         goto out;
568         }
569
570         /* If provided password, combine it with pool */
571         for (i = 0; i < params->passphrase_size; i++)
572                 pwd[i] += params->passphrase[i];
573
574         for (i = 0; tcrypt_kdf[i].name; i++) {
575                 if (params->hash_name && strcmp(params->hash_name, tcrypt_kdf[i].hash))
576                         continue;
577                 if (!(params->flags & CRYPT_TCRYPT_LEGACY_MODES) && tcrypt_kdf[i].legacy)
578                         continue;
579                 if (!(params->flags & CRYPT_TCRYPT_VERA_MODES) && tcrypt_kdf[i].veracrypt)
580                         continue;
581                 if ((params->flags & CRYPT_TCRYPT_VERA_MODES) && params->veracrypt_pim) {
582                         /* Do not try TrueCrypt modes if we have PIM value */
583                         if (!tcrypt_kdf[i].veracrypt)
584                                 continue;
585                         /* adjust iterations to given PIM cmdline parameter */
586                         iterations = tcrypt_kdf[i].veracrypt_pim_const +
587                                     (tcrypt_kdf[i].veracrypt_pim_mult * params->veracrypt_pim);
588                 } else
589                         iterations = tcrypt_kdf[i].iterations;
590                 /* Derive header key */
591                 log_dbg(cd, "TCRYPT: trying KDF: %s-%s-%d%s.",
592                         tcrypt_kdf[i].name, tcrypt_kdf[i].hash, tcrypt_kdf[i].iterations,
593                         params->veracrypt_pim && tcrypt_kdf[i].veracrypt ? "-PIM" : "");
594                 r = crypt_pbkdf(tcrypt_kdf[i].name, tcrypt_kdf[i].hash,
595                                 (char*)pwd, passphrase_size,
596                                 hdr->salt, TCRYPT_HDR_SALT_LEN,
597                                 key, TCRYPT_HDR_KEY_LEN,
598                                 iterations, 0, 0);
599                 if (r < 0) {
600                         log_verbose(cd, _("PBKDF2 hash algorithm %s not available, skipping."),
601                                       tcrypt_kdf[i].hash);
602                         skipped++;
603                         r = -EPERM;
604                         continue;
605                 }
606
607                 /* Decrypt header */
608                 r = TCRYPT_decrypt_hdr(cd, hdr, key, params);
609                 if (r == -ENOENT) {
610                         skipped++;
611                         r = -EPERM;
612                         continue;
613                 }
614                 if (r != -EPERM)
615                         break;
616         }
617
618         if ((r < 0 && skipped && skipped == i) || r == -ENOTSUP) {
619                 log_err(cd, _("Required kernel crypto interface not available."));
620 #ifdef ENABLE_AF_ALG
621                 log_err(cd, _("Ensure you have algif_skcipher kernel module loaded."));
622 #endif
623                 r = -ENOTSUP;
624         }
625         if (r < 0)
626                 goto out;
627
628         r = TCRYPT_hdr_from_disk(cd, hdr, params, i, r);
629         if (!r) {
630                 log_dbg(cd, "TCRYPT: Magic: %s, Header version: %d, req. %d, sector %d"
631                         ", mk_offset %" PRIu64 ", hidden_size %" PRIu64
632                         ", volume size %" PRIu64, tcrypt_kdf[i].veracrypt ?
633                         VCRYPT_HDR_MAGIC : TCRYPT_HDR_MAGIC,
634                         (int)hdr->d.version, (int)hdr->d.version_tc, (int)hdr->d.sector_size,
635                         hdr->d.mk_offset, hdr->d.hidden_volume_size, hdr->d.volume_size);
636                 log_dbg(cd, "TCRYPT: Header cipher %s-%s, key size %zu",
637                         params->cipher, params->mode, params->key_size);
638         }
639 out:
640         crypt_safe_memzero(pwd, TCRYPT_KEY_POOL_LEN);
641         if (key)
642                 crypt_safe_memzero(key, TCRYPT_HDR_KEY_LEN);
643         free(key);
644         return r;
645 }
646
647 int TCRYPT_read_phdr(struct crypt_device *cd,
648                      struct tcrypt_phdr *hdr,
649                      struct crypt_params_tcrypt *params)
650 {
651         struct device *base_device = NULL, *device = crypt_metadata_device(cd);
652         ssize_t hdr_size = sizeof(struct tcrypt_phdr);
653         char *base_device_path;
654         int devfd, r;
655
656         assert(sizeof(struct tcrypt_phdr) == 512);
657
658         log_dbg(cd, "Reading TCRYPT header of size %zu bytes from device %s.",
659                 hdr_size, device_path(device));
660
661         if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER &&
662             crypt_dev_is_partition(device_path(device))) {
663                 base_device_path = crypt_get_base_device(device_path(device));
664
665                 log_dbg(cd, "Reading TCRYPT system header from device %s.", base_device_path ?: "?");
666                 if (!base_device_path)
667                         return -EINVAL;
668
669                 r = device_alloc(cd, &base_device, base_device_path);
670                 free(base_device_path);
671                 if (r < 0)
672                         return r;
673                 devfd = device_open(cd, base_device, O_RDONLY);
674         } else
675                 devfd = device_open(cd, device, O_RDONLY);
676
677         if (devfd < 0) {
678                 device_free(cd, base_device);
679                 log_err(cd, _("Cannot open device %s."), device_path(device));
680                 return -EINVAL;
681         }
682
683         r = -EIO;
684         if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) {
685                 if (read_lseek_blockwise(devfd, device_block_size(cd, device),
686                         device_alignment(device), hdr, hdr_size,
687                         TCRYPT_HDR_SYSTEM_OFFSET) == hdr_size) {
688                         r = TCRYPT_init_hdr(cd, hdr, params);
689                 }
690         } else if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER) {
691                 if (params->flags & CRYPT_TCRYPT_BACKUP_HEADER) {
692                         if (read_lseek_blockwise(devfd, device_block_size(cd, device),
693                                 device_alignment(device), hdr, hdr_size,
694                                 TCRYPT_HDR_HIDDEN_OFFSET_BCK) == hdr_size)
695                                 r = TCRYPT_init_hdr(cd, hdr, params);
696                 } else {
697                         if (read_lseek_blockwise(devfd, device_block_size(cd, device),
698                                 device_alignment(device), hdr, hdr_size,
699                                 TCRYPT_HDR_HIDDEN_OFFSET) == hdr_size)
700                                 r = TCRYPT_init_hdr(cd, hdr, params);
701                         if (r && read_lseek_blockwise(devfd, device_block_size(cd, device),
702                                 device_alignment(device), hdr, hdr_size,
703                                 TCRYPT_HDR_HIDDEN_OFFSET_OLD) == hdr_size)
704                                 r = TCRYPT_init_hdr(cd, hdr, params);
705                 }
706         } else if (params->flags & CRYPT_TCRYPT_BACKUP_HEADER) {
707                 if (read_lseek_blockwise(devfd, device_block_size(cd, device),
708                         device_alignment(device), hdr, hdr_size,
709                         TCRYPT_HDR_OFFSET_BCK) == hdr_size)
710                         r = TCRYPT_init_hdr(cd, hdr, params);
711         } else if (read_lseek_blockwise(devfd, device_block_size(cd, device),
712                         device_alignment(device), hdr, hdr_size, 0) == hdr_size)
713                 r = TCRYPT_init_hdr(cd, hdr, params);
714
715         device_free(cd, base_device);
716         if (r < 0)
717                 memset(hdr, 0, sizeof (*hdr));
718         return r;
719 }
720
721 static struct tcrypt_algs *TCRYPT_get_algs(const char *cipher, const char *mode)
722 {
723         int i;
724
725         if (!cipher || !mode)
726                 return NULL;
727
728         for (i = 0; tcrypt_cipher[i].chain_count; i++)
729                 if (!strcmp(tcrypt_cipher[i].long_name, cipher) &&
730                     !strcmp(tcrypt_cipher[i].mode, mode))
731                     return &tcrypt_cipher[i];
732
733         return NULL;
734 }
735
736 int TCRYPT_activate(struct crypt_device *cd,
737                      const char *name,
738                      struct tcrypt_phdr *hdr,
739                      struct crypt_params_tcrypt *params,
740                      uint32_t flags)
741 {
742         char dm_name[PATH_MAX], dm_dev_name[PATH_MAX], cipher_spec[MAX_CIPHER_LEN*2+1];
743         char *part_path;
744         unsigned int i;
745         int r;
746         uint32_t req_flags, dmc_flags;
747         struct tcrypt_algs *algs;
748         enum devcheck device_check;
749         uint64_t offset = crypt_get_data_offset(cd);
750         struct volume_key *vk = NULL;
751         struct device  *ptr_dev = crypt_data_device(cd), *device = NULL, *part_device = NULL;
752         struct crypt_dm_active_device dmd = {
753                 .flags = flags
754         };
755
756         if (!hdr->d.version) {
757                 log_dbg(cd, "TCRYPT: this function is not supported without encrypted header load.");
758                 return -ENOTSUP;
759         }
760
761         if (hdr->d.sector_size % SECTOR_SIZE) {
762                 log_err(cd, _("Activation is not supported for %d sector size."),
763                         hdr->d.sector_size);
764                 return -ENOTSUP;
765         }
766
767         if (strstr(params->mode, "-tcrypt")) {
768                 log_err(cd, _("Kernel does not support activation for this TCRYPT legacy mode."));
769                 return -ENOTSUP;
770         }
771
772         if (strstr(params->mode, "-tcw"))
773                 req_flags = DM_TCW_SUPPORTED;
774         else
775                 req_flags = DM_PLAIN64_SUPPORTED;
776
777         algs = TCRYPT_get_algs(params->cipher, params->mode);
778         if (!algs)
779                 return -EINVAL;
780
781         if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER)
782                 dmd.size = 0;
783         else if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER)
784                 dmd.size = hdr->d.hidden_volume_size / SECTOR_SIZE;
785         else
786                 dmd.size = hdr->d.volume_size / SECTOR_SIZE;
787
788         if (dmd.flags & CRYPT_ACTIVATE_SHARED)
789                 device_check = DEV_OK;
790         else
791                 device_check = DEV_EXCL;
792
793         if ((params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) &&
794              !crypt_dev_is_partition(device_path(crypt_data_device(cd)))) {
795                 part_path = crypt_get_partition_device(device_path(crypt_data_device(cd)),
796                                                        crypt_get_data_offset(cd), dmd.size);
797                 if (part_path) {
798                         if (!device_alloc(cd, &part_device, part_path)) {
799                                 log_verbose(cd, _("Activating TCRYPT system encryption for partition %s."),
800                                             part_path);
801                                 ptr_dev = part_device;
802                                 offset = 0;
803                         }
804                         free(part_path);
805                 } else
806                         /*
807                          * System encryption use the whole device mapping, there can
808                          * be active partitions.
809                          */
810                         device_check = DEV_OK;
811         }
812
813         r = device_block_adjust(cd, ptr_dev, device_check,
814                                 offset, &dmd.size, &dmd.flags);
815         if (r)
816                 goto out;
817
818         /* From here, key size for every cipher must be the same */
819         vk = crypt_alloc_volume_key(algs->cipher[0].key_size +
820                                     algs->cipher[0].key_extra_size, NULL);
821         if (!vk) {
822                 r = -ENOMEM;
823                 goto out;
824         }
825
826         for (i = algs->chain_count; i > 0; i--) {
827                 if (i == 1) {
828                         dm_name[sizeof(dm_name)-1] = '\0';
829                         strncpy(dm_name, name, sizeof(dm_name)-1);
830                         dmd.flags = flags;
831                 } else {
832                         if (snprintf(dm_name, sizeof(dm_name), "%s_%d", name, i-1) < 0) {
833                                 r = -EINVAL;
834                                 break;
835                         }
836                         dmd.flags = flags | CRYPT_ACTIVATE_PRIVATE;
837                 }
838
839                 TCRYPT_copy_key(&algs->cipher[i-1], algs->mode,
840                                 vk->key, hdr->d.keys);
841
842                 if (algs->chain_count != i) {
843                         if (snprintf(dm_dev_name, sizeof(dm_dev_name), "%s/%s_%d", dm_get_dir(), name, i) < 0) {
844                                 r = -EINVAL;
845                                 break;
846                         }
847                         r = device_alloc(cd, &device, dm_dev_name);
848                         if (r)
849                                 break;
850                         ptr_dev = device;
851                         offset = 0;
852                 }
853
854                 r = snprintf(cipher_spec, sizeof(cipher_spec), "%s-%s", algs->cipher[i-1].name, algs->mode);
855                 if (r < 0 || (size_t)r >= sizeof(cipher_spec)) {
856                         r = -ENOMEM;
857                         break;
858                 }
859
860                 r = dm_crypt_target_set(&dmd.segment, 0, dmd.size, ptr_dev, vk,
861                                 cipher_spec, crypt_get_iv_offset(cd), offset,
862                                 crypt_get_integrity(cd),
863                                 crypt_get_integrity_tag_size(cd),
864                                 crypt_get_sector_size(cd));
865                 if (r)
866                         break;
867
868                 log_dbg(cd, "Trying to activate TCRYPT device %s using cipher %s.",
869                         dm_name, dmd.segment.u.crypt.cipher);
870                 r = dm_create_device(cd, dm_name, CRYPT_TCRYPT, &dmd);
871
872                 dm_targets_free(cd, &dmd);
873                 device_free(cd, device);
874                 device = NULL;
875
876                 if (r)
877                         break;
878         }
879
880         if (r < 0 &&
881             (dm_flags(cd, DM_CRYPT, &dmc_flags) || ((dmc_flags & req_flags) != req_flags))) {
882                 log_err(cd, _("Kernel does not support TCRYPT compatible mapping."));
883                 r = -ENOTSUP;
884         }
885
886 out:
887         crypt_free_volume_key(vk);
888         device_free(cd, device);
889         device_free(cd, part_device);
890         return r;
891 }
892
893 static int TCRYPT_remove_one(struct crypt_device *cd, const char *name,
894                       const char *base_uuid, int index, uint32_t flags)
895 {
896         struct crypt_dm_active_device dmd;
897         char dm_name[PATH_MAX];
898         int r;
899
900         if (snprintf(dm_name, sizeof(dm_name), "%s_%d", name, index) < 0)
901                 return -ENOMEM;
902
903         r = dm_status_device(cd, dm_name);
904         if (r < 0)
905                 return r;
906
907         r = dm_query_device(cd, dm_name, DM_ACTIVE_UUID, &dmd);
908         if (!r && !strncmp(dmd.uuid, base_uuid, strlen(base_uuid)))
909                 r = dm_remove_device(cd, dm_name, flags);
910
911         free(CONST_CAST(void*)dmd.uuid);
912         return r;
913 }
914
915 int TCRYPT_deactivate(struct crypt_device *cd, const char *name, uint32_t flags)
916 {
917         struct crypt_dm_active_device dmd;
918         int r;
919
920         r = dm_query_device(cd, name, DM_ACTIVE_UUID, &dmd);
921         if (r < 0)
922                 return r;
923         if (!dmd.uuid)
924                 return -EINVAL;
925
926         r = dm_remove_device(cd, name, flags);
927         if (r < 0)
928                 goto out;
929
930         r = TCRYPT_remove_one(cd, name, dmd.uuid, 1, flags);
931         if (r < 0)
932                 goto out;
933
934         r = TCRYPT_remove_one(cd, name, dmd.uuid, 2, flags);
935 out:
936         free(CONST_CAST(void*)dmd.uuid);
937         return (r == -ENODEV) ? 0 : r;
938 }
939
940 static int TCRYPT_status_one(struct crypt_device *cd, const char *name,
941                              const char *base_uuid, int index,
942                              size_t *key_size, char *cipher,
943                              struct tcrypt_phdr *tcrypt_hdr,
944                              struct device **device)
945 {
946         struct crypt_dm_active_device dmd;
947         struct dm_target *tgt = &dmd.segment;
948         char dm_name[PATH_MAX], *c;
949         int r;
950
951         if (snprintf(dm_name, sizeof(dm_name), "%s_%d", name, index) < 0)
952                 return -ENOMEM;
953
954         r = dm_status_device(cd, dm_name);
955         if (r < 0)
956                 return r;
957
958         r = dm_query_device(cd, dm_name, DM_ACTIVE_DEVICE |
959                                           DM_ACTIVE_UUID |
960                                           DM_ACTIVE_CRYPT_CIPHER |
961                                           DM_ACTIVE_CRYPT_KEYSIZE, &dmd);
962         if (r < 0)
963                 return r;
964         if (!single_segment(&dmd) || tgt->type != DM_CRYPT) {
965                 r = -ENOTSUP;
966                 goto out;
967         }
968
969         r = 0;
970
971         if (!strncmp(dmd.uuid, base_uuid, strlen(base_uuid))) {
972                 if ((c = strchr(tgt->u.crypt.cipher, '-')))
973                         *c = '\0';
974                 strcat(cipher, "-");
975                 strncat(cipher, tgt->u.crypt.cipher, MAX_CIPHER_LEN);
976                 *key_size += tgt->u.crypt.vk->keylength;
977                 tcrypt_hdr->d.mk_offset = tgt->u.crypt.offset * SECTOR_SIZE;
978                 device_free(cd, *device);
979                 MOVE_REF(*device, tgt->data_device);
980         } else
981                 r = -ENODEV;
982 out:
983         dm_targets_free(cd, &dmd);
984         free(CONST_CAST(void*)dmd.uuid);
985         return r;
986 }
987
988 int TCRYPT_init_by_name(struct crypt_device *cd, const char *name,
989                         const char *uuid,
990                         const struct dm_target *tgt,
991                         struct device **device,
992                         struct crypt_params_tcrypt *tcrypt_params,
993                         struct tcrypt_phdr *tcrypt_hdr)
994 {
995         struct tcrypt_algs *algs;
996         char cipher[MAX_CIPHER_LEN * 4], mode[MAX_CIPHER_LEN+1], *tmp;
997         size_t key_size;
998         int r;
999
1000         memset(tcrypt_params, 0, sizeof(*tcrypt_params));
1001         memset(tcrypt_hdr, 0, sizeof(*tcrypt_hdr));
1002         tcrypt_hdr->d.sector_size = SECTOR_SIZE;
1003         tcrypt_hdr->d.mk_offset = tgt->u.crypt.offset * SECTOR_SIZE;
1004
1005         strncpy(cipher, tgt->u.crypt.cipher, MAX_CIPHER_LEN);
1006         tmp = strchr(cipher, '-');
1007         if (!tmp)
1008                 return -EINVAL;
1009         *tmp = '\0';
1010         mode[MAX_CIPHER_LEN] = '\0';
1011         strncpy(mode, ++tmp, MAX_CIPHER_LEN);
1012
1013         key_size = tgt->u.crypt.vk->keylength;
1014         r = TCRYPT_status_one(cd, name, uuid, 1, &key_size,
1015                               cipher, tcrypt_hdr, device);
1016         if (!r)
1017                 r = TCRYPT_status_one(cd, name, uuid, 2, &key_size,
1018                                       cipher, tcrypt_hdr, device);
1019
1020         if (r < 0 && r != -ENODEV)
1021                 return r;
1022
1023         algs = TCRYPT_get_algs(cipher, mode);
1024         if (!algs || key_size != algs->chain_key_size)
1025                 return -EINVAL;
1026
1027         tcrypt_params->key_size = algs->chain_key_size;
1028         tcrypt_params->cipher = algs->long_name;
1029         tcrypt_params->mode = algs->mode;
1030         return 0;
1031 }
1032
1033 uint64_t TCRYPT_get_data_offset(struct crypt_device *cd,
1034                                  struct tcrypt_phdr *hdr,
1035                                  struct crypt_params_tcrypt *params)
1036 {
1037         uint64_t size;
1038
1039         if (!hdr->d.version) {
1040                 /* No real header loaded, initialized by active device, use default mk_offset */
1041         } else if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER) {
1042                 /* Mapping through whole device, not partition! */
1043                 if (crypt_dev_is_partition(device_path(crypt_data_device(cd))))
1044                         return 0;
1045         } else if (params->mode && !strncmp(params->mode, "xts", 3)) {
1046                 if (hdr->d.version < 3)
1047                         return 1;
1048
1049                 if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER) {
1050                         if (hdr->d.version > 3)
1051                                 return (hdr->d.mk_offset / SECTOR_SIZE);
1052                         if (device_size(crypt_metadata_device(cd), &size) < 0)
1053                                 return 0;
1054                         return (size - hdr->d.hidden_volume_size +
1055                                 (TCRYPT_HDR_HIDDEN_OFFSET_OLD)) / SECTOR_SIZE;
1056                 }
1057         } else if (params->flags & CRYPT_TCRYPT_HIDDEN_HEADER) {
1058                 if (device_size(crypt_metadata_device(cd), &size) < 0)
1059                         return 0;
1060                 return (size - hdr->d.hidden_volume_size +
1061                         (TCRYPT_HDR_HIDDEN_OFFSET_OLD)) / SECTOR_SIZE;
1062         }
1063
1064         return hdr->d.mk_offset / SECTOR_SIZE;
1065 }
1066
1067 uint64_t TCRYPT_get_iv_offset(struct crypt_device *cd,
1068                               struct tcrypt_phdr *hdr,
1069                               struct crypt_params_tcrypt *params)
1070 {
1071         uint64_t iv_offset;
1072
1073         if (params->mode && !strncmp(params->mode, "xts", 3))
1074                 iv_offset = TCRYPT_get_data_offset(cd, hdr, params);
1075         else if (params->mode && !strncmp(params->mode, "lrw", 3))
1076                 iv_offset = 0;
1077         else
1078                 iv_offset = hdr->d.mk_offset / SECTOR_SIZE;
1079
1080         if (params->flags & CRYPT_TCRYPT_SYSTEM_HEADER)
1081                 iv_offset += crypt_dev_partition_offset(device_path(crypt_data_device(cd)));
1082
1083         return iv_offset;
1084 }
1085
1086 int TCRYPT_get_volume_key(struct crypt_device *cd,
1087                           struct tcrypt_phdr *hdr,
1088                           struct crypt_params_tcrypt *params,
1089                           struct volume_key **vk)
1090 {
1091         struct tcrypt_algs *algs;
1092         unsigned int i, key_index;
1093
1094         if (!hdr->d.version) {
1095                 log_err(cd, _("This function is not supported without TCRYPT header load."));
1096                 return -ENOTSUP;
1097         }
1098
1099         algs = TCRYPT_get_algs(params->cipher, params->mode);
1100         if (!algs)
1101                 return -EINVAL;
1102
1103         *vk = crypt_alloc_volume_key(params->key_size, NULL);
1104         if (!*vk)
1105                 return -ENOMEM;
1106
1107         for (i = 0, key_index = 0; i < algs->chain_count; i++) {
1108                 TCRYPT_copy_key(&algs->cipher[i], algs->mode,
1109                                 &(*vk)->key[key_index], hdr->d.keys);
1110                 key_index += algs->cipher[i].key_size;
1111         }
1112
1113         return 0;
1114 }
1115
1116 int TCRYPT_dump(struct crypt_device *cd,
1117                 struct tcrypt_phdr *hdr,
1118                 struct crypt_params_tcrypt *params)
1119 {
1120         log_std(cd, "%s header information for %s\n",
1121                 hdr->d.magic[0] == 'T' ? "TCRYPT" : "VERACRYPT",
1122                 device_path(crypt_metadata_device(cd)));
1123         if (hdr->d.version) {
1124                 log_std(cd, "Version:       \t%d\n", hdr->d.version);
1125                 log_std(cd, "Driver req.:\t%x.%x\n", hdr->d.version_tc >> 8,
1126                                                     hdr->d.version_tc & 0xFF);
1127
1128                 log_std(cd, "Sector size:\t%" PRIu32 "\n", hdr->d.sector_size);
1129                 log_std(cd, "MK offset:\t%" PRIu64 "\n", hdr->d.mk_offset);
1130                 log_std(cd, "PBKDF2 hash:\t%s\n", params->hash_name);
1131         }
1132         log_std(cd, "Cipher chain:\t%s\n", params->cipher);
1133         log_std(cd, "Cipher mode:\t%s\n", params->mode);
1134         log_std(cd, "MK bits:       \t%zu\n", params->key_size * 8);
1135         return 0;
1136 }