Mercurial > illumos > onarm
annotate usr/src/cmd/gss/gssd/gssdtest.c @ 4:1a15d5aaf794
synchronized with onnv_86 (6202) in onnv-gate
author | Koji Uno <koji.uno@sun.com> |
---|---|
date | Mon, 31 Aug 2009 14:38:03 +0900 |
parents | c9caec207d52 |
children |
rev | line source |
---|---|
0 | 1 /* |
2 * CDDL HEADER START | |
3 * | |
4 * The contents of this file are subject to the terms of the | |
5 * Common Development and Distribution License, Version 1.0 only | |
6 * (the "License"). You may not use this file except in compliance | |
7 * with the License. | |
8 * | |
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE | |
10 * or http://www.opensolaris.org/os/licensing. | |
11 * See the License for the specific language governing permissions | |
12 * and limitations under the License. | |
13 * | |
14 * When distributing Covered Code, include this CDDL HEADER in each | |
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. | |
16 * If applicable, add the following below this CDDL HEADER, with the | |
17 * fields enclosed by brackets "[]" replaced with your own identifying | |
18 * information: Portions Copyright [yyyy] [name of copyright owner] | |
19 * | |
20 * CDDL HEADER END | |
21 */ | |
22 /* | |
23 * Copyright 2003 Sun Microsystems, Inc. All rights reserved. | |
24 * Use is subject to license terms. | |
25 */ | |
26 | |
4
1a15d5aaf794
synchronized with onnv_86 (6202) in onnv-gate
Koji Uno <koji.uno@sun.com>
parents:
0
diff
changeset
|
27 #pragma ident "%Z%%M% %I% %E% SMI" |
0 | 28 |
29 /* | |
30 * Test client for gssd. This program is not shipped on the binary | |
31 * release. | |
32 */ | |
33 | |
34 #include <stdio.h> | |
35 #include <strings.h> | |
36 #include <ctype.h> | |
37 #include <stdlib.h> | |
38 #include <gssapi/gssapi.h> | |
39 #include <gssapi/gssapi_ext.h> | |
40 #include "gssd.h" | |
41 #include <rpc/rpc.h> | |
42 | |
43 #define _KERNEL | |
44 #include <gssapi/gssapi.h> | |
45 #undef _KERNEL | |
46 | |
47 int gss_major_code; | |
48 int gss_minor_code; | |
49 | |
50 int init_sec_context_phase = 0; | |
51 int accept_sec_context_phase = 0; | |
52 | |
53 gss_ctx_id_t initiator_context_handle; | |
54 gss_ctx_id_t acceptor_context_handle; | |
55 gss_cred_id_t acceptor_credentials; | |
56 gss_buffer_desc init_token_buffer; | |
57 gss_buffer_desc accept_token_buffer; | |
58 gss_buffer_desc delete_token_buffer; | |
59 gss_buffer_desc message_buffer; | |
60 gss_buffer_desc msg_token; | |
61 | |
62 #define LOOP_COUNTER 100 | |
63 #define GSS_KRB5_MECH_OID "1.2.840.113554.1.2.2" | |
64 #define GSS_DUMMY_MECH_OID "1.3.6.1.4.1.42.2.26.1.2" | |
65 #ifdef _KERNEL | |
66 #define OCTAL_MACRO "%03o." | |
67 #define MALLOC(n) kmem_alloc((n), KM_SLEEP) | |
68 #define CALLOC(n, s) kmem_zalloc((n)*(s), KM_SLEEP) | |
69 #define FREE(x, n) kmem_free((x), (n)) | |
70 #define memcpy(dst, src, n) bcopy((src), (dst), (n)) | |
71 #define fprintf(s, m) printf(m) | |
72 #define isspace(s) ((s) == ' ' || (s) == '\t' || (s) == '\n' || \ | |
73 (s) == '\r' || (s) == '\v' || (s) == '\f') | |
74 | |
75 static char *strdup(const char *s) | |
76 { | |
77 int len = strlen(s); | |
78 char *new = MALLOC(len+1); | |
79 strcpy(new, s); | |
80 return (new); | |
81 } | |
82 | |
83 #else /* !_KERNEL */ | |
84 #define OCTAL_MACRO "%03.3o." | |
85 #define MALLOC(n) malloc(n) | |
86 #define CALLOC(n, s) calloc((n), (s)) | |
87 #define FREE(x, n) free(x) | |
88 #endif /* _KERNEL */ | |
89 | |
90 static gss_OID gss_str2oid(char *); | |
91 static char * gss_oid2str(gss_OID); | |
92 static void instructs(); | |
93 static void usage(); | |
94 static int parse_input_line(char *, int *, char ***); | |
95 extern uid_t getuid(); | |
96 | |
97 static void _gss_init_sec_context(int, char **); | |
98 static void _gss_acquire_cred(int, char **); | |
99 static void _gss_add_cred(int, char **); | |
100 static void _gss_sign(int, char **); | |
101 static void _gss_release_cred(int, char **); | |
102 static void _gss_accept_sec_context(int, char **); | |
103 static void _gss_process_context_token(int, char **); | |
104 static void _gss_delete_sec_context(int, char **); | |
105 static void _gss_context_time(int, char **); | |
106 static void _gss_verify(int, char **); | |
107 /* EXPORT DELETE START */ | |
108 static void _gss_seal(int, char **); | |
109 static void _gss_unseal(int, char **); | |
110 /* EXPORT DELETE END */ | |
111 static void _gss_display_status(int, char **); | |
112 static void _gss_indicate_mechs(int, char **); | |
113 static void _gss_inquire_cred(int, char **); | |
114 static void _gssd_expname_to_unix_cred(int, char **); | |
115 static void _gssd_name_to_unix_cred(int, char **); | |
116 static void _gssd_get_group_info(int, char **); | |
117 | |
118 static int do_gssdtest(char *buf); | |
119 | |
120 | |
121 #ifndef _KERNEL | |
122 static int read_line(char *buf, int size) | |
123 { | |
124 int len; | |
125 | |
126 /* read the next line. If cntl-d, return with zero char count */ | |
127 printf(gettext("\n> ")); | |
128 | |
129 if (fgets(buf, size, stdin) == NULL) | |
130 return (0); | |
131 | |
132 len = strlen(buf); | |
133 buf[--len] = '\0'; | |
134 return (len); | |
135 } | |
136 | |
137 int | |
138 main() | |
139 { | |
140 char buf[512]; | |
141 int len, ret; | |
142 | |
143 /* Print out usage and instructions to start off the session */ | |
144 | |
145 instructs(); | |
146 usage(); | |
147 | |
148 /* | |
149 * Loop, repeatedly calling parse_input_line() to get the | |
150 * next line and parse it into argc and argv. Act on the | |
151 * arguements found on the line. | |
152 */ | |
153 | |
154 do { | |
155 len = read_line(buf, 512); | |
156 if (len) | |
157 ret = do_gssdtest(buf); | |
158 } while (len && !ret); | |
159 | |
160 return (0); | |
161 } | |
162 #endif /* !_KERNEL */ | |
163 | |
164 static int | |
165 do_gssdtest(char *buf) | |
166 { | |
167 int argc, seal_argc; | |
168 int i; | |
169 char **argv, **argv_array; | |
170 | |
171 char *cmd; | |
172 char *seal_ini_array [] = { "initiator", " Hello"}; | |
173 char *seal_acc_array [] = { "acceptor", " Hello"}; | |
174 char *unseal_acc_array [] = {"acceptor"}; | |
175 char *unseal_ini_array [] = {"initiator"}; | |
176 char *delet_acc_array [] = {"acceptor"}; | |
177 char *delet_ini_array [] = {"initiator"}; | |
178 | |
179 argv = 0; | |
180 | |
181 if (parse_input_line(buf, &argc, &argv) == 0) { | |
182 printf(gettext("\n")); | |
183 return (1); | |
184 } | |
185 | |
186 if (argc == 0) { | |
187 usage(); | |
188 /*LINTED*/ | |
189 FREE(argv_array, (argc+1)*sizeof (char *)); | |
190 return (0); | |
191 } | |
192 | |
193 /* | |
194 * remember argv_array address, which is memory calloc'd by | |
195 * parse_input_line, so it can be free'd at the end of the loop. | |
196 */ | |
197 | |
198 argv_array = argv; | |
199 | |
200 cmd = argv[0]; | |
201 | |
202 argc--; | |
203 argv++; | |
204 | |
205 if (strcmp(cmd, "gss_loop") == 0 || | |
206 strcmp(cmd, "loop") == 0) { | |
207 | |
208 if (argc < 1) { | |
209 usage(); | |
210 FREE(argv_array, (argc+2) * sizeof (char *)); | |
211 return (0); | |
212 } | |
213 for (i = 0; i < LOOP_COUNTER; i++) { | |
214 printf(gettext("Loop Count is %d \n"), i); | |
215 /* | |
216 * if (i > 53) | |
217 * printf ("Loop counter is greater than 55\n"); | |
218 */ | |
219 _gss_acquire_cred(argc, argv); | |
220 _gss_init_sec_context(argc, argv); | |
221 _gss_accept_sec_context(0, argv); | |
222 _gss_init_sec_context(argc, argv); | |
223 /* EXPORT DELETE START */ | |
224 seal_argc = 2; | |
225 _gss_seal(seal_argc, seal_ini_array); | |
226 seal_argc = 1; | |
227 _gss_unseal(seal_argc, unseal_acc_array); | |
228 seal_argc = 2; | |
229 _gss_seal(seal_argc, seal_acc_array); | |
230 seal_argc = 1; | |
231 _gss_unseal(seal_argc, unseal_ini_array); | |
232 /* EXPORT DELETE END */ | |
233 seal_argc = 2; | |
234 _gss_sign(seal_argc, seal_ini_array); | |
235 seal_argc = 1; | |
236 _gss_verify(seal_argc, unseal_acc_array); | |
237 seal_argc = 2; | |
238 _gss_sign(seal_argc, seal_acc_array); | |
239 seal_argc = 1; | |
240 _gss_verify(seal_argc, unseal_ini_array); | |
241 _gss_delete_sec_context(argc, delet_acc_array); | |
242 _gss_delete_sec_context(argc, delet_ini_array); | |
243 } | |
244 } | |
245 if (strcmp(cmd, "gss_all") == 0 || | |
246 strcmp(cmd, "all") == 0) { | |
247 _gss_acquire_cred(argc, argv); | |
248 _gss_init_sec_context(argc, argv); | |
249 _gss_accept_sec_context(0, argv); | |
250 _gss_init_sec_context(argc, argv); | |
251 /* EXPORT DELETE START */ | |
252 seal_argc = 2; | |
253 _gss_seal(seal_argc, seal_acc_array); | |
254 seal_argc = 1; | |
255 _gss_unseal(seal_argc, unseal_ini_array); | |
256 seal_argc = 2; | |
257 _gss_seal(seal_argc, seal_ini_array); | |
258 seal_argc = 1; | |
259 _gss_unseal(seal_argc, unseal_acc_array); | |
260 /* EXPORT DELETE END */ | |
261 seal_argc = 2; | |
262 _gss_sign(seal_argc, seal_ini_array); | |
263 seal_argc = 1; | |
264 _gss_verify(seal_argc, unseal_acc_array); | |
265 seal_argc = 2; | |
266 _gss_sign(seal_argc, seal_acc_array); | |
267 seal_argc = 1; | |
268 _gss_verify(seal_argc, unseal_ini_array); | |
269 | |
270 } | |
271 if (strcmp(cmd, "gss_acquire_cred") == 0 || | |
272 strcmp(cmd, "acquire") == 0) { | |
273 _gss_acquire_cred(argc, argv); | |
274 if (argc == 1) | |
275 _gss_add_cred(argc, argv); | |
276 } | |
277 | |
278 else if (strcmp(cmd, "gss_release_cred") == 0 || | |
279 strcmp(cmd, "release") == 0) | |
280 _gss_release_cred(argc, argv); | |
281 else if (strcmp(cmd, "gss_init_sec_context") == 0 || | |
282 strcmp(cmd, "init") == 0) | |
283 _gss_init_sec_context(argc, argv); | |
284 else if (strcmp(cmd, "gss_accept_sec_context") == 0 || | |
285 strcmp(cmd, "accept") == 0) | |
286 _gss_accept_sec_context(argc, argv); | |
287 else if (strcmp(cmd, "gss_process_context_token") == 0 || | |
288 strcmp(cmd, "process") == 0) | |
289 _gss_process_context_token(argc, argv); | |
290 else if (strcmp(cmd, "gss_delete_sec_context") == 0 || | |
291 strcmp(cmd, "delete") == 0) | |
292 _gss_delete_sec_context(argc, argv); | |
293 else if (strcmp(cmd, "gss_context_time") == 0 || | |
294 strcmp(cmd, "time") == 0) | |
295 _gss_context_time(argc, argv); | |
296 else if (strcmp(cmd, "gss_sign") == 0 || | |
297 strcmp(cmd, "sign") == 0) | |
298 _gss_sign(argc, argv); | |
299 else if (strcmp(cmd, "gss_verify") == 0 || | |
300 strcmp(cmd, "verify") == 0) | |
301 _gss_verify(argc, argv); | |
302 /* EXPORT DELETE START */ | |
303 else if (strcmp(cmd, "gss_seal") == 0 || | |
304 strcmp(cmd, "seal") == 0) | |
305 _gss_seal(argc, argv); | |
306 else if (strcmp(cmd, "gss_unseal") == 0 || | |
307 strcmp(cmd, "unseal") == 0) | |
308 _gss_unseal(argc, argv); | |
309 /* EXPORT DELETE END */ | |
310 else if (strcmp(cmd, "gss_display_status") == 0|| | |
311 strcmp(cmd, "status") == 0) | |
312 _gss_display_status(argc, argv); | |
313 else if (strcmp(cmd, "gss_indicate_mechs") == 0 || | |
314 strcmp(cmd, "indicate") == 0) | |
315 _gss_indicate_mechs(argc, argv); | |
316 else if (strcmp(cmd, "gss_inquire_cred") == 0 || | |
317 strcmp(cmd, "inquire") == 0) | |
318 _gss_inquire_cred(argc, argv); | |
319 else if (strcmp(cmd, "expname2unixcred") == 0 || | |
320 strcmp(cmd, "gsscred_expname_to_unix_cred") == 0) | |
321 _gssd_expname_to_unix_cred(argc, argv); | |
322 else if (strcmp(cmd, "name2unixcred") == 0 || | |
323 strcmp(cmd, "gsscred_name_to_unix_cred") == 0) | |
324 _gssd_name_to_unix_cred(argc, argv); | |
325 else if (strcmp(cmd, "grpinfo") == 0 || | |
326 strcmp(cmd, "gss_get_group_info") == 0) | |
327 _gssd_get_group_info(argc, argv); | |
328 else if (strcmp(cmd, "exit") == 0) { | |
329 printf(gettext("\n")); | |
330 FREE(argv_array, (argc+2) * sizeof (char *)); | |
331 return (1); | |
332 } else | |
333 usage(); | |
334 | |
335 /* free argv array */ | |
336 | |
337 FREE(argv_array, (argc+2) * sizeof (char *)); | |
338 return (0); | |
339 } | |
340 | |
341 static void | |
342 _gss_acquire_cred(argc, argv) | |
343 int argc; | |
344 char **argv; | |
345 { | |
346 | |
347 OM_UINT32 status, minor_status; | |
348 gss_buffer_desc name; | |
349 gss_name_t desired_name = (gss_name_t) 0; | |
350 OM_uint32 time_req; | |
351 gss_OID_set_desc desired_mechs_desc; | |
352 gss_OID_set desired_mechs = &desired_mechs_desc; | |
353 int cred_usage; | |
354 gss_OID_set actual_mechs = GSS_C_NULL_OID_SET; | |
355 gss_OID_set inquire_mechs = GSS_C_NULL_OID_SET; | |
356 OM_UINT32 time_rec; | |
357 char * string; | |
358 char * inq_string; | |
359 uid_t uid; | |
360 gss_OID mech_type; | |
361 | |
362 /* | |
363 * First set up the command line independent input arguments. | |
364 */ | |
365 | |
366 time_req = (OM_uint32) 0; | |
367 cred_usage = GSS_C_ACCEPT; | |
368 uid = getuid(); | |
369 | |
370 /* Parse the command line for the variable input arguments */ | |
371 | |
372 if (argc == 0) { | |
373 usage(); | |
374 return; | |
375 } | |
376 | |
377 /* | |
378 * Get the name of the principal. | |
379 */ | |
380 | |
381 name.length = strlen(argv[0])+1; | |
382 name.value = argv[0]; | |
383 | |
384 /* | |
385 * Now convert the string given by the first argument into internal | |
386 * form suitable for input to gss_acquire_cred() | |
387 */ | |
388 | |
389 if ((status = gss_import_name(&minor_status, &name, | |
390 (gss_OID)GSS_C_NT_HOSTBASED_SERVICE, &desired_name)) | |
391 != GSS_S_COMPLETE) { | |
392 printf(gettext( | |
393 "could not parse desired name: err (octal) %o (%s)\n"), | |
394 status, gettext("gss_acquire_cred error")); | |
395 return; | |
396 } | |
397 | |
398 argc--; | |
399 argv++; | |
400 | |
401 /* | |
402 * The next argument is an OID in dotted decimal form. | |
403 */ | |
404 | |
405 if (argc == 0) { | |
406 printf(gettext("Assuming Kerberos V5 as the mechanism\n")); | |
407 printf(gettext( | |
408 "The mech OID 1.2.840.113554.1.2.2 will be used\n")); | |
409 mech_type = gss_str2oid((char *)GSS_KRB5_MECH_OID); | |
410 } else | |
411 mech_type = gss_str2oid(argv[0]); | |
412 | |
413 if (mech_type == 0 || mech_type->length == 0) { | |
414 printf(gettext("improperly formated mechanism OID\n")); | |
415 return; | |
416 } | |
417 | |
418 /* | |
419 * set up desired_mechs so it points to mech_type. | |
420 */ | |
421 | |
422 desired_mechs = (gss_OID_set) MALLOC(sizeof (gss_OID_desc)); | |
423 | |
424 desired_mechs->count = 1; | |
425 desired_mechs->elements = mech_type; | |
426 | |
427 status = kgss_acquire_cred( | |
428 &minor_status, | |
429 desired_name, | |
430 time_req, | |
431 desired_mechs, | |
432 cred_usage, | |
433 &acceptor_credentials, | |
434 &actual_mechs, | |
435 &time_rec, | |
436 uid); | |
437 | |
438 /* store major and minor status for gss_display_status() call */ | |
439 | |
440 gss_major_code = status; | |
441 gss_minor_code = minor_status; | |
442 | |
443 if (status == GSS_S_COMPLETE) { | |
444 /* process returned values */ | |
445 | |
446 printf(gettext("\nacquire succeeded\n\n")); | |
447 | |
448 /* | |
449 * print out the actual mechs returned NB: Since only one | |
450 * mechanism is specified in desired_mechs, only one | |
451 * can be returned in actual_mechs. Consequently, | |
452 * actual_mechs->elements points to an array of only one | |
453 * element. | |
454 */ | |
455 | |
456 if ((string = gss_oid2str(actual_mechs->elements)) == 0) { | |
457 printf(gettext("actual mechs == NULL\n\n")); | |
458 } else { | |
459 printf(gettext("actual mechs = %s\n\n"), string); | |
460 FREE(string, (actual_mechs->elements->length+1)*4+1); | |
461 } | |
462 | |
463 if (cred_usage == GSS_C_BOTH) | |
464 printf(gettext("GSS_C_BOTH\n\n")); | |
465 | |
466 if (cred_usage == GSS_C_INITIATE) | |
467 printf(gettext("GSS_C_INITIATE\n\n")); | |
468 | |
469 if (cred_usage == GSS_C_ACCEPT) | |
470 printf(gettext("GSS_C_ACCEPT\n\n")); | |
471 status = kgss_inquire_cred( | |
472 &minor_status, | |
473 acceptor_credentials, | |
474 NULL, | |
475 &time_req, | |
476 &cred_usage, | |
477 &inquire_mechs, | |
478 uid); | |
479 | |
480 if (status != GSS_S_COMPLETE) | |
481 printf(gettext("server ret err (octal) %o (%s)\n"), | |
482 status, gettext("gss_inquire_cred error")); | |
483 else { | |
484 if ((inq_string = | |
485 gss_oid2str(inquire_mechs->elements)) == 0) { | |
486 printf(gettext | |
487 ("mechs from inquire == NULL\n\n")); | |
488 } else { | |
489 printf(gettext | |
490 ("mechs from inquiry = %s\n\n"), | |
491 inq_string); | |
492 FREE(inq_string, | |
493 (inquire_mechs->elements->length+1)*4+1); | |
494 } | |
495 printf(gettext("inquire_cred successful \n\n")); | |
496 } | |
497 | |
498 } else { | |
499 printf(gettext("server ret err (octal) %o (%s)\n"), | |
500 status, gettext("gss_acquire_cred error")); | |
501 } | |
502 | |
503 /* free allocated memory */ | |
504 | |
505 /* actual mechs is allocated by clnt_stubs. Release it here */ | |
506 if (actual_mechs != GSS_C_NULL_OID_SET) | |
507 gss_release_oid_set_and_oids(&minor_status, &actual_mechs); | |
508 if (inquire_mechs != GSS_C_NULL_OID_SET) | |
509 gss_release_oid_set_and_oids(&minor_status, &inquire_mechs); | |
510 | |
511 gss_release_name(&minor_status, &desired_name); | |
512 | |
513 /* mech_type and desired_mechs are allocated above. Release it here */ | |
514 | |
515 FREE(mech_type->elements, mech_type->length); | |
516 FREE(mech_type, sizeof (gss_OID_desc)); | |
517 FREE(desired_mechs, sizeof (gss_OID_desc)); | |
518 } | |
519 | |
520 static void | |
521 _gss_add_cred(argc, argv) | |
522 int argc; | |
523 char **argv; | |
524 { | |
525 | |
526 OM_UINT32 status, minor_status; | |
527 gss_buffer_desc name; | |
528 gss_name_t desired_name = (gss_name_t) 0; | |
529 OM_uint32 time_req; | |
530 OM_uint32 initiator_time_req; | |
531 OM_uint32 acceptor_time_req; | |
532 int cred_usage; | |
533 gss_OID_set actual_mechs = GSS_C_NULL_OID_SET; | |
534 gss_OID_set inquire_mechs = GSS_C_NULL_OID_SET; | |
535 char * string; | |
536 uid_t uid; | |
537 gss_OID mech_type; | |
538 int i; | |
539 | |
540 /* | |
541 * First set up the command line independent input arguments. | |
542 */ | |
543 | |
544 initiator_time_req = (OM_uint32) 0; | |
545 acceptor_time_req = (OM_uint32) 0; | |
546 cred_usage = GSS_C_ACCEPT; | |
547 uid = getuid(); | |
548 | |
549 /* Parse the command line for the variable input arguments */ | |
550 | |
551 if (argc == 0) { | |
552 usage(); | |
553 return; | |
554 } | |
555 | |
556 /* | |
557 * Get the name of the principal. | |
558 */ | |
559 | |
560 name.length = strlen(argv[0])+1; | |
561 name.value = argv[0]; | |
562 | |
563 /* | |
564 * Now convert the string given by the first argument into internal | |
565 * form suitable for input to gss_acquire_cred() | |
566 */ | |
567 | |
568 if ((status = gss_import_name(&minor_status, &name, | |
569 (gss_OID)GSS_C_NT_HOSTBASED_SERVICE, &desired_name)) | |
570 != GSS_S_COMPLETE) { | |
571 printf(gettext( | |
572 "could not parse desired name: err (octal) %o (%s)\n"), | |
573 status, gettext("gss_acquire_cred error")); | |
574 return; | |
575 } | |
576 | |
577 argc--; | |
578 argv++; | |
579 | |
580 /* | |
581 * The next argument is an OID in dotted decimal form. | |
582 */ | |
583 | |
584 if (argc == 0) { | |
585 printf(gettext("Assuming dummy as the mechanism\n")); | |
586 printf(gettext( | |
587 "The mech OID 1.3.6.1.4.1.42.2.26.1.2 will be used\n")); | |
588 mech_type = gss_str2oid((char *)GSS_DUMMY_MECH_OID); | |
589 } else | |
590 mech_type = gss_str2oid(argv[0]); | |
591 | |
592 if (mech_type == 0 || mech_type->length == 0) { | |
593 printf(gettext("improperly formated mechanism OID\n")); | |
594 return; | |
595 } | |
596 | |
597 /* | |
598 * set up desired_mechs so it points to mech_type. | |
599 */ | |
600 | |
601 status = kgss_add_cred( | |
602 &minor_status, | |
603 acceptor_credentials, | |
604 desired_name, | |
605 mech_type, | |
606 cred_usage, | |
607 initiator_time_req, | |
608 acceptor_time_req, | |
609 &actual_mechs, | |
610 NULL, | |
611 NULL, | |
612 uid); | |
613 | |
614 /* store major and minor status for gss_display_status() call */ | |
615 | |
616 gss_major_code = status; | |
617 gss_minor_code = minor_status; | |
618 if (status == GSS_S_COMPLETE) { | |
619 /* process returned values */ | |
620 | |
621 printf(gettext("\nadd succeeded\n\n")); | |
622 if (actual_mechs) { | |
623 for (i = 0; i < actual_mechs->count; i++) { | |
624 if ((string = | |
625 gss_oid2str | |
626 (&actual_mechs->elements[i])) == 0) { | |
627 printf(gettext | |
628 ("actual mechs == NULL\n\n")); | |
629 } else { | |
630 printf(gettext | |
631 ("actual mechs = %s\n\n"), string); | |
632 FREE(string, | |
633 (actual_mechs->elements->length+1)*4+1); | |
634 } | |
635 } | |
636 } | |
637 /* | |
638 * Try adding the cred again for the same mech | |
639 * We should get GSS_S_DUPLICATE_ELEMENT | |
640 * if not return an error | |
641 */ | |
642 status = kgss_add_cred( | |
643 &minor_status, | |
644 acceptor_credentials, | |
645 desired_name, | |
646 mech_type, | |
647 cred_usage, | |
648 initiator_time_req, | |
649 acceptor_time_req, | |
650 NULL, /* &actual_mechs, */ | |
651 NULL, | |
652 NULL, | |
653 uid); | |
654 if (status != GSS_S_DUPLICATE_ELEMENT) { | |
655 printf(gettext("Expected duplicate element, Got " | |
656 " (octal) %o (%s)\n"), | |
657 status, gettext("gss_add_cred error")); | |
658 } | |
659 status = kgss_inquire_cred( | |
660 &minor_status, | |
661 acceptor_credentials, | |
662 NULL, | |
663 &time_req, | |
664 &cred_usage, | |
665 &inquire_mechs, | |
666 uid); | |
667 | |
668 if (status != GSS_S_COMPLETE) | |
669 printf(gettext("server ret err (octal) %o (%s)\n"), | |
670 status, gettext("gss_inquire_cred error")); | |
671 else { | |
672 for (i = 0; i < inquire_mechs->count; i++) { | |
673 if ((string = | |
674 gss_oid2str | |
675 (&inquire_mechs->elements[i])) == 0) { | |
676 printf(gettext | |
677 ("inquire_mechs mechs == NULL\n\n")); | |
678 } else { | |
679 printf(gettext | |
680 ("inquire_cred mechs = %s\n\n"), | |
681 string); | |
682 FREE(string, | |
683 (inquire_mechs->elements->length+1)*4 | |
684 +1); | |
685 } | |
686 } | |
687 printf(gettext("inquire_cred successful \n\n")); | |
688 } | |
689 | |
690 } else { | |
691 printf(gettext("server ret err (octal) %o (%s)\n"), | |
692 status, gettext("gss_acquire_cred error")); | |
693 } | |
694 | |
695 /* Let us do inquire_cred_by_mech for both mechanisms */ | |
696 status = kgss_inquire_cred_by_mech( | |
697 &minor_status, | |
698 acceptor_credentials, | |
699 mech_type, | |
700 uid); | |
701 if (status != GSS_S_COMPLETE) | |
702 printf(gettext("server ret err (octal) %o (%s)\n"), | |
703 status, gettext("gss_inquire_cred_by_mech")); | |
704 else | |
705 printf(gettext("gss_inquire_cred_by_mech successful")); | |
706 | |
707 | |
708 FREE(mech_type->elements, mech_type->length); | |
709 FREE(mech_type, sizeof (gss_OID_desc)); | |
710 mech_type = gss_str2oid((char *)GSS_KRB5_MECH_OID); | |
711 status = kgss_inquire_cred_by_mech( | |
712 &minor_status, | |
713 acceptor_credentials, | |
714 mech_type, | |
715 uid); | |
716 if (status != GSS_S_COMPLETE) | |
717 printf(gettext("server ret err (octal) %o (%s)\n"), | |
718 status, gettext | |
719 ("gss_inquire_cred_by_mech for dummy mech error")); | |
720 | |
721 /* free allocated memory */ | |
722 | |
723 /* actual mechs is allocated by clnt_stubs. Release it here */ | |
724 if (actual_mechs != GSS_C_NULL_OID_SET) | |
725 gss_release_oid_set_and_oids(&minor_status, &actual_mechs); | |
726 if (inquire_mechs != GSS_C_NULL_OID_SET) | |
727 gss_release_oid_set_and_oids(&minor_status, &inquire_mechs); | |
728 | |
729 gss_release_name(&minor_status, &desired_name); | |
730 | |
731 /* mech_type and desired_mechs are allocated above. Release it here */ | |
732 | |
733 FREE(mech_type->elements, mech_type->length); | |
734 FREE(mech_type, sizeof (gss_OID_desc)); | |
735 } | |
736 | |
737 /*ARGSUSED*/ | |
738 static void | |
739 _gss_release_cred(argc, argv) | |
740 int argc; | |
741 char **argv; | |
742 { | |
743 OM_UINT32 status; | |
744 OM_UINT32 minor_status; | |
745 uid_t uid; | |
746 | |
747 /* set up input arguments here */ | |
748 | |
749 if (argc != 0) { | |
750 usage(); | |
751 return; | |
752 } | |
753 | |
754 uid = getuid(); | |
755 | |
756 status = kgss_release_cred( | |
757 &minor_status, | |
758 &acceptor_credentials, | |
759 uid); | |
760 | |
761 /* store major and minor status for gss_display_status() call */ | |
762 | |
763 gss_major_code = status; | |
764 gss_minor_code = minor_status; | |
765 | |
766 if (status == GSS_S_COMPLETE) { | |
767 printf(gettext("\nrelease succeeded\n\n")); | |
768 } else { | |
769 printf(gettext("server ret err (octal) %o (%s)\n"), | |
770 status, gettext("gss_release_cred error")); | |
771 } | |
772 } | |
773 | |
774 static void | |
775 _gss_init_sec_context(argc, argv) | |
776 int argc; | |
777 char **argv; | |
778 { | |
779 | |
780 OM_uint32 status; | |
781 | |
782 OM_uint32 minor_status; | |
783 gss_cred_id_t claimant_cred_handle; | |
784 gss_name_t target_name = (gss_name_t) 0; | |
785 gss_OID mech_type = (gss_OID) 0; | |
786 int req_flags; | |
787 OM_uint32 time_req; | |
788 gss_channel_bindings_t input_chan_bindings; | |
789 gss_buffer_t input_token; | |
790 gss_buffer_desc context_token; | |
791 gss_OID actual_mech_type; | |
792 int ret_flags; | |
793 OM_uint32 time_rec; | |
794 uid_t uid; | |
795 char * string; | |
796 gss_buffer_desc name; | |
797 | |
798 /* | |
799 * If this is the first phase of the context establishment, | |
800 * clear initiator_context_handle and indicate next phase. | |
801 */ | |
802 | |
803 if (init_sec_context_phase == 0) { | |
804 initiator_context_handle = GSS_C_NO_CONTEXT; | |
805 input_token = GSS_C_NO_BUFFER; | |
806 init_sec_context_phase = 1; | |
807 } else | |
808 input_token = &init_token_buffer; | |
809 | |
810 /* | |
811 * First set up the non-variable command line independent input | |
812 * arguments | |
813 */ | |
814 | |
815 claimant_cred_handle = GSS_C_NO_CREDENTIAL; | |
816 | |
817 req_flags = GSS_C_MUTUAL_FLAG; | |
818 time_req = (OM_uint32) 0; | |
819 input_chan_bindings = GSS_C_NO_CHANNEL_BINDINGS; | |
820 uid = getuid(); | |
821 | |
822 /* Now parse the command line for the remaining input arguments */ | |
823 | |
824 if (argc == 0) { | |
825 usage(); | |
826 return; | |
827 } | |
828 | |
829 /* | |
830 * Get the name of the target. | |
831 */ | |
832 | |
833 name.length = strlen(argv[0])+1; | |
834 name.value = argv[0]; | |
835 | |
836 /* | |
837 * Now convert the string given by the first argument into a target | |
838 * name suitable for input to gss_init_sec_context() | |
839 */ | |
840 | |
841 if ((status = gss_import_name(&minor_status, &name, | |
842 /* GSS_C_NULL_OID, &target_name)) */ | |
843 (gss_OID)GSS_C_NT_HOSTBASED_SERVICE, &target_name)) | |
844 != GSS_S_COMPLETE) { | |
845 printf(gettext( | |
846 "could not parse target name: err (octal) %o (%s)\n"), | |
847 status, | |
848 gettext("gss_init_sec_context error")); | |
849 if (input_token != GSS_C_NO_BUFFER) | |
850 gss_release_buffer(&minor_status, &init_token_buffer); | |
851 init_sec_context_phase = 0; | |
852 return; | |
853 } | |
854 | |
855 argc--; | |
856 argv++; | |
857 | |
858 if (argc == 0) { | |
859 printf(gettext("Assuming Kerberos V5 as the mechanism\n")); | |
860 printf(gettext( | |
861 "The mech OID 1.2.840.113554.1.2.2 will be used\n")); | |
862 mech_type = gss_str2oid((char *)GSS_KRB5_MECH_OID); | |
863 } else { | |
864 mech_type = gss_str2oid(argv[0]); | |
865 } | |
866 | |
867 if (mech_type == 0 || mech_type->length == 0) { | |
868 printf(gettext("improperly formated mechanism OID\n")); | |
869 if (input_token != GSS_C_NO_BUFFER) | |
870 gss_release_buffer(&minor_status, &init_token_buffer); | |
871 init_sec_context_phase = 0; | |
872 return; | |
873 } | |
874 | |
875 /* call kgss_init_sec_context */ | |
876 | |
877 status = kgss_init_sec_context(&minor_status, | |
878 claimant_cred_handle, | |
879 &initiator_context_handle, | |
880 target_name, | |
881 mech_type, | |
882 req_flags, | |
883 time_req, | |
884 input_chan_bindings, | |
885 input_token, | |
886 &actual_mech_type, | |
887 &accept_token_buffer, | |
888 &ret_flags, | |
889 &time_rec, | |
890 uid); | |
891 | |
892 /* store major and minor status for gss_display_status() call */ | |
893 gss_major_code = status; | |
894 gss_minor_code = minor_status; | |
895 | |
896 if (status != GSS_S_COMPLETE && | |
897 status != GSS_S_CONTINUE_NEEDED) { | |
898 | |
899 printf(gettext("server ret err (octal) %o (%s)\n"), | |
900 status, "gss_init_sec_context error"); | |
901 init_sec_context_phase = 0; | |
902 if (status == GSS_S_NO_CRED) | |
903 printf(gettext(" : no credentials")); | |
904 if (input_token != GSS_C_NO_BUFFER) | |
905 gss_release_buffer(&minor_status, &init_token_buffer); | |
906 if (status != GSS_S_FAILURE && minor_status != 0xffffffff) | |
907 status = kgss_delete_sec_context(&minor_status, | |
908 &initiator_context_handle, | |
909 &msg_token); | |
910 return; | |
911 | |
912 } else if (status == GSS_S_COMPLETE) { | |
913 | |
914 /* process returned values */ | |
915 | |
916 printf(gettext("\ninit succeeded\n\n")); | |
917 | |
918 /* print out the actual mechanism type */ | |
919 | |
920 if ((string = gss_oid2str(actual_mech_type)) == 0) { | |
921 | |
922 printf(gettext( | |
923 "gssapi internal err : actual " | |
924 "mech type null\n")); | |
925 init_sec_context_phase = 0; | |
926 if (input_token != GSS_C_NO_BUFFER) | |
927 gss_release_buffer(&minor_status, | |
928 &init_token_buffer); | |
929 gss_release_buffer(&minor_status, &accept_token_buffer); | |
930 status = kgss_delete_sec_context(&minor_status, | |
931 &initiator_context_handle, | |
932 &msg_token); | |
933 return; | |
934 } else { | |
935 printf(gettext("actual mech type = %s\n\n"), string); | |
936 FREE(string, (actual_mech_type->length+1)*4+1); | |
937 } | |
938 | |
939 /* print out value of ret_flags and time_req */ | |
940 | |
941 if (ret_flags & GSS_C_DELEG_FLAG) | |
942 printf(gettext("GSS_C_DELEG_FLAG = True\n")); | |
943 else | |
944 printf(gettext("GSS_C_DELEG_FLAG = False\n")); | |
945 | |
946 if (ret_flags & GSS_C_MUTUAL_FLAG) | |
947 printf(gettext("GSS_C_MUTUAL_FLAG = True\n")); | |
948 else | |
949 printf(gettext("GSS_C_MUTUAL_FLAG = False\n")); | |
950 | |
951 if (ret_flags & GSS_C_REPLAY_FLAG) | |
952 printf(gettext("GSS_C_REPLAY_FLAG = True\n")); | |
953 else | |
954 printf(gettext("GSS_C_REPLAY_FLAG = False\n")); | |
955 | |
956 if (ret_flags & GSS_C_SEQUENCE_FLAG) | |
957 printf(gettext("GSS_C_SEQUENCE_FLAG = True\n")); | |
958 else | |
959 printf(gettext("GSS_C_SEQUENCE_FLAG = False\n")); | |
960 | |
961 if (ret_flags & GSS_C_CONF_FLAG) | |
962 printf(gettext("GSS_C_CONF_FLAG = True\n")); | |
963 else | |
964 printf(gettext("GSS_C_CONF_FLAG = False\n")); | |
965 | |
966 if (ret_flags & GSS_C_INTEG_FLAG) | |
967 printf(gettext("GSS_C_INTEG_FLAG = True\n\n")); | |
968 else | |
969 printf(gettext("GSS_C_INTEG_FLAG = False\n\n")); | |
970 | |
971 printf(gettext("time_req = %u seconds\n\n"), time_rec); | |
972 | |
973 /* free allocated memory */ | |
974 | |
975 FREE(mech_type->elements, mech_type->length); | |
976 FREE(mech_type, sizeof (gss_OID_desc)); | |
977 | |
978 /* these two were malloc'd by kgss_init_sec_context() */ | |
979 | |
980 FREE(actual_mech_type->elements, actual_mech_type->length); | |
981 FREE(actual_mech_type, sizeof (gss_OID_desc)); | |
982 | |
983 gss_release_name(&minor_status, &target_name); | |
984 | |
985 if (input_token != GSS_C_NO_BUFFER) | |
986 gss_release_buffer(&minor_status, &init_token_buffer); | |
987 | |
988 /* | |
989 * if status == GSS_S_COMPLETE, reset the phase to 0 and | |
990 * release token in accept_token_buffer | |
991 */ | |
992 | |
993 init_sec_context_phase = 0; | |
994 /* Save and restore the context */ | |
995 status = kgss_export_sec_context(&minor_status, | |
996 &initiator_context_handle, | |
997 &context_token); | |
998 if (status != GSS_S_COMPLETE) { | |
999 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1000 status, gettext("gss_export_sec_context_error")); | |
1001 return; | |
1002 } | |
1003 status = kgss_import_sec_context(&minor_status, | |
1004 &context_token, | |
1005 &initiator_context_handle); | |
1006 if (status != GSS_S_COMPLETE) { | |
1007 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1008 status, gettext("gss_import_sec_context_error")); | |
1009 return; | |
1010 } | |
1011 (void) gss_release_buffer(&minor_status, &context_token); | |
1012 | |
1013 /* gss_export & gss_import secxc_context worked, return */ | |
1014 printf(gettext("\nexport and import of contexts succeeded\n")); | |
1015 printf(gettext("\ninit completed")); | |
1016 | |
1017 } else { | |
1018 printf(gettext("\nfirst phase of init succeeded")); | |
1019 printf(gettext("\ninit must be called again\n\n")); | |
1020 } | |
1021 | |
1022 } | |
1023 | |
1024 /*ARGSUSED*/ | |
1025 static void | |
1026 _gss_accept_sec_context(argc, argv) | |
1027 int argc; | |
1028 char **argv; | |
1029 { | |
1030 OM_UINT32 status; | |
1031 | |
1032 OM_uint32 minor_status; | |
1033 gss_channel_bindings_t input_chan_bindings; | |
1034 gss_OID mech_type; | |
1035 int ret_flags; | |
1036 OM_uint32 time_rec; | |
1037 gss_cred_id_t delegated_cred_handle; | |
1038 uid_t uid; | |
1039 char *string; | |
1040 gss_buffer_desc src_name, src_name_string; | |
1041 gss_buffer_desc output_token; | |
1042 gss_name_t gss_name; | |
1043 gss_buffer_desc context_token; | |
1044 | |
1045 /* | |
1046 * If this is the first phase of the context establishment, | |
1047 * clear acceptor_context_handle and indicate next phase. | |
1048 */ | |
1049 | |
1050 if (accept_sec_context_phase == 0) { | |
1051 acceptor_context_handle = GSS_C_NO_CONTEXT; | |
1052 accept_sec_context_phase = 1; | |
1053 } | |
1054 | |
1055 /* Now set up the other command line independent input arguments */ | |
1056 | |
1057 input_chan_bindings = GSS_C_NO_CHANNEL_BINDINGS; | |
1058 | |
1059 uid = (uid_t) getuid(); | |
1060 | |
1061 if (argc != 0) { | |
1062 usage(); | |
1063 return; | |
1064 } | |
1065 | |
1066 status = kgss_accept_sec_context(&minor_status, | |
1067 &acceptor_context_handle, | |
1068 acceptor_credentials, | |
1069 &accept_token_buffer, | |
1070 input_chan_bindings, | |
1071 &src_name, | |
1072 &mech_type, | |
1073 &init_token_buffer, | |
1074 &ret_flags, | |
1075 &time_rec, | |
1076 &delegated_cred_handle, | |
1077 uid); | |
1078 | |
1079 /* store major and minor status for gss_display_status() call */ | |
1080 | |
1081 gss_major_code = status; | |
1082 gss_minor_code = minor_status; | |
1083 | |
1084 if (status != GSS_S_COMPLETE && status != GSS_S_CONTINUE_NEEDED) { | |
1085 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1086 status, gettext("gss_accept_sec_context error")); | |
1087 gss_release_buffer(&minor_status, &accept_token_buffer); | |
1088 return; | |
1089 } else if (status == GSS_S_COMPLETE) { | |
1090 | |
1091 /* process returned values */ | |
1092 | |
1093 printf(gettext("\naccept succeeded\n\n")); | |
1094 | |
1095 /* | |
1096 * convert the exported name returned in src_name into | |
1097 * a string and print it. | |
1098 */ | |
1099 if ((status = gss_import_name(&minor_status, &src_name, | |
1100 (gss_OID) GSS_C_NT_EXPORT_NAME, &gss_name)) | |
1101 != GSS_S_COMPLETE) { | |
1102 printf(gettext( | |
1103 "could not import src name 0x%x\n"), status); | |
1104 accept_sec_context_phase = 0; | |
1105 status = kgss_delete_sec_context(&minor_status, | |
1106 &acceptor_context_handle, | |
1107 &output_token); | |
1108 gss_release_buffer(&minor_status, &accept_token_buffer); | |
1109 if (status == GSS_S_CONTINUE_NEEDED) | |
1110 gss_release_buffer(&minor_status, | |
1111 &init_token_buffer); | |
1112 gss_release_buffer(&minor_status, &src_name); | |
1113 return; | |
1114 } | |
1115 | |
1116 memset(&src_name_string, 0, sizeof (src_name_string)); | |
1117 if ((status = gss_display_name(&minor_status, gss_name, | |
1118 &src_name_string, NULL)) != GSS_S_COMPLETE) { | |
1119 printf(gettext("could not display src name: " | |
1120 "err (octal) %o (%s)\n"), status, | |
1121 "gss_init_sec_context error"); | |
1122 accept_sec_context_phase = 0; | |
1123 status = kgss_delete_sec_context(&minor_status, | |
1124 &acceptor_context_handle, | |
1125 &output_token); | |
1126 gss_release_buffer(&minor_status, &accept_token_buffer); | |
1127 if (status == GSS_S_CONTINUE_NEEDED) | |
1128 gss_release_buffer(&minor_status, | |
1129 &init_token_buffer); | |
1130 gss_release_buffer(&minor_status, &src_name); | |
1131 return; | |
1132 } | |
1133 printf(gettext("src name = %s\n"), src_name_string.value); | |
1134 gss_release_name(&minor_status, &gss_name); | |
1135 gss_release_buffer(&minor_status, &src_name_string); | |
1136 gss_release_buffer(&minor_status, &src_name); | |
1137 | |
1138 /* print out the mechanism type */ | |
1139 | |
1140 if ((string = gss_oid2str(mech_type)) == 0) { | |
1141 | |
1142 printf(gettext( | |
1143 "gssapi internal err :" | |
1144 " actual mech type null\n")); | |
1145 accept_sec_context_phase = 0; | |
1146 status = kgss_delete_sec_context(&minor_status, | |
1147 &acceptor_context_handle, | |
1148 &output_token); | |
1149 gss_release_buffer(&minor_status, &accept_token_buffer); | |
1150 if (status == GSS_S_CONTINUE_NEEDED) | |
1151 gss_release_buffer(&minor_status, | |
1152 &init_token_buffer); | |
1153 return; | |
1154 } else { | |
1155 | |
1156 printf(gettext("actual mech type = %s\n\n"), string); | |
1157 FREE(string, (mech_type->length+1)*4+1); | |
1158 } | |
1159 | |
1160 /* Save and restore the context */ | |
1161 status = kgss_export_sec_context(&minor_status, | |
1162 &initiator_context_handle, | |
1163 &context_token); | |
1164 if (status != GSS_S_COMPLETE) { | |
1165 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1166 status, gettext("gss_export_sec_context_error")); | |
1167 return; | |
1168 } | |
1169 status = kgss_import_sec_context(&minor_status, | |
1170 &context_token, | |
1171 &initiator_context_handle); | |
1172 if (status != GSS_S_COMPLETE) { | |
1173 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1174 status, gettext("gss_import_sec_context_error")); | |
1175 return; | |
1176 } | |
1177 (void) gss_release_buffer(&minor_status, &context_token); | |
1178 | |
1179 /* gss_export & gss_import secxc_context worked, return */ | |
1180 | |
1181 /* print out value of ret_flags and time_req */ | |
1182 | |
1183 if (ret_flags & GSS_C_DELEG_FLAG) | |
1184 printf(gettext("GSS_C_DELEG_FLAG = True\n")); | |
1185 else | |
1186 printf(gettext("GSS_C_DELEG_FLAG = False\n")); | |
1187 | |
1188 if (ret_flags & GSS_C_MUTUAL_FLAG) | |
1189 printf(gettext("GSS_C_MUTUAL_FLAG = True\n")); | |
1190 else | |
1191 printf(gettext("GSS_C_MUTUAL_FLAG = False\n")); | |
1192 | |
1193 if (ret_flags & GSS_C_REPLAY_FLAG) | |
1194 printf(gettext("GSS_C_REPLAY_FLAG = True\n")); | |
1195 else | |
1196 printf(gettext("GSS_C_REPLAY_FLAG = False\n")); | |
1197 | |
1198 if (ret_flags & GSS_C_SEQUENCE_FLAG) | |
1199 printf(gettext("GSS_C_SEQUENCE_FLAG = True\n")); | |
1200 else | |
1201 printf(gettext("GSS_C_SEQUENCE_FLAG = False\n")); | |
1202 | |
1203 if (ret_flags & GSS_C_CONF_FLAG) | |
1204 printf(gettext("GSS_C_CONF_FLAG = True\n")); | |
1205 else | |
1206 printf(gettext("GSS_C_CONF_FLAG = False\n")); | |
1207 | |
1208 if (ret_flags & GSS_C_INTEG_FLAG) | |
1209 printf(gettext("GSS_C_INTEG_FLAG = True\n\n")); | |
1210 else | |
1211 printf(gettext("GSS_C_INTEG_FLAG = False\n\n")); | |
1212 | |
1213 printf(gettext("time_rec = %d seconds\n\n"), time_rec); | |
1214 | |
1215 /* free allocated memory */ | |
1216 | |
1217 printf(gettext("\nexport and import of contexts succeeded\n")); | |
1218 | |
1219 FREE(mech_type->elements, mech_type->length); | |
1220 FREE(mech_type, sizeof (gss_OID_desc)); | |
1221 } else { | |
1222 printf(gettext("\nfirst phase of accept succeeded")); | |
1223 printf(gettext("\naccept must be called again\n\n")); | |
1224 } | |
1225 | |
1226 | |
1227 /* free the input token in accept_token_buffer */ | |
1228 gss_release_buffer(&minor_status, &accept_token_buffer); | |
1229 | |
1230 /* if status == GSS_S_COMPLETE, reset the phase to 0 */ | |
1231 | |
1232 if (status == GSS_S_COMPLETE) | |
1233 accept_sec_context_phase = 0; | |
1234 | |
1235 /* gss_accept_sec_context worked, return */ | |
1236 } | |
1237 | |
1238 void | |
1239 _gss_process_context_token(argc, argv) | |
1240 int argc; | |
1241 char **argv; | |
1242 { | |
1243 OM_UINT32 status; | |
1244 | |
1245 gss_ctx_id_t context_handle; | |
1246 OM_uint32 minor_status; | |
1247 uid_t uid; | |
1248 | |
1249 uid = (uid_t) getuid(); | |
1250 | |
1251 /* parse the command line to determine the variable input argument */ | |
1252 | |
1253 if (argc == 0) { | |
1254 usage(); | |
1255 return; | |
1256 } | |
1257 | |
1258 if (strcmp(argv[0], "initiator") == 0) | |
1259 context_handle = initiator_context_handle; | |
1260 else if (strcmp(argv[0], "acceptor") == 0) | |
1261 context_handle = acceptor_context_handle; | |
1262 else { | |
1263 printf(gettext( | |
1264 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1265 return; | |
1266 } | |
1267 | |
1268 argc--; | |
1269 argv++; | |
1270 | |
1271 if (argc != 0) { | |
1272 usage(); | |
1273 return; | |
1274 } | |
1275 | |
1276 status = kgss_process_context_token(&minor_status, | |
1277 context_handle, | |
1278 delete_token_buffer, | |
1279 uid); | |
1280 | |
1281 /* store major and minor status for gss_display_status() call */ | |
1282 | |
1283 gss_major_code = status; | |
1284 gss_minor_code = minor_status; | |
1285 | |
1286 if (status != GSS_S_COMPLETE) { | |
1287 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1288 status, gettext("gss_process_context_token error")); | |
1289 return; | |
1290 | |
1291 } else { | |
1292 printf(gettext("\nprocess succeeded\n\n")); | |
1293 return; | |
1294 } | |
1295 } | |
1296 | |
1297 static void | |
1298 _gss_delete_sec_context(argc, argv) | |
1299 int argc; | |
1300 char **argv; | |
1301 { | |
1302 OM_UINT32 status; | |
1303 gss_ctx_id_t *context_handle; | |
1304 OM_uint32 minor_status; | |
1305 uid_t uid; | |
1306 | |
1307 uid = (uid_t) getuid(); | |
1308 | |
1309 /* parse the command line to determine the variable input argument */ | |
1310 | |
1311 if (argc == 0) { | |
1312 usage(); | |
1313 return; | |
1314 } | |
1315 | |
1316 if (strcmp(argv[0], "initiator") == 0) { | |
1317 context_handle = &initiator_context_handle; | |
1318 } else if (strcmp(argv[0], "acceptor") == 0) { | |
1319 context_handle = &acceptor_context_handle; | |
1320 } else { | |
1321 printf(gettext( | |
1322 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1323 return; | |
1324 } | |
1325 | |
1326 argc--; | |
1327 argv++; | |
1328 | |
1329 if (argc != 0) { | |
1330 usage(); | |
1331 return; | |
1332 } | |
1333 | |
1334 | |
1335 status = kgss_delete_sec_context(&minor_status, | |
1336 context_handle, | |
1337 &delete_token_buffer); | |
1338 | |
1339 | |
1340 /* store major and minor status for gss_display_status() call */ | |
1341 | |
1342 gss_major_code = status; | |
1343 gss_minor_code = minor_status; | |
1344 | |
1345 if (status != GSS_S_COMPLETE) { | |
1346 | |
1347 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1348 status, gettext("gss_delete_sec_context error")); | |
1349 return; | |
1350 | |
1351 } else { | |
1352 printf(gettext("\ndelete succeeded\n\n")); | |
1353 return; | |
1354 } | |
1355 } | |
1356 | |
1357 /*ARGSUSED*/ | |
1358 static void | |
1359 _gss_context_time(argc, argv) | |
1360 int argc; | |
1361 char **argv; | |
1362 { | |
1363 /* | |
1364 * set up input arguments here | |
1365 * this function is unimplemented. Call usage() and return | |
1366 */ | |
1367 | |
1368 printf(gettext("\nunimplemented function")); | |
1369 } | |
1370 | |
1371 static void | |
1372 _gss_sign(argc, argv) | |
1373 int argc; | |
1374 char **argv; | |
1375 { | |
1376 OM_UINT32 status; | |
1377 OM_uint32 minor_status; | |
1378 gss_ctx_id_t context_handle; | |
1379 int qop_req; | |
1380 uid_t uid; | |
1381 | |
1382 uid = (uid_t) getuid(); | |
1383 | |
1384 /* specify the default quality of protection */ | |
1385 | |
1386 qop_req = GSS_C_QOP_DEFAULT; | |
1387 | |
1388 /* set up the arguments specified in the input parameters */ | |
1389 | |
1390 if (argc == 0) { | |
1391 usage(); | |
1392 return; | |
1393 } | |
1394 | |
1395 | |
1396 if (strcmp(argv[0], "initiator") == 0) | |
1397 context_handle = initiator_context_handle; | |
1398 else if (strcmp(argv[0], "acceptor") == 0) | |
1399 context_handle = acceptor_context_handle; | |
1400 else { | |
1401 printf(gettext( | |
1402 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1403 return; | |
1404 } | |
1405 | |
1406 argc--; | |
1407 argv++; | |
1408 | |
1409 if (argc == 0) { | |
1410 usage(); | |
1411 return; | |
1412 } | |
1413 | |
1414 message_buffer.length = strlen(argv[0])+1; | |
1415 message_buffer.value = (void *) MALLOC(message_buffer.length); | |
1416 strcpy(message_buffer.value, argv[0]); | |
1417 | |
1418 argc--; | |
1419 argv++; | |
1420 | |
1421 if (argc != 0) { | |
1422 usage(); | |
1423 return; | |
1424 } | |
1425 | |
1426 status = kgss_sign(&minor_status, | |
1427 context_handle, | |
1428 qop_req, | |
1429 &message_buffer, | |
1430 &msg_token, | |
1431 uid); | |
1432 | |
1433 /* store major and minor status for gss_display_status() call */ | |
1434 | |
1435 gss_major_code = status; | |
1436 gss_minor_code = minor_status; | |
1437 | |
1438 if (status != GSS_S_COMPLETE) { | |
1439 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1440 status, gettext("gss_sign error")); | |
1441 return; | |
1442 | |
1443 } else { | |
1444 printf(gettext("\nsign succeeded\n\n")); | |
1445 return; | |
1446 } | |
1447 } | |
1448 | |
1449 static void | |
1450 _gss_verify(argc, argv) | |
1451 int argc; | |
1452 char **argv; | |
1453 { | |
1454 OM_UINT32 status, minor_status; | |
1455 gss_ctx_id_t context_handle; | |
1456 int qop_state; | |
1457 uid_t uid; | |
1458 | |
1459 uid = (uid_t) getuid(); | |
1460 | |
1461 /* set up the arguments specified in the input parameters */ | |
1462 | |
1463 if (argc == 0) { | |
1464 usage(); | |
1465 return; | |
1466 } | |
1467 | |
1468 | |
1469 if (strcmp(argv[0], "initiator") == 0) | |
1470 context_handle = initiator_context_handle; | |
1471 else if (strcmp(argv[0], "acceptor") == 0) | |
1472 context_handle = acceptor_context_handle; | |
1473 else { | |
1474 printf(gettext( | |
1475 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1476 return; | |
1477 } | |
1478 | |
1479 argc--; | |
1480 argv++; | |
1481 | |
1482 if (argc != 0) { | |
1483 usage(); | |
1484 return; | |
1485 } | |
1486 | |
1487 status = kgss_verify(&minor_status, | |
1488 context_handle, | |
1489 &message_buffer, | |
1490 &msg_token, | |
1491 &qop_state, | |
1492 uid); | |
1493 | |
1494 /* store major and minor status for gss_display_status() call */ | |
1495 | |
1496 gss_major_code = status; | |
1497 gss_minor_code = minor_status; | |
1498 | |
1499 if (status != GSS_S_COMPLETE) { | |
1500 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1501 status, gettext("gss_verify error")); | |
1502 return; | |
1503 } else { | |
1504 | |
1505 /* print out the verified message */ | |
1506 | |
1507 printf(gettext( | |
1508 "verified message = \"%s\"\n\n"), message_buffer.value); | |
1509 | |
1510 /* print out the quality of protection returned */ | |
1511 | |
1512 printf(gettext("quality of protection = %d \n\n"), qop_state); | |
1513 | |
1514 /* free the message buffer and message token and return */ | |
1515 | |
1516 gss_release_buffer(&minor_status, &message_buffer); | |
1517 gss_release_buffer(&minor_status, &msg_token); | |
1518 | |
1519 return; | |
1520 } | |
1521 } | |
1522 | |
1523 /* EXPORT DELETE START */ | |
1524 static void | |
1525 _gss_seal(argc, argv) | |
1526 int argc; | |
1527 char **argv; | |
1528 { | |
1529 OM_UINT32 status; | |
1530 | |
1531 OM_uint32 minor_status; | |
1532 gss_ctx_id_t context_handle; | |
1533 int conf_req_flag; | |
1534 int qop_req; | |
1535 gss_buffer_desc input_message_buffer; | |
1536 int conf_state; | |
1537 uid_t uid; | |
1538 | |
1539 uid = (uid_t) getuid(); | |
1540 | |
1541 /* | |
1542 * specify the default confidentiality requested (both integrity | |
1543 * and confidentiality) and quality of protection | |
1544 */ | |
1545 | |
1546 conf_req_flag = 1; | |
1547 qop_req = GSS_C_QOP_DEFAULT; | |
1548 | |
1549 /* set up the arguments specified in the input parameters */ | |
1550 | |
1551 if (argc == 0) { | |
1552 usage(); | |
1553 return; | |
1554 } | |
1555 | |
1556 | |
1557 if (strcmp(argv[0], "initiator") == 0) | |
1558 context_handle = initiator_context_handle; | |
1559 else if (strcmp(argv[0], "acceptor") == 0) | |
1560 context_handle = acceptor_context_handle; | |
1561 else { | |
1562 printf(gettext( | |
1563 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1564 return; | |
1565 } | |
1566 | |
1567 argc--; | |
1568 argv++; | |
1569 | |
1570 if (argc == 0) { | |
1571 usage(); | |
1572 return; | |
1573 } | |
1574 | |
1575 | |
1576 input_message_buffer.length = strlen(argv[0])+1; | |
1577 input_message_buffer.value = | |
1578 (void *) MALLOC(input_message_buffer.length); | |
1579 strcpy(input_message_buffer.value, argv[0]); | |
1580 | |
1581 argc--; | |
1582 argv++; | |
1583 | |
1584 if (argc != 0) { | |
1585 usage(); | |
1586 return; | |
1587 } | |
1588 | |
1589 status = kgss_seal(&minor_status, | |
1590 context_handle, | |
1591 conf_req_flag, | |
1592 qop_req, | |
1593 &input_message_buffer, | |
1594 &conf_state, | |
1595 &message_buffer, | |
1596 uid); | |
1597 | |
1598 /* store major and minor status for gss_display_status() call */ | |
1599 | |
1600 gss_major_code = status; | |
1601 gss_minor_code = minor_status; | |
1602 | |
1603 /* free the inputmessage buffer */ | |
1604 | |
1605 gss_release_buffer(&minor_status, &input_message_buffer); | |
1606 | |
1607 if (status != GSS_S_COMPLETE) { | |
1608 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1609 status, gettext("gss_seal error")); | |
1610 return; | |
1611 } else { | |
1612 printf(gettext("\nseal succeeded\n\n")); | |
1613 return; | |
1614 } | |
1615 } | |
1616 | |
1617 static void | |
1618 _gss_unseal(argc, argv) | |
1619 int argc; | |
1620 char **argv; | |
1621 { | |
1622 OM_UINT32 status; | |
1623 | |
1624 OM_uint32 minor_status; | |
1625 gss_ctx_id_t context_handle; | |
1626 gss_buffer_desc output_message_buffer; | |
1627 int conf_state; | |
1628 int qop_state; | |
1629 uid_t uid; | |
1630 | |
1631 uid = (uid_t) getuid(); | |
1632 | |
1633 /* set up the arguments specified in the input parameters */ | |
1634 | |
1635 if (argc == 0) { | |
1636 usage(); | |
1637 return; | |
1638 } | |
1639 | |
1640 | |
1641 if (strcmp(argv[0], "initiator") == 0) | |
1642 context_handle = initiator_context_handle; | |
1643 else if (strcmp(argv[0], "acceptor") == 0) | |
1644 context_handle = acceptor_context_handle; | |
1645 else { | |
1646 printf(gettext( | |
1647 "must specify either \"initiator\" or \"acceptor\"\n")); | |
1648 return; | |
1649 } | |
1650 | |
1651 argc--; | |
1652 argv++; | |
1653 | |
1654 if (argc != 0) { | |
1655 usage(); | |
1656 return; | |
1657 } | |
1658 | |
1659 status = kgss_unseal(&minor_status, | |
1660 context_handle, | |
1661 &message_buffer, | |
1662 &output_message_buffer, | |
1663 &conf_state, | |
1664 &qop_state, | |
1665 uid); | |
1666 | |
1667 /* store major and minor status for gss_display_status() call */ | |
1668 | |
1669 gss_major_code = status; | |
1670 gss_minor_code = minor_status; | |
1671 | |
1672 if (status == GSS_S_COMPLETE) { | |
1673 printf(gettext("\nunseal succeeded\n\n")); | |
1674 printf(gettext("unsealed message = \"%s\"\n\n"), | |
1675 output_message_buffer.value); | |
1676 if (conf_state) | |
1677 printf(gettext("confidentiality and integrity used\n")); | |
1678 else | |
1679 printf(gettext("only integrity used\n")); | |
1680 printf(gettext("quality of protection = %d\n\n"), qop_state); | |
1681 gss_release_buffer(&minor_status, &output_message_buffer); | |
1682 } else { | |
1683 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1684 status, gettext("gss_unseal error")); | |
1685 } | |
1686 | |
1687 /* free the message buffer and return */ | |
1688 | |
1689 gss_release_buffer(&minor_status, &message_buffer); | |
1690 } | |
1691 /* EXPORT DELETE END */ | |
1692 | |
1693 static void | |
1694 _gss_display_status(argc, argv) | |
1695 int argc; | |
1696 char **argv; | |
1697 { | |
1698 OM_UINT32 status; | |
1699 OM_uint32 minor_status; | |
1700 int status_type; | |
1701 int status_value; | |
1702 gss_OID mech_type = (gss_OID) 0; | |
1703 int message_context; | |
1704 gss_buffer_desc status_string; | |
1705 uid_t uid; | |
1706 | |
1707 uid = (uid_t) getuid(); | |
1708 | |
1709 /* initialize message context to zero */ | |
1710 | |
1711 message_context = 0; | |
1712 | |
1713 if (argc == 0) { | |
1714 printf(gettext("Assuming Kerberos V5 as the mechanism\n")); | |
1715 printf(gettext( | |
1716 "The mech OID 1.2.840.113554.1.2.2 will be used\n")); | |
1717 mech_type = gss_str2oid((char *)GSS_KRB5_MECH_OID); | |
1718 } else | |
1719 mech_type = gss_str2oid(argv[0]); | |
1720 | |
1721 if (mech_type == 0 || mech_type->length == 0) { | |
1722 printf(gettext("improperly formated mechanism OID\n")); | |
1723 return; | |
1724 } | |
1725 | |
1726 /* Is this call for the major or minor status? */ | |
1727 | |
1728 if (strcmp(argv[0], "major") == 0) { | |
1729 status_type = GSS_C_GSS_CODE; | |
1730 status_value = gss_major_code; | |
1731 } else if (strcmp(argv[0], "minor") == 0) { | |
1732 status_type = GSS_C_MECH_CODE; | |
1733 status_value = gss_minor_code; | |
1734 } else { | |
1735 printf(gettext("must specify either \"major\" or \"minor\"\n")); | |
1736 return; | |
1737 } | |
1738 | |
1739 argc--; | |
1740 argv++; | |
1741 | |
1742 if (argc != 0) { | |
1743 usage(); | |
1744 return; | |
1745 } | |
1746 | |
1747 status = kgss_display_status(&minor_status, | |
1748 status_value, | |
1749 status_type, | |
1750 mech_type, | |
1751 &message_context, | |
1752 &status_string, | |
1753 uid); | |
1754 | |
1755 if (status == GSS_S_COMPLETE) { | |
1756 printf(gettext("status =\n %s\n\n"), status_string.value); | |
1757 } else if (status == GSS_S_BAD_MECH) { | |
1758 printf(gettext("invalide mechanism OID\n\n")); | |
1759 } else { | |
1760 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1761 status, gettext("gss_display_status error")); | |
1762 } | |
1763 } | |
1764 | |
1765 /*ARGSUSED*/ | |
1766 static void | |
1767 _gss_indicate_mechs(argc, argv) | |
1768 int argc; | |
1769 char **argv; | |
1770 { | |
1771 OM_UINT32 status; | |
1772 OM_UINT32 minor_status; | |
1773 gss_OID_set oid_set = GSS_C_NULL_OID_SET; | |
1774 uid_t uid; | |
1775 | |
1776 uid = (uid_t) getuid(); | |
1777 | |
1778 /* set up input arguments here */ | |
1779 | |
1780 if (argc != 0) { | |
1781 usage(); | |
1782 return; | |
1783 } | |
1784 | |
1785 status = kgss_indicate_mechs(&minor_status, &oid_set, uid); | |
1786 | |
1787 if (status == GSS_S_COMPLETE) { | |
1788 int i; | |
1789 char *string; | |
1790 | |
1791 printf(gettext("%d supported mechanism%s%s\n"), oid_set->count, | |
1792 (oid_set->count == 1) ? "" : "s", | |
1793 (oid_set->count > 0) ? ":" : ""); | |
1794 | |
1795 for (i = 0; i < oid_set->count; i++) { | |
1796 string = gss_oid2str(&oid_set->elements[i]); | |
1797 printf(gettext("\t%s\n"), string); | |
1798 FREE(string, ((oid_set->elements[i].length+1)*4)+1); | |
1799 } | |
1800 printf("\n"); | |
1801 | |
1802 } else { | |
1803 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1804 status, gettext("gss_indicate_mechs error")); | |
1805 } | |
1806 | |
1807 if (oid_set) | |
1808 gss_release_oid_set_and_oids(&minor_status, &oid_set); | |
1809 } | |
1810 | |
1811 /*ARGSUSED*/ | |
1812 static void | |
1813 _gss_inquire_cred(argc, argv) | |
1814 int argc; | |
1815 char **argv; | |
1816 { | |
1817 /* set up input arguments here */ | |
1818 | |
1819 if (argc != 0) { | |
1820 usage(); | |
1821 return; | |
1822 } | |
1823 | |
1824 | |
1825 /* this function is unimplemented. Call usage() and return */ | |
1826 | |
1827 printf(gettext("\nUnsupported function")); | |
1828 } | |
1829 | |
1830 static char hexChars[] = "0123456789ABCDEF"; | |
1831 | |
1832 static void | |
1833 _gssd_expname_to_unix_cred(argc, argv) | |
1834 int argc; | |
1835 char **argv; | |
1836 { | |
1837 OM_uint32 major; | |
1838 gss_buffer_desc expName; | |
1839 char krb5_root_name[] = "040100092A864886F712010202000000" | |
1840 "25000A2A864886F71201020101726F6F744053554E534F46" | |
1841 "542E454E472E53554E2E434F4D00"; | |
1842 unsigned char *byteStr, *hexStr; | |
1843 uid_t uidOut, uidIn; | |
1844 gid_t *gids, gidOut; | |
1845 int gidsLen, i, newLen; | |
1846 | |
1847 /* set up the arguments */ | |
1848 uidIn = (uid_t) getuid(); | |
1849 | |
1850 if (argc < 1) { | |
1851 printf(gettext( | |
1852 "Using principal name of root for krberos_v5\n")); | |
1853 expName.value = (void*)krb5_root_name; | |
1854 expName.length = strlen(krb5_root_name); | |
1855 } else { | |
1856 expName.value = (void*)argv[0]; | |
1857 expName.length = strlen(argv[0]); | |
1858 } | |
1859 | |
1860 /* convert the name from hex to byte... */ | |
1861 hexStr = (unsigned char *)expName.value; | |
1862 newLen = expName.length/2; | |
1863 byteStr = (unsigned char *)MALLOC(newLen+1); | |
1864 expName.value = (char *)byteStr; | |
1865 for (i = 0; i < expName.length; i += 2) { | |
1866 *byteStr = (strchr(hexChars, *hexStr++) - hexChars) << 4; | |
1867 *byteStr += (strchr(hexChars, *hexStr++) - hexChars); | |
1868 byteStr++; | |
1869 } | |
1870 expName.length = newLen; | |
1871 | |
1872 major = kgsscred_expname_to_unix_cred(&expName, &uidOut, &gidOut, | |
1873 &gids, &gidsLen, uidIn); | |
1874 | |
1875 FREE(expName.value, newLen); | |
1876 | |
1877 if (major == GSS_S_COMPLETE) { | |
1878 printf(gettext("uid = <%d>\tgid = <%d>\t"), uidOut, gidOut); | |
1879 if (gidsLen > 0) | |
1880 printf(gettext(" %d gids <"), gidsLen); | |
1881 else | |
1882 printf(gettext( | |
1883 " no supplementary group information\n")); | |
1884 for (i = 0; i < gidsLen; i++) | |
1885 printf(" %d ", gids[i]); | |
1886 if (gidsLen > 0) { | |
1887 printf(">\n"); | |
1888 FREE(gids, gidsLen * sizeof (gid_t)); | |
1889 } | |
1890 } else { | |
1891 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1892 major, gettext("gsscred_expname_to_unix_cred")); | |
1893 } | |
1894 } | |
1895 | |
1896 static void | |
1897 _gssd_name_to_unix_cred(argc, argv) | |
1898 int argc; | |
1899 char **argv; | |
1900 { | |
1901 OM_uint32 major, minor; | |
1902 gss_name_t gssName; | |
1903 gss_buffer_desc gssBuf = GSS_C_EMPTY_BUFFER; | |
1904 int gidsLen, i; | |
1905 gid_t *gids, gidOut; | |
1906 uid_t uidOut, uid; | |
1907 char defaultPrincipal[] = "root"; | |
1908 gss_OID mechType, nameType; | |
1909 | |
1910 uid = getuid(); | |
1911 | |
1912 /* optional argument 1 - contains principal name */ | |
1913 if (argc > 0) { | |
1914 gssBuf.value = (void *)argv[0]; | |
1915 gssBuf.length = strlen((char *)argv[0]); | |
1916 } else { | |
1917 gssBuf.value = (void *)defaultPrincipal; | |
1918 gssBuf.length = strlen(defaultPrincipal); | |
1919 } | |
1920 printf(gettext( | |
1921 "Using <%s> as the principal name.\n"), (char *)gssBuf.value); | |
1922 | |
1923 | |
1924 /* optional argument 2 - contains name oid */ | |
1925 if (argc > 1) | |
1926 nameType = gss_str2oid((char *) argv[1]); | |
1927 else | |
1928 nameType = (gss_OID)GSS_C_NT_USER_NAME; | |
1929 | |
1930 if (nameType == NULL || nameType->length == 0) { | |
1931 printf(gettext("improperly formated name OID\n")); | |
1932 return; | |
1933 } | |
1934 printf(gettext("Principal name of type: <%s>.\n"), | |
1935 (argc > 1) ? argv[1] : "GSS_C_NT_USER_NAME"); | |
1936 | |
1937 | |
1938 /* optional argument 3 - contains mech oid */ | |
1939 if (argc > 2) | |
1940 mechType = gss_str2oid(argv[2]); | |
1941 else | |
1942 mechType = gss_str2oid((char *)GSS_KRB5_MECH_OID); | |
1943 | |
1944 if (mechType == NULL || mechType->length == NULL) { | |
1945 FREE(nameType->elements, nameType->length); | |
1946 FREE(nameType, sizeof (gss_OID_desc)); | |
1947 printf(gettext("improperly formated mech OID\n")); | |
1948 return; | |
1949 } | |
1950 printf(gettext("Mechanism oid: <%s>.\n"), | |
1951 (argc > 2) ? argv[2] : | |
1952 (char *)GSS_KRB5_MECH_OID "(Kerberos v5)"); | |
1953 | |
1954 | |
1955 /* convert the name to internal format */ | |
1956 if ((major = gss_import_name(&minor, &gssBuf, | |
1957 nameType, &gssName)) != GSS_S_COMPLETE) { | |
1958 printf(gettext("could not parse name: err (octal) %o (%s)\n"), | |
1959 major, "gss_import_name"); | |
1960 | |
1961 FREE(nameType->elements, nameType->length); | |
1962 FREE(nameType, sizeof (gss_OID_desc)); | |
1963 return; | |
1964 } | |
1965 | |
1966 major = kgsscred_name_to_unix_cred(gssName, mechType, &uidOut, | |
1967 &gidOut, &gids, &gidsLen, uid); | |
1968 | |
1969 gss_release_name(&minor, &gssName); | |
1970 FREE(mechType->elements, mechType->length); | |
1971 FREE(mechType, sizeof (gss_OID_desc)); | |
1972 if (argc > 1) { | |
1973 FREE(nameType->elements, nameType->length); | |
1974 FREE(nameType, sizeof (gss_OID_desc)); | |
1975 } | |
1976 | |
1977 if (major == GSS_S_COMPLETE) { | |
1978 printf("uid = <%d>\tgid = <%d>\t", uidOut, gidOut); | |
1979 if (gidsLen > 0) | |
1980 printf(gettext(" %d gids <"), gidsLen); | |
1981 else | |
1982 printf(gettext( | |
1983 " no supplementary group information\n")); | |
1984 for (i = 0; i < gidsLen; i++) | |
1985 printf(" %d ", gids[i]); | |
1986 if (gidsLen > 0) { | |
1987 printf(">\n"); | |
1988 FREE(gids, gidsLen * sizeof (gid_t)); | |
1989 } | |
1990 } else { | |
1991 printf(gettext("server ret err (octal) %o (%s)\n"), | |
1992 major, gettext("gsscred_name_to_unix_cred")); | |
1993 } | |
1994 } | |
1995 | |
1996 static void | |
1997 _gssd_get_group_info(argc, argv) | |
1998 int argc; | |
1999 char **argv; | |
2000 { | |
2001 OM_uint32 major; | |
2002 uid_t puid, uidIn; | |
2003 gid_t *gids, gidOut; | |
2004 int gidsLen, i; | |
2005 | |
2006 /* set up the arguments */ | |
2007 uidIn = (uid_t) getuid(); | |
2008 | |
2009 if (argc < 1) | |
2010 puid = 0; | |
2011 else | |
2012 puid = atol(argv[0]); | |
2013 | |
2014 printf(gettext("Retrieving group info for uid of <%d>\n"), puid); | |
2015 | |
2016 major = kgss_get_group_info(puid, &gidOut, &gids, &gidsLen, uidIn); | |
2017 | |
2018 if (major == GSS_S_COMPLETE) { | |
2019 printf(gettext("group id = <%d>\t"), gidOut); | |
2020 if (gidsLen > 0) | |
2021 printf(gettext(" %d gids <"), gidsLen); | |
2022 else | |
2023 printf(gettext( | |
2024 " no supplementary group information\n")); | |
2025 for (i = 0; i < gidsLen; i++) | |
2026 printf(" %d ", gids[i]); | |
2027 if (gidsLen > 0) { | |
2028 printf(">\n"); | |
2029 FREE(gids, gidsLen * sizeof (gid_t)); | |
2030 } | |
2031 } else { | |
2032 printf(gettext("server ret err (octal) %o (%s)\n"), | |
2033 major, "gss_get_group_info"); | |
2034 } | |
2035 } | |
2036 | |
2037 static gss_OID | |
2038 gss_str2oid(string) | |
2039 char * string; | |
2040 { | |
2041 /* | |
2042 * a convenient wrapper routine for gss_str_to_oid | |
2043 * this can handle all valid oid strings. | |
2044 */ | |
2045 OM_uint32 minor; | |
2046 gss_buffer_desc abuf; | |
2047 gss_OID oidOut; | |
2048 | |
2049 abuf.value = (void*)string; | |
2050 abuf.length = strlen(string); | |
2051 | |
2052 if (gss_str_to_oid(&minor, &abuf, &oidOut) != GSS_S_COMPLETE) | |
2053 return (NULL); | |
2054 | |
2055 return (oidOut); | |
2056 } | |
2057 | |
2058 static char * | |
2059 gss_oid2str(oid) | |
2060 gss_OID oid; | |
2061 { | |
2062 /* | |
2063 * a convenient wrapper for gss_oid_to_str | |
2064 * this calls the GSS-API routine which should | |
2065 * be able to handle all types of oids. | |
2066 */ | |
2067 OM_uint32 minor; | |
2068 gss_buffer_desc oidStr; | |
2069 | |
2070 if (gss_oid_to_str(&minor, oid, &oidStr) != GSS_S_COMPLETE) | |
2071 return (NULL); | |
2072 | |
2073 return ((char *)oidStr.value); | |
2074 } /* gss_oid2str */ | |
2075 | |
2076 static void | |
2077 instructs() | |
2078 { | |
2079 fprintf(stderr, | |
2080 gettext( | |
2081 "\nThis program must be run as root. Root must be installed on the KDC\n" | |
2082 "and exist in srvtab as root/<hostname>, where <hostname> is the machine on\n" | |
2083 "which the test runs. Before running gssdtest for Kerberos mechanism, the\n" | |
2084 "operator running as root must kinit as some other principal, e.g., test.\n" | |
2085 "There are two mechanisms avaialble: dummy and Kerberos(default).\n" | |
2086 "The OID for dummy mechanism is 1.3.6.1.4.1.42.2.26.1.2.\n" | |
2087 "The OID for Kerberos mechanism is 1.2.840.113554.1.2.2.\n" | |
2088 "The order of context establishment calls is important. First, acquire must" | |
2089 "\nbe called. This obtains the credentials used by accept. Acquire need\n" | |
2090 "only be called once, since the credentials it returns are used each time\n" | |
2091 "accept is called. Then init is called, followed by accept. Calling init\n" | |
2092 "twice without calling accept or calling these in a different order gives\n" | |
2093 "erroneous results and will cause memory leaks in the gssapi daemon. \n" | |
2094 "Finally, after calling init and accept, init must be called again to\n" | |
2095 "finish context establishment. So an example sequence (with data valid for\n" | |
2096 "the Kerberos mechanism and running on the machine \"elrond\" in the realm\n" | |
2097 "FOO.BAR.SUN.COM is :\n")); | |
2098 fprintf(stderr, | |
2099 gettext("\nacquire service@host 1.2.840.113554.1.2.2\n" | |
2100 "init service@host 1.2.840.113554.1.2.2\n" | |
2101 "accept\ninit service@host 1.2.840.113554.1.2.2\n" | |
2102 "\nAfter a context is established, sign, seal,\n" | |
2103 "verify and unseal may be called. Here are some examples\n" | |
2104 "for these routines : \n\n" | |
2105 "sign initiator ThisTestMessageIsForSigning\n" | |
2106 "verify acceptor\nseal initiator ThisTestMessageIsForSealing\n" | |
2107 "unseal acceptor\n\nEach input line is terminated by <cr>.\n" | |
2108 "The program is terminated by cntl-d\nor the command \"exit\"" | |
2109 "\nfrom the prompt\n\n")); | |
2110 } | |
2111 | |
2112 static void | |
2113 usage() | |
2114 { | |
2115 fprintf(stderr, | |
2116 gettext( | |
2117 "\nusage:\t[acquire | gss_acquire_cred]" | |
2118 "desired_name mech_type\n" | |
2119 "\t[release | gss_release_cred]\n" | |
2120 "\t[init | gss_init_sec_context] target_name mech_type\n" | |
2121 "\t[accept | gss_accept_sec_context]\n" | |
2122 "\t[process | gss_process_context_token] initiator | acceptor\n" | |
2123 "\t[delete | gss_delete_sec_context] initiator | acceptor\n" | |
2124 "\t[time | gss_context_time] {not yet implemented}\n" | |
2125 "\t[sign | gss_sign] initiator | acceptor message-to-sign\n" | |
2126 "\t[verify | gss_verify] initiator | acceptor\n" | |
2127 "\t[seal | gss_seal] initiator | acceptor message-to-seal\n" | |
2128 "\t[unseal | gss_unseal] initiator | acceptor\n" | |
2129 "\t[status | gss_display_status] mech_type [major | minor] \n" | |
2130 "\t[indicate | gss_indicate_mechs]\n" | |
2131 "\t[inquire | gss_inquire_cred] {not yet implemented}\n" | |
2132 "\t[expname2unixcred | gsscred_expname_to_unix_cred]" | |
2133 " export-name\n" | |
2134 "\t[name2unixcred | gsscred_name_to_unix_cred] " | |
2135 "pname [name_type mech_type]\n" | |
2136 "\t[grpinfo | gss_get_group_info] uid\n" | |
2137 "\t[gss_all | all] desired_name\n" | |
2138 "\t[gss_loop | loop] desired_name\n" | |
2139 "\texit\n\n")); | |
2140 } | |
2141 | |
2142 /* Copied from parse_argv(), then modified */ | |
2143 | |
2144 static int | |
2145 parse_input_line(input_line, argc, argv) | |
2146 char *input_line; | |
2147 int * argc; | |
2148 char ***argv; | |
2149 { | |
2150 const char nil = '\0'; | |
2151 char * chptr; | |
2152 int chr_cnt; | |
2153 int arg_cnt = 0; | |
2154 int ch_was_space = 1; | |
2155 int ch_is_space; | |
2156 | |
2157 chr_cnt = strlen(input_line); | |
2158 | |
2159 /* Count the arguments in the input_line string */ | |
2160 | |
2161 *argc = 1; | |
2162 | |
2163 for (chptr = &input_line[0]; *chptr != nil; chptr++) { | |
2164 ch_is_space = isspace(*chptr); | |
2165 if (ch_is_space && !ch_was_space) { | |
2166 (*argc)++; | |
2167 } | |
2168 ch_was_space = ch_is_space; | |
2169 } | |
2170 | |
2171 if (ch_was_space) { | |
2172 (*argc)--; | |
2173 } /* minus trailing spaces */ | |
2174 | |
2175 /* Now that we know how many args calloc the argv array */ | |
2176 | |
2177 *argv = (char **) CALLOC((*argc)+1, sizeof (char *)); | |
2178 chptr = (char *) (&input_line[0]); | |
2179 | |
2180 for (ch_was_space = 1; *chptr != nil; chptr++) { | |
2181 ch_is_space = isspace(*chptr); | |
2182 if (ch_is_space) { | |
2183 *chptr = nil; /* replace each space with nil */ | |
2184 } else if (ch_was_space) { /* begining of word? */ | |
2185 (*argv)[arg_cnt++] = chptr; /* new argument ? */ | |
2186 } | |
2187 | |
2188 ch_was_space = ch_is_space; | |
2189 } | |
2190 | |
2191 return (chr_cnt); | |
2192 } |