2 * tfcrypt -- high security Threefish encryption tool.
4 * tfcrypt is copyrighted:
5 * Copyright (C) 2012-2019 Andrey Rys. All rights reserved.
7 * tfcrypt is licensed to you under the terms of std. MIT/X11 license:
9 * Permission is hereby granted, free of charge, to any person obtaining
10 * a copy of this software and associated documentation files (the
11 * "Software"), to deal in the Software without restriction, including
12 * without limitation the rights to use, copy, modify, merge, publish,
13 * distribute, sublicense, and/or sell copies of the Software, and to
14 * permit persons to whom the Software is furnished to do so, subject to
15 * the following conditions:
17 * The above copyright notice and this permission notice shall be
18 * included in all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
21 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
22 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
23 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
24 * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
25 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
26 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31 enum { TFB64_STOP1 = 1, TFB64_STOPF };
33 void do_edbase64(char **fargv)
35 struct base64_decodestate dstate;
36 struct base64_encodestate estate;
42 if (!strcmp(fargv[0], "-")) sfd = 0;
44 sfd = open(fargv[0], O_RDONLY | O_LARGEFILE);
45 if (do_preserve_time) if (fstat(sfd, &s_stat) == -1)
46 xerror(YES, NO, YES, "stat(%s)", fargv[0]);
48 if (sfd == -1) xerror(NO, NO, YES, "%s", fargv[0]);
51 if (fargv[0] && fargv[1]) {
52 if (!strcmp(fargv[1], "-")) dfd = 1;
53 else dfd = open(fargv[1], O_WRONLY | O_CREAT | O_LARGEFILE | write_flags, 0666);
54 if (dfd == -1) xerror(NO, NO, YES, "%s", fargv[1]);
57 if (do_edcrypt == TFC_DO_ENCRYPT) {
58 memset(&estate, 0, sizeof(struct base64_encodestate));
59 base64_init_encodestate(&estate);
61 else if (do_edcrypt == TFC_DO_DECRYPT) {
62 memset(&dstate, 0, sizeof(struct base64_decodestate));
63 base64_init_decodestate(&dstate);
71 lblock = lrem = do_edcrypt == TFC_DO_DECRYPT ? TFC_B64_DWIDTH : TFC_B64_EWIDTH;
73 if (error_action == TFC_ERRACT_SYNC) rdpos = tfc_fdgetpos(sfd);
74 _again: lio = xread(sfd, pblk, lrem);
75 if (lio == 0) do_stop = TFB64_STOP1;
76 if (lio != NOSIZE) ldone += lio;
78 if (errno != EIO && catch_all_errors != YES)
79 xerror(NO, NO, NO, "%s", fargv[0]);
80 switch (error_action) {
81 case TFC_ERRACT_CONT: xerror(YES, NO, NO, "%s", fargv[0]); goto _again; break;
83 case TFC_ERRACT_LSYNC:
84 xerror(YES, NO, NO, "%s", fargv[0]);
85 lio = ldone = lrem = lblock;
86 memset(srcblk, 0, lio);
87 if (rdpos == NOFSIZE) lseek(sfd, lio, SEEK_CUR);
88 else lseek(sfd, rdpos + lio, SEEK_SET);
90 default: xerror(NO, NO, NO, "%s", fargv[0]); break;
93 if (lio && lio < lrem) {
99 if (do_edcrypt == TFC_DO_ENCRYPT) {
101 base64_encode_block((const char *)srcblk, ldone, (char *)dstblk, &estate);
103 ldone = estate.count;
105 else if (do_edcrypt == TFC_DO_DECRYPT) {
107 base64_decode_block((const char *)srcblk, ldone, (char *)dstblk, sizeof(dstblk), &dstate);
108 ldone = dstate.count;
113 do_stop = TFB64_STOPF;
118 _wagain: lio = xwrite(dfd, pblk, lrem);
119 if (lio != NOSIZE) ldone += lio;
120 else xerror(NO, NO, NO, "%s", fargv[1]);
121 if (do_edcrypt == TFC_DO_ENCRYPT) {
123 if (lread >= lblock || do_stop == TFB64_STOPF) {
124 t = xwrite(dfd, "\n", 1);
125 if (t != NOSIZE) lio += t;
129 if (lio != NOSIZE) ldone += lio;
130 else xerror(NO, NO, NO, "%s", fargv[1]);
131 if (do_fsync && fsync(dfd) == -1) xerror(NO, NO, NO, "%s", fargv[1]);
139 if (do_edcrypt == TFC_DO_ENCRYPT && do_stop == TFB64_STOP1) {
140 size_t t = estate.count;
141 pblk = dstblk + estate.count;
142 base64_encode_blockend((char *)dstblk, &estate);
143 lrem = estate.count - t;
145 do_stop = TFB64_STOPF;
149 memset(&estate, 0, sizeof(struct base64_encodestate));
150 memset(&dstate, 0, sizeof(struct base64_decodestate));
151 if (do_preserve_time) fcopy_matime(dfd, &s_stat);
155 static void base64_eprint(FILE *where, struct base64_encodestate *estate, const char *input, size_t inputl)
161 memset(t, 0, sizeof(t));
163 base64_encode_block(input, ix > 128 ? 128 : ix, t, estate);
165 if (ix < 128) base64_encode_blockend(t, estate);
166 fprintf(where, "%s", t);
170 memset(t, 0, sizeof(t));
173 void tfc_printbase64(FILE *where, const void *p, size_t n, tfc_yesno nl)
175 struct base64_encodestate estate;
176 memset(&estate, 0, sizeof(struct base64_encodestate));
177 base64_eprint(where, &estate, (const char *)p, n);
178 if (nl) tfc_nfsay(where, "\n");