Commit | Line | Data |
---|---|---|
19220671 MW |
1 | /* -*-c-*- |
2 | * | |
3 | * Various unit-level tests | |
4 | * | |
5 | * (c) 2017 Straylight/Edgeware | |
6 | */ | |
7 | ||
8 | /*----- Licensing notice --------------------------------------------------* | |
9 | * | |
10 | * This file is part of Trivial IP Encryption (TrIPE). | |
11 | * | |
12 | * TrIPE is free software: you can redistribute it and/or modify it under | |
13 | * the terms of the GNU General Public License as published by the Free | |
14 | * Software Foundation; either version 3 of the License, or (at your | |
15 | * option) any later version. | |
16 | * | |
17 | * TrIPE is distributed in the hope that it will be useful, but WITHOUT | |
18 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
19 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
20 | * for more details. | |
21 | * | |
22 | * You should have received a copy of the GNU General Public License | |
23 | * along with TrIPE. If not, see <https://www.gnu.org/licenses/>. | |
24 | */ | |
25 | ||
26 | /*----- Header files ------------------------------------------------------*/ | |
27 | ||
28 | #include "tripe.h" | |
29 | ||
30 | /*----- Data structures ---------------------------------------------------*/ | |
31 | ||
32 | /*----- Global variables --------------------------------------------------*/ | |
33 | ||
34 | sel_state sel; | |
35 | ||
36 | /*----- Static variables --------------------------------------------------*/ | |
37 | ||
38 | static char **args; | |
39 | ||
40 | /*----- Main code ---------------------------------------------------------*/ | |
41 | ||
42 | static void usage(FILE *fp) | |
43 | { | |
44 | pquis(fp, | |
45 | "Usage: $ [-k FILE] [-t KEYTAG] [-T TRACE-OPTS] COMMAND [ARGS...]\n"); | |
46 | } | |
47 | ||
48 | static void version(FILE *fp) | |
49 | { pquis(fp, "$, TrIPE version " VERSION "\n"); } | |
50 | ||
51 | static void help(FILE *fp) | |
52 | { | |
53 | version(fp); fputc('\n', fp); | |
54 | usage(fp); fputc('\n', fp); | |
55 | fputs("\ | |
56 | Options in full:\n\ | |
57 | \n\ | |
58 | -h, --help Show this help text.\n\ | |
59 | -v, --version Show version number.\n\ | |
60 | -u, --usage Show brief usage message.\n\ | |
61 | \n\ | |
62 | -k, --keyring=FILE Get keys from FILE.\n\ | |
63 | -t, --tag=KEYTAG Use KEYTAG as master private key.\n\ | |
64 | -T, --trace=TRACE-OPTS Turn on tracing options.\n\ | |
65 | \n\ | |
66 | Commands:\n\ | |
67 | \n\ | |
68 | ies-encrypt TY MESSAGE\n\ | |
69 | ies-decrypt TY CIPHERTEXT\n\ | |
70 | ", fp); | |
71 | } | |
72 | ||
73 | static uint32 parseu32(const char *p) | |
74 | { | |
75 | int e = errno; | |
76 | unsigned long i; | |
77 | char *q; | |
78 | ||
79 | errno = 0; | |
80 | i = strtoul(p, &q, 0); | |
81 | while (*q && isspace((unsigned char)*q)) q++; | |
82 | if (errno || *q || i > 0xffffffffu) die(2, "bad 32-bit integer `%s'", p); | |
83 | errno = e; | |
84 | return (i); | |
85 | } | |
86 | ||
87 | static const char *getarg(void) | |
88 | { if (!*args) die(2, "missing argument"); else return (*args++); } | |
89 | ||
90 | static void lastarg(void) | |
91 | { if (*args) die(2, "unexpected argument `%s'", *args); } | |
92 | ||
93 | int main(int argc, char *argv[]) | |
94 | { | |
95 | const char *kr = "keyring"; | |
96 | const char *tag = "tripe"; | |
97 | const char *arg; | |
98 | codec *b64; | |
99 | int i, err; | |
100 | uint32 ty; | |
101 | buf b, bb; | |
102 | dstr d = DSTR_INIT; | |
103 | unsigned f = 0; | |
104 | #define f_bogus 1u | |
105 | ||
106 | ego(argv[0]); | |
107 | for (;;) { | |
108 | static const struct option opts[] = { | |
109 | { "help", 0, 0, 'h' }, | |
110 | { "version", 0, 0, 'v' }, | |
111 | { "usage", 0, 0, 'u' }, | |
112 | { "keyring", OPTF_ARGREQ, 0, 'k' }, | |
113 | { "tag", OPTF_ARGREQ, 0, 't' }, | |
114 | { "trace", OPTF_ARGREQ, 0, 'T' }, | |
115 | { 0, 0, 0, 0 } | |
116 | }; | |
117 | ||
118 | i = mdwopt(argc, argv, "hvuk:t:T:", opts, 0, 0, 0); if (i < 0) break; | |
119 | switch (i) { | |
120 | case 'h': help(stdout); exit(0); | |
121 | case 'v': version(stdout); exit(0); | |
122 | case 'u': usage(stdout); exit(0); | |
123 | case 'k': kr = optarg; break; | |
124 | case 't': tag = optarg; break; | |
125 | case 'T': | |
126 | tr_flags = traceopt(tr_opts, optarg, tr_flags, 0); | |
127 | break; | |
128 | default: f |= f_bogus; break; | |
129 | } | |
130 | } | |
131 | if (f&f_bogus) { usage(stderr); exit(2); } | |
132 | args = argv + optind; | |
133 | ||
134 | km_init(kr, kr, tag); | |
86b67990 | 135 | if (!master) die(3, "failed to load the master key"); |
fb9a33c0 MW |
136 | T( trace_on(stderr, tr_flags); |
137 | master->grp->ops->tracegrp(master->grp); | |
138 | master->algs.bulk->ops->tracealgs(master->algs.bulk); ) | |
19220671 MW |
139 | |
140 | arg = getarg(); | |
141 | if (strcmp(arg, "ies-encrypt") == 0) { | |
142 | arg = getarg(); ty = parseu32(arg); | |
143 | arg = getarg(); buf_init(&b, (/*unconst*/ octet *)arg, strlen(arg)); | |
144 | buf_init(&bb, buf_t, sizeof(buf_t)); | |
145 | lastarg(); | |
146 | if ((err = ies_encrypt(master, ty, &b, &bb)) != 0) | |
147 | die(3, "ies_encrypt failed: err = %d", err); | |
148 | b64 = base64_class.encoder(0, "\n", 72); | |
149 | if ((err = b64->ops->code(b64, BBASE(&bb), BLEN(&bb), &d)) != 0 || | |
150 | (err = b64->ops->code(b64, 0, 0, &d)) != 0) | |
151 | die(3, "base64 encoding failed: %s", codec_strerror(err)); | |
152 | b64->ops->destroy(b64); | |
153 | DPUTC(&d, '\n'); | |
154 | fwrite(d.buf, 1, d.len, stdout); | |
155 | dstr_destroy(&d); | |
156 | } else if (strcmp(arg, "ies-decrypt") == 0) { | |
157 | arg = getarg(); ty = parseu32(arg); | |
158 | arg = getarg(); | |
159 | b64 = base64_class.decoder(CDCF_IGNSPC | CDCF_IGNNEWL); | |
160 | if ((err = b64->ops->code(b64, arg, strlen(arg), &d)) != 0 || | |
161 | (err = b64->ops->code(b64, 0, 0, &d)) != 0) | |
162 | die(3, "base64 decoding failed: %s", codec_strerror(err)); | |
163 | b64->ops->destroy(b64); | |
164 | lastarg(); | |
165 | buf_init(&b, d.buf, d.len); buf_init(&bb, buf_t, sizeof(buf_t)); | |
166 | if ((err = ies_decrypt(master, ty, &b, &bb)) != 0) | |
167 | die(3, "ies_decrypt failed: err = %d", err); | |
168 | fwrite(BBASE(&bb), 1, BLEN(&bb), stdout); | |
169 | dstr_destroy(&d); | |
170 | } else | |
171 | die(2, "unknown command `%s'", arg); | |
172 | ||
173 | return (0); | |
174 | } | |
175 | ||
176 | /*----- That's all, folks -------------------------------------------------*/ |