Import Upstream version 1.8.5
[hcoop/debian/openafs.git] / tests / auth / keys-t.c
1 /*
2 * Copyright (c) 2010 Your File System Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 *
13 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR `AS IS'' AND ANY EXPRESS OR
14 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
15 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
16 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
17 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
18 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
19 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
20 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
22 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23 */
24
25 /*!
26 * Tests for the afsconf key handling functions
27 */
28
29 #include <afsconfig.h>
30 #include <afs/param.h>
31
32 #include <roken.h>
33
34 #include <afs/cellconfig.h>
35 #include <afs/keys.h>
36 #include <afs/afsutil.h>
37 #include <rx/rxkad.h>
38
39 #include <tests/tap/basic.h>
40
41 #include "test.h"
42 #include "common.h"
43
44 static int
45 copy(char *inFile, char *outFile)
46 {
47 int in, out;
48 char *block, *block_out;
49 ssize_t len;
50 size_t len_out;
51
52 in = open(inFile, O_RDONLY);
53 if (in<0)
54 return EIO;
55
56 out = open(outFile, O_WRONLY | O_CREAT, 0600);
57 if (out<0)
58 return EIO;
59
60 block = malloc(1024);
61 do {
62 len = read(in, block, 1024);
63 if (len <= 0)
64 break;
65 len_out = len;
66 block_out = block;
67 do {
68 len = write(out, block_out, len_out);
69 if (len <= 0)
70 break;
71 block_out += len;
72 len_out -= len;
73 } while (len_out > 0);
74 } while (len > 0);
75 free(block);
76
77 close(in);
78 close(out);
79
80 if (len == -1)
81 return EIO;
82
83 return 0;
84 }
85
86 int
87 keyMatches(struct afsconf_typedKey *typedKey,
88 afsconf_keyType type, int kvno, int subType,
89 void *keyMaterial, size_t keyLen)
90 {
91 afsconf_keyType keyType;
92 int keyKvno;
93 int keySubType;
94 struct rx_opaque *buffer;
95
96 afsconf_typedKey_values(typedKey, &keyType, &keyKvno, &keySubType,
97 &buffer);
98
99 return (keyType == type && keyKvno == kvno && keySubType == subType &&
100 buffer->len == keyLen &&
101 memcmp(keyMaterial, buffer->val, buffer->len) == 0);
102 }
103
104 int main(int argc, char **argv)
105 {
106 struct afsconf_dir *dir;
107 struct afsconf_keys keys;
108 struct ktc_encryptionKey key;
109 struct rx_opaque *keyMaterial;
110 struct afsconf_typedKey *typedKey;
111 struct afsconf_typedKeyList *typedKeyList;
112 char *dirname;
113 char *keyfile;
114 char *keyfilesrc;
115 afs_int32 kvno;
116 int code;
117 int i;
118
119 afstest_SkipTestsIfBadHostname();
120
121 plan(134);
122
123 /* Create a temporary afs configuration directory */
124
125 dirname = afstest_BuildTestConfig();
126
127 if (asprintf(&keyfile, "%s/KeyFile", dirname) == -1)
128 goto out;
129
130 /* Work out the path to our KeyFile. If the test harness hasn't set
131 * the SOURCE environment variable, then assume it is in our CWD */
132 if (getenv("SOURCE") == NULL) {
133 keyfilesrc = strdup("KeyFile");
134 } else {
135 if (asprintf(&keyfilesrc, "%s/auth/KeyFile", getenv("SOURCE")) == -1)
136 goto out;
137 }
138
139 /* First, copy in a known keyfile */
140 code = copy(keyfilesrc, keyfile);
141 free(keyfilesrc);
142 if (code)
143 goto out;
144
145 /* Start with a blank configuration directory */
146 dir = afsconf_Open(dirname);
147 ok(dir != NULL, "Sucessfully re-opened config directory");
148 if (dir == NULL)
149 goto out;
150
151 /* Verify that GetKeys returns the entire set of keys correctly */
152 code = afsconf_GetKeys(dir, &keys);
153 is_int(0, code, "afsconf_GetKeys returns successfully");
154 is_int(3, keys.nkeys, "... and returns the right number of keys");
155 is_int(1, keys.key[0].kvno, " ... first key number is correct");
156 is_int(2, keys.key[1].kvno, " ... second key number is correct");
157 is_int(4, keys.key[2].kvno, " ... third key number is correct");
158 ok(memcmp(keys.key[0].key, "\x01\x02\x04\x08\x10\x20\x40\x80", 8) == 0,
159 " ... first key matches");
160 ok(memcmp(keys.key[1].key, "\x04\x04\x04\x04\x04\x04\x04\x04", 8) == 0,
161 " ... second key matches");
162 ok(memcmp(keys.key[2].key, "\x19\x16\xfe\xe6\xba\x77\x2f\xfd", 8) == 0,
163 " ... third key matches");
164
165 /* Verify that GetLatestKey returns the newest key */
166 code = afsconf_GetLatestKey(dir, &kvno, &key);
167 is_int(0, code, "afsconf_GetLatestKey returns sucessfully");
168 is_int(4, kvno, " ... with correct key number");
169 ok(memcmp(&key, "\x19\x16\xfe\xe6\xba\x77\x2f\xfd", 8) == 0,
170 " ... and correct key");
171
172 /* Check that GetLatestKey works if called with NULL parameters */
173 code = afsconf_GetLatestKey(dir, NULL, NULL);
174 is_int(0, code, "afsconf_GetLatestKey works if parameters are NULL");
175
176 /* Verify that random access using GetKey works properly */
177 code = afsconf_GetKey(dir, 2, &key);
178 is_int(0, code, "afsconf_GetKey returns successfully");
179 ok(memcmp(&key, "\x04\x04\x04\x04\x04\x04\x04\x04", 8) == 0,
180 " ... and with correct key");
181
182 /* And that it fails if the key number doesn't exist */
183 code = afsconf_GetKey(dir, 3, &key);
184 is_int(code, AFSCONF_NOTFOUND,
185 "afsconf_GetKey returns not found for missing key");
186
187 /* Check that AddKey can be used to add a new 'newest' key */
188 code = afsconf_AddKey(dir, 5, "\x08\x08\x08\x08\x08\x08\x08\x08", 0);
189 is_int(0, code, "afsconf_AddKey sucessfully adds a new key");
190
191 /* And that we can get it back with GetKeys, GetLatestKey and GetKey */
192 code = afsconf_GetKeys(dir, &keys);
193 is_int(0, code, " ... and GetKeys still works");
194 is_int(4, keys.nkeys, "... and has the correct number of keys");
195 is_int(5, keys.key[3].kvno, " ... and the fourth key has the correct kvno");
196 ok(memcmp(keys.key[3].key, "\x08\x08\x08\x08\x08\x08\x08\x08", 8) == 0,
197 " ... and is the correct key");
198
199 code = afsconf_GetLatestKey(dir, &kvno, &key);
200 is_int(0, code, " ... and GetLatestKey returns successfully");
201 is_int(5, kvno, " ... with the correct key number");
202 ok(memcmp(&key, "\x08\x08\x08\x08\x08\x08\x08\x08", 8) == 0,
203 " ... and the correct key");
204
205 code = afsconf_GetKey(dir, 5, &key);
206 is_int(0, code, " ... and GetKey still works");
207 ok(memcmp(&key, "\x08\x08\x08\x08\x08\x08\x08\x08", 8) == 0,
208 " ... and returns the correct key");
209
210 /* Check that AddKey without the overwrite flag won't overwrite an existing
211 * key */
212 code = afsconf_AddKey(dir, 5, "\x10\x10\x10\x10\x10\x10\x10", 0);
213 is_int(AFSCONF_KEYINUSE, code, "AddKey won't overwrite without being told to");
214
215 /* Check with GetKey that it didn't */
216 code = afsconf_GetKey(dir, 5, &key);
217 is_int(0, code, " ... and GetKey still works");
218 ok(memcmp(&key, "\x08\x08\x08\x08\x08\x08\x08\x08", 8) == 0,
219 " ... and key hasn't been overwritten");
220
221 /* Check that AddKey with the overwrite flag will overwrite an existing key */
222 code = afsconf_AddKey(dir, 5, "\x10\x10\x10\x10\x10\x10\x10\x10", 1);
223 is_int(0, code, "AddKey overwrites when asked");
224
225 /* Use GetKey to check that it did so */
226 code = afsconf_GetKey(dir, 5, &key);
227 is_int(0, code, " ... and GetKey still works");
228 ok(memcmp(&key, "\x10\x10\x10\x10\x10\x10\x10\x10", 8) == 0,
229 " ... and key has been overwritten");
230
231 /* Check that deleting a key that doesn't exist fails */
232 code = afsconf_DeleteKey(dir, 6);
233 is_int(AFSCONF_NOTFOUND, code,
234 "afsconf_DeleteKey returns NOTFOUND if key doesn't exist");
235
236 /* Check that we can delete a key using afsconf_DeleteKey */
237 code = afsconf_DeleteKey(dir, 2);
238 is_int(0, code, "afsconf_DeleteKey can delete a key");
239 code = afsconf_GetKey(dir, 2, &key);
240 is_int(AFSCONF_NOTFOUND, code, " ... and afsconf_GetKey can't find it");
241
242 /* Check that deleting it doesn't leave a hole in what GetKeys returns */
243 code = afsconf_GetKeys(dir, &keys);
244 is_int(0, code, "... and afsconf_GetKeys returns it");
245 is_int(3, keys.nkeys, "... and returns the right number of keys");
246 is_int(1, keys.key[0].kvno, " ... first key number is correct");
247 is_int(4, keys.key[1].kvno, " ... second key number is correct");
248 is_int(5, keys.key[2].kvno, " ... third key number is correct");
249
250 /* Make sure that if we drop the dir structure, and then rebuild it, we
251 * still have the same KeyFile */
252 afsconf_Close(dir);
253
254 dir = afsconf_Open(dirname);
255 ok(dir != NULL, "Sucessfully re-opened config directory");
256 if (dir == NULL)
257 goto out;
258
259 code = afsconf_GetKeys(dir, &keys);
260 is_int(0, code, "afsconf_GetKeys still works");
261 is_int(3, keys.nkeys, "... and returns the right number of keys");
262 is_int(1, keys.key[0].kvno, " ... first key number is correct");
263 is_int(4, keys.key[1].kvno, " ... second key number is correct");
264 is_int(5, keys.key[2].kvno, " ... third key number is correct");
265
266 /* Now check that we're limited to 8 keys */
267 for (i=0; i<5; i++) {
268 code = afsconf_AddKey(dir, 10+i, "\x10\x10\x10\x10\x10\x10\x10\x10",
269 0);
270 is_int(0, code, "Adding %dth key with AddKey works", i+4);
271 }
272 code = afsconf_AddKey(dir, 20, "\x10\x10\x10\x10\x10\x10\x10\x10",0);
273 is_int(AFSCONF_FULL, code, "afsconf_AddKey fails once we've got 8 keys");
274
275 /* Check that the new interface also fails when we've got too many
276 * keys */
277 keyMaterial = rx_opaque_new("\x10\x10\x10\x10\x10\x10\x10\x10", 8);
278 typedKey = afsconf_typedKey_new(afsconf_rxkad, 20, 0, keyMaterial);
279 rx_opaque_free(&keyMaterial);
280 code = afsconf_AddTypedKey(dir, typedKey, 0);
281 afsconf_typedKey_put(&typedKey);
282 is_int(AFSCONF_FULL, code,
283 "afsconf_AddTypedKey fails for rxkad once we've got 8 keys");
284
285 /* Check the new accessors work for rxkad keys */
286 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 4, 0, &typedKey);
287 is_int(0, code,
288 "afsconf_GetKeyByTypes works for rxkad");
289 ok(keyMatches(typedKey, afsconf_rxkad, 4, 0,
290 "\x19\x16\xfe\xe6\xba\x77\x2f\xfd", 8),
291 " ... and returned key matches");
292
293 afsconf_typedKey_put(&typedKey);
294
295 code = afsconf_GetKeysByType(dir, afsconf_rxkad, 4, &typedKeyList);
296 is_int(0, code,
297 "afsconf_GetKeysByType works for rxkad");
298 is_int(1, typedKeyList->nkeys,
299 " ... and returns 1 key, as expected");
300 ok(keyMatches(typedKeyList->keys[0], afsconf_rxkad, 4, 0,
301 "\x19\x16\xfe\xe6\xba\x77\x2f\xfd", 8),
302 " ... and returned key matches");
303
304 afsconf_PutTypedKeyList(&typedKeyList);
305
306 code = afsconf_GetLatestKeyByTypes(dir, afsconf_rxkad, 0, &typedKey);
307 is_int(0, code,
308 "afsconf_GetLatestKeyByTypes works for rxkad");
309 ok(keyMatches(typedKey, afsconf_rxkad, 14, 0,
310 "\x10\x10\x10\x10\x10\x10\x10\x10", 8),
311 " ... and returned key matches");
312
313 afsconf_typedKey_put(&typedKey);
314
315 code = afsconf_GetLatestKeysByType(dir, afsconf_rxkad, &typedKeyList);
316 is_int(0, code,
317 "afsconf_GetLatestKeysByType works for rxkad");
318 is_int(1, typedKeyList->nkeys,
319 " ... and returns 1 key, as expected");
320 ok(keyMatches(typedKeyList->keys[0], afsconf_rxkad, 14, 0,
321 "\x10\x10\x10\x10\x10\x10\x10\x10", 8),
322 " ... and returned key matches");
323 afsconf_PutTypedKeyList(&typedKeyList);
324
325 /* Check that we can't delete a key that doesn't exist */
326 code = afsconf_DeleteKeyByType(dir, afsconf_rxkad, 6);
327 is_int(AFSCONF_NOTFOUND, code,
328 "afsconf_DeleteKeyByType returns NOTFOUND if key doesn't exist");
329 code = afsconf_DeleteKeyBySubType(dir, afsconf_rxkad, 6, 0);
330 is_int(AFSCONF_NOTFOUND, code,
331 "afsconf_DeleteKeyBySubType returns NOTFOUND if key doesn't exist");
332 code = afsconf_DeleteKeyBySubType(dir, afsconf_rxkad, 14, 1);
333 is_int(AFSCONF_NOTFOUND, code,
334 "afsconf_DeleteKeyBySubType doesn't delete with wrong subtype");
335 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 14, 0, &typedKey);
336 is_int(0, code, " ... and key is still there!");
337 afsconf_typedKey_put(&typedKey);
338
339 /* Check that we can delete a key that does */
340 code = afsconf_DeleteKeyByType(dir, afsconf_rxkad, 13);
341 is_int(0, code, "afsconf_DeleteKeyByType works");
342 code = afsconf_GetKeysByType(dir, afsconf_rxkad, 13, &typedKeyList);
343 is_int(AFSCONF_NOTFOUND, code, " ... and is really gone");
344
345 code = afsconf_DeleteKeyBySubType(dir, afsconf_rxkad, 14, 0);
346 is_int(0, code, "afsconf_DeleteKeyBySubType works");
347 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 14, 0, &typedKey);
348 is_int(AFSCONF_NOTFOUND, code, " ... and is really gone");
349
350 /* Unlink the KeyFile */
351 unlink(keyfile);
352
353 /* Force a rebuild of the directory structure, just in case */
354 afsconf_Close(dir);
355
356 dir = afsconf_Open(dirname);
357 ok(dir != NULL, "Sucessfully re-opened config directory");
358 if (dir == NULL)
359 goto out;
360
361 /* Check that all of the various functions work properly if the file
362 * isn't there */
363 code = afsconf_GetKeys(dir, &keys);
364 is_int(0, code, "afsconf_GetKeys works with an empty KeyFile");
365 is_int(0, keys.nkeys, " ... and returns the right number of keys");
366 code = afsconf_GetKey(dir, 1, &key);
367 is_int(AFSCONF_NOTFOUND, code,
368 "afsconf_GetKey returns NOTFOUND with an empty KeyFile");
369 code = afsconf_DeleteKey(dir, 1);
370 is_int(AFSCONF_NOTFOUND, code,
371 "afsconf_DeleteKey returns NOTFOUND with an empty KeyFile");
372 code = afsconf_GetLatestKey(dir, &kvno, &key);
373 is_int(AFSCONF_NOTFOUND, code,
374 "afsconf_GetLatestKey returns NOTFOUND with an empty KeyFile");
375 code = afsconf_GetKeysByType(dir, afsconf_rxkad, 1, &typedKeyList);
376 is_int(AFSCONF_NOTFOUND, code,
377 "afsconf_GetKeysByType returns NOTFOUND with an empty KeyFile");
378 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 1, 0, &typedKey);
379 is_int(AFSCONF_NOTFOUND, code,
380 "afsconf_GetKeyByTypes returns NOTFOUND with an empty KeyFile");
381 code = afsconf_GetLatestKeysByType(dir, afsconf_rxkad, &typedKeyList);
382 is_int(AFSCONF_NOTFOUND, code,
383 "afsconf_GetLatestKeysByType returns NOTFOUND with empty KeyFile");
384 code = afsconf_GetLatestKeyByTypes(dir, afsconf_rxkad, 0, &typedKey);
385 is_int(AFSCONF_NOTFOUND, code,
386 "afsconf_GetLatestKeyByTypes returns NOTFOUND with empty KeyFile");
387
388 /* Now try adding a key to an empty file */
389 code = afsconf_AddKey(dir, 1, "\x10\x10\x10\x10\x10\x10\x10\x10", 1);
390 is_int(0, code, "afsconf_AddKey succeeds with an empty KeyFile");
391 code = afsconf_GetLatestKey(dir, &kvno, &key);
392 is_int(0, code, " ... and afsconf_GetLatestKey succeeds");
393 is_int(1, kvno, " ... with correct kvno");
394 ok(memcmp(&key, "\x10\x10\x10\x10\x10\x10\x10\x10", 8) == 0,
395 " ... and key");
396
397 /* And adding a key using the new interface */
398
399 keyMaterial = rx_opaque_new("\x20\x20\x20\x20\x20\x20\x20\x20", 8);
400 typedKey = afsconf_typedKey_new(afsconf_rxkad, 2, 0, keyMaterial);
401 rx_opaque_free(&keyMaterial);
402 code = afsconf_AddTypedKey(dir, typedKey, 0);
403 afsconf_typedKey_put(&typedKey);
404 is_int(0, code, "afsconf_AddTypedKey works");
405 code = afsconf_GetLatestKey(dir, &kvno, &key);
406 is_int(0, code, " ... and afsconf_GetLatestKey succeeds");
407 is_int(2, kvno, " ... with correct kvno");
408 ok(memcmp(&key, "\x20\x20\x20\x20\x20\x20\x20\x20", 8) == 0,
409 " ... and key");
410 code = afsconf_GetLatestKeyByTypes(dir, afsconf_rxkad, 0, &typedKey);
411 is_int(0, code, " ... and so does afsconf_GetLatestKeyByTypes");
412 ok(keyMatches(typedKey, afsconf_rxkad, 2, 0,
413 "\x20\x20\x20\x20\x20\x20\x20\x20", 8),
414 " ... with correct key");
415 afsconf_typedKey_put(&typedKey);
416
417 /* And that we can't add a key to an existing kvno and type */
418 keyMaterial = rx_opaque_new("\x30\x30\x30\x30\x30\x30\x30\x30", 8);
419 typedKey = afsconf_typedKey_new(afsconf_rxkad, 2, 0, keyMaterial);
420 rx_opaque_free(&keyMaterial);
421 code = afsconf_AddTypedKey(dir, typedKey, 0);
422 afsconf_typedKey_put(&typedKey);
423 is_int(AFSCONF_KEYINUSE, code,
424 "afsconf_AddTypedKey won't overwrite without being told to");
425 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 2, 0, &typedKey);
426 is_int(0, code, " ... and key still exists");
427 ok(keyMatches(typedKey, afsconf_rxkad, 2, 0,
428 "\x20\x20\x20\x20\x20\x20\x20\x20", 8),
429 " ... and hasn't changed");
430 afsconf_typedKey_put(&typedKey);
431
432 /* But we can if we force */
433 keyMaterial = rx_opaque_new("\x30\x30\x30\x30\x30\x30\x30\x30", 8);
434 typedKey = afsconf_typedKey_new(afsconf_rxkad, 2, 0, keyMaterial);
435 rx_opaque_free(&keyMaterial);
436 code = afsconf_AddTypedKey(dir, typedKey, 1);
437 afsconf_typedKey_put(&typedKey);
438 is_int(0, code, "afsconf_AddTypedKey overwrites when asked");
439 code = afsconf_GetKeyByTypes(dir, afsconf_rxkad, 2, 0, &typedKey);
440 is_int(0, code, " ... and GetKeyByTypes retrieves new key");
441 ok(keyMatches(typedKey, afsconf_rxkad, 2, 0,
442 "\x30\x30\x30\x30\x30\x30\x30\x30", 8),
443 " ... and it is the new key");
444
445 /* Check that we can't add bad rxkad keys */
446 keyMaterial = rx_opaque_new("\x30\x30\x30\x30\x30\x30\x30", 7);
447 typedKey = afsconf_typedKey_new(afsconf_rxkad, 3, 0, keyMaterial);
448 rx_opaque_free(&keyMaterial);
449 code = afsconf_AddTypedKey(dir, typedKey, 1);
450 afsconf_typedKey_put(&typedKey);
451 is_int(AFSCONF_BADKEY, code,
452 "afsconf_AddTypedKey won't add short rxkad keys");
453 keyMaterial = rx_opaque_new("\x30\x30\x30\x30\x30\x30\x30\x30\x30", 9);
454 typedKey = afsconf_typedKey_new(afsconf_rxkad, 3, 0, keyMaterial);
455 rx_opaque_free(&keyMaterial);
456 code = afsconf_AddTypedKey(dir, typedKey, 1);
457 afsconf_typedKey_put(&typedKey);
458 is_int(AFSCONF_BADKEY, code,
459 "afsconf_AddTypedKey won't add long rxkad keys");
460 keyMaterial = rx_opaque_new("\x30\x30\x30\x30\x30\x30\x30\x30", 8);
461 typedKey = afsconf_typedKey_new(afsconf_rxkad, 3, 1, keyMaterial);
462 rx_opaque_free(&keyMaterial);
463 code = afsconf_AddTypedKey(dir, typedKey, 1);
464 afsconf_typedKey_put(&typedKey);
465 is_int(AFSCONF_BADKEY, code,
466 "afsconf_AddTypedKey won't add rxkad keys with non-zero subtype");
467
468 /* Now, test things with other key types. */
469
470 /* Add a different key type, but with same kvno as rxkad */
471 keyMaterial = rx_opaque_new("\x01", 1);
472 typedKey = afsconf_typedKey_new(1, 2, 0, keyMaterial);
473 code = afsconf_AddTypedKey(dir, typedKey, 0);
474 afsconf_typedKey_put(&typedKey);
475 is_int(0, code,
476 "afsconf_AddTypedKey can add keys with different key type");
477
478 /* Add a different subtype, with same kvno */
479 keyMaterial = rx_opaque_new("\x02\x03", 2);
480 typedKey = afsconf_typedKey_new(1, 2, 1, keyMaterial);
481 code = afsconf_AddTypedKey(dir, typedKey, 0);
482 afsconf_typedKey_put(&typedKey);
483 is_int(0, code,
484 "afsconf_AddTypedKey can add keys with different sub type");
485
486 /* Check the GetKeyByTypes returns one of the keys */
487 code = afsconf_GetKeyByTypes(dir, 1, 2, 1, &typedKey);
488 is_int(0, code, "afsconf_GetKeyByTypes returns");
489 ok(keyMatches(typedKey, 1, 2, 1, "\x02\x03", 2),
490 " ... with the right key");
491
492 /* Check that GetKeysByType returns both of the keys */
493 code = afsconf_GetKeysByType(dir, 1, 2, &typedKeyList);
494 is_int(0, code, "afsconf_GetKeysByType returns");
495 is_int(2, typedKeyList->nkeys, " ... with correct number of keys");
496 ok(keyMatches(typedKeyList->keys[0], 1, 2, 0, "\x01", 1),
497 " ... with the right key in slot 0");
498 ok(keyMatches(typedKeyList->keys[1], 1, 2, 1, "\x02\x03", 2),
499 " ... with the right key in slot 1");
500 afsconf_PutTypedKeyList(&typedKeyList);
501
502 /* Add another key, before these ones, so we can check that
503 * latest really works */
504 keyMaterial = rx_opaque_new("\x03", 1);
505 typedKey = afsconf_typedKey_new(1, 1, 0, keyMaterial);
506 code = afsconf_AddTypedKey(dir, typedKey, 0);
507 afsconf_typedKey_put(&typedKey);
508 is_int(0, code, "afsconf_AddTypedKey worked again");
509
510 /* Check that GetLatestKeyByTypes returns one */
511 code = afsconf_GetLatestKeyByTypes(dir, 1, 1, &typedKey);
512 is_int(0, code, "afsconf_GetLatestKeyByTypes returns");
513 ok(keyMatches(typedKey, 1, 2, 1, "\x02\x03", 2),
514 " ... with the right key");
515
516 /* Check that GetLatestKeysByType returns both */
517 code = afsconf_GetLatestKeysByType(dir, 1, &typedKeyList);
518 is_int(0, code, "afsconf_GetLatestKeysByType returns");
519 is_int(2, typedKeyList->nkeys, " ... with correct number of keys");
520 ok(keyMatches(typedKeyList->keys[0], 1, 2, 0, "\x01", 1),
521 " ... with the right key in slot 0");
522 ok(keyMatches(typedKeyList->keys[1], 1, 2, 1, "\x02\x03", 2),
523 " ... with the right key in slot 1");
524 afsconf_PutTypedKeyList(&typedKeyList);
525
526 /* Check that closing this instance, and reopening, still has all of
527 * the required keys
528 */
529 afsconf_Close(dir);
530
531 dir = afsconf_Open(dirname);
532 ok(dir != NULL, "Sucessfully re-opened config directory");
533 if (dir == NULL)
534 goto out;
535
536 /* Check that GetKeysByType returns all of the keys */
537 code = afsconf_GetKeysByType(dir, 1, 1, &typedKeyList);
538 is_int(0, code, "afsconf_GetKeysByType returns after reopening");
539 is_int(1, typedKeyList->nkeys, " ... First kvno has correct number of keys");
540 ok(keyMatches(typedKeyList->keys[0], 1, 1, 0, "\x03", 1),
541 " ... and key material is correct");
542 afsconf_PutTypedKeyList(&typedKeyList);
543
544 code = afsconf_GetKeysByType(dir, 1, 2, &typedKeyList);
545 is_int(0, code, "afsconf_GetKeysByType returns after reopening");
546 is_int(2, typedKeyList->nkeys, " ... with correct number of keys");
547 ok(keyMatches(typedKeyList->keys[0], 1, 2, 0, "\x01", 1),
548 " ... with the right key in slot 0");
549 ok(keyMatches(typedKeyList->keys[1], 1, 2, 1, "\x02\x03", 2),
550 " ... with the right key in slot 1");
551 afsconf_PutTypedKeyList(&typedKeyList);
552
553 /* Check that GetAllKeys works as expected */
554 code = afsconf_GetAllKeys(dir, &typedKeyList);
555 is_int(0, code, "afsconf_GetAllKeys returns success");
556 is_int(5, typedKeyList->nkeys, " ... with the correct number of keys");
557 ok(keyMatches(typedKeyList->keys[0], afsconf_rxkad, 1, 0,
558 "\x10\x10\x10\x10\x10\x10\x10\x10", 8),
559 " ... with right key in slot 0");
560 ok(keyMatches(typedKeyList->keys[1], afsconf_rxkad, 2, 0,
561 "\x30\x30\x30\x30\x30\x30\x30\x30", 8),
562 " ... with right key in slot 1");
563 ok(keyMatches(typedKeyList->keys[2], 1, 1, 0, "\x03", 1),
564 " ... with right key in slot 2");
565 ok(keyMatches(typedKeyList->keys[3], 1, 2, 0, "\x01", 1),
566 " ... with right key in slot 3");
567 ok(keyMatches(typedKeyList->keys[4], 1, 2, 1, "\x02\03", 2),
568 " ... with right key in slot 4");
569
570 afsconf_Close(dir);
571
572 afstest_UnlinkTestConfig(dirname);
573 free(dirname);
574 free(keyfile);
575
576 /* Start a new test configuration */
577 dirname = afstest_BuildTestConfig();
578 dir = afsconf_Open(dirname);
579 ok(dir != NULL, "Sucessfully opened brand new config directory");
580 if (dir == NULL)
581 goto out;
582
583 /* Check that directories with just new style keys work */
584 keyMaterial = rx_opaque_new("\x02\x03", 2);
585 typedKey = afsconf_typedKey_new(1, 2, 1, keyMaterial);
586 code = afsconf_AddTypedKey(dir, typedKey, 0);
587 afsconf_typedKey_put(&typedKey);
588 is_int(0, code,
589 "afsconf_AddTypedKey can add keys with different sub type");
590
591 /* Check the GetKeyByTypes returns one of the keys */
592 code = afsconf_GetKeyByTypes(dir, 1, 2, 1, &typedKey);
593 is_int(0, code, "afsconf_GetKeyByTypes returns it");
594 ok(keyMatches(typedKey, 1, 2, 1, "\x02\x03", 2),
595 " ... with the right key");
596
597 out:
598 afstest_UnlinkTestConfig(dirname);
599
600 return 0;
601 }