summaryrefslogtreecommitdiff
path: root/tools/credman.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/credman.c')
-rw-r--r--tools/credman.c237
1 files changed, 237 insertions, 0 deletions
diff --git a/tools/credman.c b/tools/credman.c
new file mode 100644
index 0000000..08c9eb8
--- /dev/null
+++ b/tools/credman.c
@@ -0,0 +1,237 @@
1/*
2 * Copyright (c) 2019 Yubico AB. All rights reserved.
3 * Use of this source code is governed by a BSD-style
4 * license that can be found in the LICENSE file.
5 */
6
7#include <fido.h>
8#include <fido/credman.h>
9
10#include <stdbool.h>
11#include <stdio.h>
12#include <stdlib.h>
13#include <string.h>
14#ifdef HAVE_UNISTD_H
15#include <unistd.h>
16#endif
17
18#include "../openbsd-compat/openbsd-compat.h"
19#include "extern.h"
20
21int
22credman_get_metadata(fido_dev_t *dev, const char *path)
23{
24 fido_credman_metadata_t *metadata = NULL;
25 char pin[1024];
26 int r;
27
28 if ((metadata = fido_credman_metadata_new()) == NULL)
29 errx(1, "fido_credman_metadata_new");
30
31 read_pin(path, pin, sizeof(pin));
32 r = fido_credman_get_dev_metadata(dev, metadata, pin);
33 explicit_bzero(pin, sizeof(pin));
34
35 if (r != FIDO_OK)
36 errx(1, "fido_credman_get_dev_metadata: %s", fido_strerr(r));
37
38 printf("existing rk(s): %u\n",
39 (unsigned)fido_credman_rk_existing(metadata));
40 printf("possible rk(s): %u\n",
41 (unsigned)fido_credman_rk_remaining(metadata));
42
43 fido_credman_metadata_free(&metadata);
44 fido_dev_close(dev);
45 fido_dev_free(&dev);
46
47 exit(0);
48}
49
50static void
51print_rp(fido_credman_rp_t *rp, size_t idx)
52{
53 char *rp_id_hash = NULL;
54
55 if (base64_encode(fido_credman_rp_id_hash_ptr(rp, idx),
56 fido_credman_rp_id_hash_len(rp, idx), &rp_id_hash) < 0)
57 errx(1, "output error");
58
59 printf("%02u: %s %s\n", (unsigned)idx, rp_id_hash,
60 fido_credman_rp_id(rp, idx));
61
62 free(rp_id_hash);
63 rp_id_hash = NULL;
64}
65
66int
67credman_list_rp(char *path)
68{
69 fido_dev_t *dev = NULL;
70 fido_credman_rp_t *rp = NULL;
71 char pin[1024];
72 int r;
73
74 if (path == NULL)
75 usage();
76 if ((rp = fido_credman_rp_new()) == NULL)
77 errx(1, "fido_credman_rp_new");
78
79 dev = open_dev(path);
80 read_pin(path, pin, sizeof(pin));
81 r = fido_credman_get_dev_rp(dev, rp, pin);
82 explicit_bzero(pin, sizeof(pin));
83
84 if (r != FIDO_OK)
85 errx(1, "fido_credman_get_dev_rp: %s", fido_strerr(r));
86
87 for (size_t i = 0; i < fido_credman_rp_count(rp); i++)
88 print_rp(rp, i);
89
90 fido_credman_rp_free(&rp);
91 fido_dev_close(dev);
92 fido_dev_free(&dev);
93
94 exit(0);
95}
96
97static void
98print_rk(const fido_credman_rk_t *rk, size_t idx)
99{
100 const fido_cred_t *cred;
101 char *id = NULL;
102 char *user_id = NULL;
103 const char *type;
104
105 if ((cred = fido_credman_rk(rk, idx)) == NULL)
106 errx(1, "fido_credman_rk");
107 if (base64_encode(fido_cred_id_ptr(cred), fido_cred_id_len(cred),
108 &id) < 0 || base64_encode(fido_cred_user_id_ptr(cred),
109 fido_cred_user_id_len(cred), &user_id) < 0)
110 errx(1, "output error");
111
112 switch (fido_cred_type(cred)) {
113 case COSE_EDDSA:
114 type = "eddsa";
115 break;
116 case COSE_ES256:
117 type = "es256";
118 break;
119 case COSE_RS256:
120 type = "rs256";
121 break;
122 default:
123 type = "unknown";
124 break;
125 }
126
127 printf("%02u: %s %s (%s) %s\n", (unsigned)idx, id,
128 fido_cred_display_name(cred), user_id, type);
129
130 free(user_id);
131 free(id);
132 user_id = NULL;
133 id = NULL;
134}
135
136int
137credman_list_rk(char *path, const char *rp_id)
138{
139 fido_dev_t *dev = NULL;
140 fido_credman_rk_t *rk = NULL;
141 char pin[1024];
142 int r;
143
144 if (path == NULL)
145 usage();
146 if ((rk = fido_credman_rk_new()) == NULL)
147 errx(1, "fido_credman_rk_new");
148
149 dev = open_dev(path);
150 read_pin(path, pin, sizeof(pin));
151 r = fido_credman_get_dev_rk(dev, rp_id, rk, pin);
152 explicit_bzero(pin, sizeof(pin));
153
154 if (r != FIDO_OK)
155 errx(1, "fido_credman_get_dev_rk: %s", fido_strerr(r));
156 for (size_t i = 0; i < fido_credman_rk_count(rk); i++)
157 print_rk(rk, i);
158
159 fido_credman_rk_free(&rk);
160 fido_dev_close(dev);
161 fido_dev_free(&dev);
162
163 exit(0);
164}
165
166int
167credman_print_rk(fido_dev_t *dev, const char *path, char *rp_id, char *cred_id)
168{
169 const fido_cred_t *cred = NULL;
170 fido_credman_rk_t *rk = NULL;
171 char pin[1024];
172 void *cred_id_ptr = NULL;
173 size_t cred_id_len = 0;
174 int r;
175
176 if ((rk = fido_credman_rk_new()) == NULL)
177 errx(1, "fido_credman_rk_new");
178 if (base64_decode(cred_id, &cred_id_ptr, &cred_id_len) < 0)
179 errx(1, "base64_decode");
180
181 read_pin(path, pin, sizeof(pin));
182 r = fido_credman_get_dev_rk(dev, rp_id, rk, pin);
183 explicit_bzero(pin, sizeof(pin));
184
185 if (r != FIDO_OK)
186 errx(1, "fido_credman_get_dev_rk: %s", fido_strerr(r));
187
188 for (size_t i = 0; i < fido_credman_rk_count(rk); i++) {
189 if ((cred = fido_credman_rk(rk, i)) == NULL ||
190 fido_cred_id_ptr(cred) == NULL)
191 errx(1, "output error");
192 if (cred_id_len != fido_cred_id_len(cred) ||
193 memcmp(cred_id_ptr, fido_cred_id_ptr(cred), cred_id_len))
194 continue;
195 print_cred(stdout, fido_cred_type(cred), cred);
196 goto out;
197 }
198
199 errx(1, "credential not found");
200
201out:
202 free(cred_id_ptr);
203 cred_id_ptr = NULL;
204
205 fido_credman_rk_free(&rk);
206 fido_dev_close(dev);
207 fido_dev_free(&dev);
208
209 exit(0);
210}
211
212int
213credman_delete_rk(fido_dev_t *dev, const char *path, char *id)
214{
215 char pin[1024];
216 void *id_ptr = NULL;
217 size_t id_len = 0;
218 int r;
219
220 if (base64_decode(id, &id_ptr, &id_len) < 0)
221 errx(1, "base64_decode");
222
223 read_pin(path, pin, sizeof(pin));
224 r = fido_credman_del_dev_rk(dev, id_ptr, id_len, pin);
225 explicit_bzero(pin, sizeof(pin));
226
227 if (r != FIDO_OK)
228 errx(1, "fido_credman_del_dev_rk: %s", fido_strerr(r));
229
230 free(id_ptr);
231 id_ptr = NULL;
232
233 fido_dev_close(dev);
234 fido_dev_free(&dev);
235
236 exit(0);
237}