X-Git-Url: https://jxself.org/git/?a=blobdiff_plain;f=tfcrypt.c;h=07939a74ddbd8de92cf40b8cfeab539bdb0b0e8a;hb=2da8baf01e863c80eccdeb5f428f16e1cf3a0473;hp=6e30bc6e46ad06b2e8edc39fac635a8d12410add;hpb=87d683181cc464de9b1d48483b72533aa9166cd3;p=tfcrypt.git diff --git a/tfcrypt.c b/tfcrypt.c index 6e30bc6..07939a7 100644 --- a/tfcrypt.c +++ b/tfcrypt.c @@ -63,8 +63,11 @@ int main(int argc, char **argv) if (!isatty(2)) do_statline_dynamic = NO; opterr = 0; - while ((c = getopt(argc, argv, "aU:C:r:K:t:TPkzxc:l:qedn:vV:pwE:O:S:AmM:R:Z:WHD:")) != -1) { + while ((c = getopt(argc, argv, "s:aU:C:r:K:t:TPkzxc:l:qedn:vV:pwE:O:S:AmM:R:Z:WHD:")) != -1) { switch (c) { + case 's': + saltf = optarg; + break; case 'r': randsource = optarg; break; @@ -143,6 +146,7 @@ int main(int argc, char **argv) tweakf = optarg; break; case 'T': + tfc_saltsz = 0; do_tfcrypt1 = YES; break; case 'l': @@ -173,6 +177,8 @@ int main(int argc, char **argv) error_action = TFC_ERRACT_CONT; else if (!strcmp(optarg, "sync")) error_action = TFC_ERRACT_SYNC; + else if (!strcmp(optarg, "lsync")) + error_action = TFC_ERRACT_LSYNC; else xerror(NO, YES, YES, "invalid error action %s specified", optarg); break; case 'O': @@ -466,6 +472,23 @@ int main(int argc, char **argv) errno = 0; do_stop = NO; + if (saltf) { + int saltfd; + + memset(tfc_salt, 0, TFC_MAX_SALT); + tfc_saltsz = 0; + if (!strcasecmp(saltf, "disable")) goto _nosalt; + + if (!strcmp(saltf, "-")) saltfd = 0; + else saltfd = open(saltf, O_RDONLY | O_LARGEFILE); + if (saltfd == -1) xerror(NO, NO, YES, "%s", saltf); + lio = read(saltfd, tfc_salt, TFC_MAX_SALT - TF_FROM_BITS(TFC_KEY_BITS)); + if (lio == NOSIZE) xerror(NO, NO, YES, "%s", saltf); + tfc_saltsz = lio; + xclose(saltfd); + } + +_nosalt: if (mackey_opt == TFC_MACKEY_FILE && mackeyf) { int mkfd = -1; tfc_yesno do_stop; @@ -482,6 +505,7 @@ int main(int argc, char **argv) pblk = tmpdata; ldone = 0; lrem = lblock = sizeof(tmpdata); + if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(mkfd); _mkragain: lio = read(mkfd, pblk, lrem); if (lio == 0) do_stop = YES; if (lio != NOSIZE) ldone += lio; @@ -491,10 +515,12 @@ _mkragain: lio = read(mkfd, pblk, lrem); switch (error_action) { case TFC_ERRACT_CONT: xerror(YES, NO, NO, "%s", mackeyf); goto _mkragain; break; case TFC_ERRACT_SYNC: + case TFC_ERRACT_LSYNC: xerror(YES, NO, NO, "%s", mackeyf); lio = ldone = lrem = lblock; memset(tmpdata, 0, lio); - lseek(mkfd, lio, SEEK_CUR); + if (rdpos == NOFSIZE) lseek(mkfd, lio, SEEK_CUR); + else lseek(mkfd, rdpos + lio, SEEK_SET); break; default: xerror(NO, NO, NO, "%s", mackeyf); break; } @@ -625,6 +651,7 @@ _nokeyfd: pblk = ctr; ldone = 0; lrem = lblock = ctrsz; + if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(sfd); _ctrragain: lio = read(sfd, pblk, lrem); if (lio != NOSIZE) ldone += lio; else { @@ -633,10 +660,12 @@ _ctrragain: lio = read(sfd, pblk, lrem); switch (error_action) { case TFC_ERRACT_CONT: xerror(YES, NO, NO, "%s", srcfname); goto _ctrragain; break; case TFC_ERRACT_SYNC: + case TFC_ERRACT_LSYNC: xerror(YES, NO, NO, "%s", srcfname); lio = ldone = lrem = lblock; memset(ctr, 0, lio); - lseek(sfd, lio, SEEK_CUR); + if (rdpos == NOFSIZE) lseek(sfd, lio, SEEK_CUR); + else lseek(sfd, rdpos + lio, SEEK_SET); break; default: xerror(NO, NO, NO, "%s", srcfname); break; } @@ -667,6 +696,7 @@ _ctrskip1: pblk = key; _xts2key: ldone = 0; lrem = lblock = TF_FROM_BITS(TFC_KEY_BITS); + if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(kfd); _keyragain: lio = read(kfd, pblk, lrem); if (lio != NOSIZE) ldone += lio; else { @@ -675,10 +705,12 @@ _keyragain: lio = read(kfd, pblk, lrem); switch (error_action) { case TFC_ERRACT_CONT: xerror(YES, NO, NO, "reading key"); goto _keyragain; break; case TFC_ERRACT_SYNC: + case TFC_ERRACT_LSYNC: xerror(YES, NO, NO, "reading key"); lio = ldone = lrem = lblock; memset(key, 0, lio); - lseek(kfd, lio, SEEK_CUR); + if (rdpos == NOFSIZE) lseek(kfd, lio, SEEK_CUR); + else lseek(kfd, rdpos + lio, SEEK_SET); break; default: xerror(NO, NO, NO, "reading key"); break; } @@ -786,9 +818,14 @@ _pwdagain: memset(&getps, 0, sizeof(struct getpasswd_state)); xerror(NO, NO, YES, "hashing key"); } - if (nr_turns > 1 && rawkey == NO) { - for (x = 0; x < nr_turns; x++) + if (rawkey == NO) { + if (tfc_saltsz > 0) { + memcpy(tfc_salt+tfc_saltsz, key, TF_FROM_BITS(TFC_KEY_BITS)); + skein(key, TFC_KEY_BITS, mackey_opt ? mackey : NULL, tfc_salt, tfc_saltsz+TF_FROM_BITS(TFC_KEY_BITS)); + } + if (nr_turns > 1) for (x = 0; x < nr_turns; x++) skein(key, TFC_KEY_BITS, mackey_opt ? mackey : NULL, key, TF_FROM_BITS(TFC_KEY_BITS)); + memset(tfc_salt, 0, TFC_MAX_SALT); } if (ctr_mode == TFC_MODE_XTS && rawkey == NO) { @@ -943,6 +980,7 @@ _ctrwagain: lio = write(dfd, pblk, lrem); pblk = srcblk; ldone = 0; lrem = lblock = blk_len_adj(maxlen, total_processed_src, blksize); + if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(sfd); _ragain: lio = read(sfd, pblk, lrem); if (lio == 0) do_stop = TFC_STOP_BEGAN; if (lio != NOSIZE) ldone += lio; @@ -952,10 +990,12 @@ _ragain: lio = read(sfd, pblk, lrem); switch (error_action) { case TFC_ERRACT_CONT: xerror(YES, NO, NO, "%s", srcfname); goto _ragain; break; case TFC_ERRACT_SYNC: + case TFC_ERRACT_LSYNC: xerror(YES, NO, NO, "%s", srcfname); lio = ldone = lrem = lblock; memset(srcblk, 0, lio); - lseek(sfd, lio, SEEK_CUR); + if (rdpos == NOFSIZE) lseek(sfd, lio, SEEK_CUR); + else lseek(sfd, rdpos + lio, SEEK_SET); break; default: xerror(NO, NO, NO, "%s", srcfname); break; } @@ -1030,6 +1070,7 @@ _nowrite: total_processed_dst += ldone; pblk = macvrfy; ldone = 0; lrem = lblock = TF_FROM_BITS(macbits); + if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(sfd); _macragain: lio = read(sfd, pblk, lrem); if (lio != NOSIZE) ldone += lio; else { @@ -1038,10 +1079,12 @@ _macragain: lio = read(sfd, pblk, lrem); switch (error_action) { case TFC_ERRACT_CONT: xerror(YES, NO, NO, "%s", srcfname); goto _macragain; break; case TFC_ERRACT_SYNC: + case TFC_ERRACT_LSYNC: xerror(YES, NO, NO, "%s", srcfname); lio = ldone = lrem = lblock; memset(macvrfy, 0, lio); - lseek(sfd, lio, SEEK_CUR); + if (rdpos == NOFSIZE) lseek(sfd, lio, SEEK_CUR); + else lseek(sfd, rdpos + lio, SEEK_SET); break; default: xerror(NO, NO, NO, "%s", srcfname); break; }