xref: /onnv-gate/usr/src/lib/gss_mechs/mech_krb5/mech/add_cred.c (revision 13132:9615cdbf7b70)
1*13132SGlenn.Barry@oracle.com /*
2*13132SGlenn.Barry@oracle.com  * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
3*13132SGlenn.Barry@oracle.com  */
40Sstevel@tonic-gate /*
50Sstevel@tonic-gate  * Copyright 2000 by the Massachusetts Institute of Technology.
60Sstevel@tonic-gate  * All Rights Reserved.
70Sstevel@tonic-gate  *
80Sstevel@tonic-gate  * Export of this software from the United States of America may
90Sstevel@tonic-gate  *   require a specific license from the United States Government.
100Sstevel@tonic-gate  *   It is the responsibility of any person or organization contemplating
110Sstevel@tonic-gate  *   export to obtain such a license before exporting.
125053Sgtb  *
130Sstevel@tonic-gate  * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
140Sstevel@tonic-gate  * distribute this software and its documentation for any purpose and
150Sstevel@tonic-gate  * without fee is hereby granted, provided that the above copyright
160Sstevel@tonic-gate  * notice appear in all copies and that both that copyright notice and
170Sstevel@tonic-gate  * this permission notice appear in supporting documentation, and that
180Sstevel@tonic-gate  * the name of M.I.T. not be used in advertising or publicity pertaining
190Sstevel@tonic-gate  * to distribution of the software without specific, written prior
200Sstevel@tonic-gate  * permission.  Furthermore if you modify this software you must label
210Sstevel@tonic-gate  * your software as modified software and not distribute it in such a
220Sstevel@tonic-gate  * fashion that it might be confused with the original M.I.T. software.
230Sstevel@tonic-gate  * M.I.T. makes no representations about the suitability of
240Sstevel@tonic-gate  * this software for any purpose.  It is provided "as is" without express
250Sstevel@tonic-gate  * or implied warranty.
265053Sgtb  *
270Sstevel@tonic-gate  */
280Sstevel@tonic-gate /*
290Sstevel@tonic-gate  * Copyright (C) 1998 by the FundsXpress, INC.
305053Sgtb  *
310Sstevel@tonic-gate  * All rights reserved.
325053Sgtb  *
330Sstevel@tonic-gate  * Export of this software from the United States of America may require
340Sstevel@tonic-gate  * a specific license from the United States Government.  It is the
350Sstevel@tonic-gate  * responsibility of any person or organization contemplating export to
360Sstevel@tonic-gate  * obtain such a license before exporting.
375053Sgtb  *
380Sstevel@tonic-gate  * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
390Sstevel@tonic-gate  * distribute this software and its documentation for any purpose and
400Sstevel@tonic-gate  * without fee is hereby granted, provided that the above copyright
410Sstevel@tonic-gate  * notice appear in all copies and that both that copyright notice and
420Sstevel@tonic-gate  * this permission notice appear in supporting documentation, and that
430Sstevel@tonic-gate  * the name of FundsXpress. not be used in advertising or publicity pertaining
440Sstevel@tonic-gate  * to distribution of the software without specific, written prior
450Sstevel@tonic-gate  * permission.  FundsXpress makes no representations about the suitability of
460Sstevel@tonic-gate  * this software for any purpose.  It is provided "as is" without express
470Sstevel@tonic-gate  * or implied warranty.
485053Sgtb  *
490Sstevel@tonic-gate  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
500Sstevel@tonic-gate  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
510Sstevel@tonic-gate  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
520Sstevel@tonic-gate  */
530Sstevel@tonic-gate 
545053Sgtb #include "gssapiP_krb5.h"
550Sstevel@tonic-gate #ifdef HAVE_STRING_H
560Sstevel@tonic-gate #include <string.h>
570Sstevel@tonic-gate #else
580Sstevel@tonic-gate #include <strings.h>
590Sstevel@tonic-gate #endif
60*13132SGlenn.Barry@oracle.com #include <locale.h> /* Solaris Kerberos */
610Sstevel@tonic-gate 
620Sstevel@tonic-gate /*
637934SMark.Phalan@Sun.COM  * $Id: add_cred.c 18396 2006-07-25 20:29:43Z lxs $
640Sstevel@tonic-gate  */
650Sstevel@tonic-gate 
660Sstevel@tonic-gate /* V2 interface */
670Sstevel@tonic-gate OM_uint32
krb5_gss_add_cred(minor_status,input_cred_handle,desired_name,desired_mech,cred_usage,initiator_time_req,acceptor_time_req,output_cred_handle,actual_mechs,initiator_time_rec,acceptor_time_rec)685053Sgtb krb5_gss_add_cred(minor_status, input_cred_handle,
690Sstevel@tonic-gate 		  desired_name, desired_mech, cred_usage,
700Sstevel@tonic-gate 		  initiator_time_req, acceptor_time_req,
715053Sgtb 		  output_cred_handle, actual_mechs,
720Sstevel@tonic-gate 		  initiator_time_rec, acceptor_time_rec)
730Sstevel@tonic-gate     OM_uint32		*minor_status;
740Sstevel@tonic-gate     gss_cred_id_t	input_cred_handle;
750Sstevel@tonic-gate     gss_name_t		desired_name;
760Sstevel@tonic-gate     gss_OID		desired_mech;
770Sstevel@tonic-gate     gss_cred_usage_t	cred_usage;
780Sstevel@tonic-gate     OM_uint32		initiator_time_req;
790Sstevel@tonic-gate     OM_uint32		acceptor_time_req;
800Sstevel@tonic-gate     gss_cred_id_t	*output_cred_handle;
810Sstevel@tonic-gate     gss_OID_set		*actual_mechs;
820Sstevel@tonic-gate     OM_uint32		*initiator_time_rec;
830Sstevel@tonic-gate     OM_uint32		*acceptor_time_rec;
840Sstevel@tonic-gate {
855053Sgtb     krb5_context	context;
865053Sgtb     OM_uint32		major_status, lifetime;
870Sstevel@tonic-gate     krb5_gss_cred_id_t	cred;
880Sstevel@tonic-gate     krb5_error_code	code;
890Sstevel@tonic-gate 
900Sstevel@tonic-gate     /* this is pretty simple, since there's not really any difference
910Sstevel@tonic-gate        between the underlying mechanisms.  The main hair is in copying
920Sstevel@tonic-gate        a mechanism if requested. */
930Sstevel@tonic-gate 
940Sstevel@tonic-gate     /* check if the desired_mech is bogus */
950Sstevel@tonic-gate 
965053Sgtb     if (!g_OID_equal(desired_mech, gss_mech_krb5) &&
970Sstevel@tonic-gate 	!g_OID_equal(desired_mech, gss_mech_krb5_old)) {
980Sstevel@tonic-gate 	*minor_status = 0;
990Sstevel@tonic-gate 	return(GSS_S_BAD_MECH);
1000Sstevel@tonic-gate     }
1010Sstevel@tonic-gate 
1020Sstevel@tonic-gate     /* check if the desired_mech is bogus */
1030Sstevel@tonic-gate 
1040Sstevel@tonic-gate     if ((cred_usage != GSS_C_INITIATE) &&
1050Sstevel@tonic-gate 	(cred_usage != GSS_C_ACCEPT) &&
1060Sstevel@tonic-gate 	(cred_usage != GSS_C_BOTH)) {
1070Sstevel@tonic-gate 	*minor_status = (OM_uint32) G_BAD_USAGE;
1080Sstevel@tonic-gate 	return(GSS_S_FAILURE);
1090Sstevel@tonic-gate     }
1100Sstevel@tonic-gate 
1110Sstevel@tonic-gate     /* since the default credential includes all the mechanisms,
1120Sstevel@tonic-gate        return an error for that case. */
1130Sstevel@tonic-gate 
1140Sstevel@tonic-gate     /*SUPPRESS 29*/
1150Sstevel@tonic-gate     if (input_cred_handle == GSS_C_NO_CREDENTIAL) {
1160Sstevel@tonic-gate 	*minor_status = 0;
1170Sstevel@tonic-gate 	return(GSS_S_DUPLICATE_ELEMENT);
1180Sstevel@tonic-gate     }
1190Sstevel@tonic-gate 
1205053Sgtb     code = krb5_gss_init_context(&context);
1215053Sgtb     if (code) {
1225053Sgtb 	*minor_status = code;
1235053Sgtb 	return GSS_S_FAILURE;
1245053Sgtb     }
1250Sstevel@tonic-gate 
1265053Sgtb     major_status = krb5_gss_validate_cred_1(minor_status, input_cred_handle,
1275053Sgtb 					    context);
1285053Sgtb     if (GSS_ERROR(major_status)) {
129*13132SGlenn.Barry@oracle.com         save_error_info(*minor_status, context);
1305053Sgtb 	krb5_free_context(context);
1315053Sgtb 	return major_status;
1320Sstevel@tonic-gate     }
1330Sstevel@tonic-gate 
1340Sstevel@tonic-gate     cred = (krb5_gss_cred_id_t) input_cred_handle;
1355053Sgtb     k5_mutex_assert_locked(&cred->lock);
1360Sstevel@tonic-gate 
1370Sstevel@tonic-gate     /* check if the cred_usage is equal or "less" than the passed-in cred
1380Sstevel@tonic-gate        if copying */
1390Sstevel@tonic-gate 
1400Sstevel@tonic-gate     if (!((cred->usage == cred_usage) ||
1410Sstevel@tonic-gate 	  ((cred->usage == GSS_C_BOTH) &&
1420Sstevel@tonic-gate 	   (output_cred_handle != NULL)))) {
1435053Sgtb       *minor_status = (OM_uint32) G_BAD_USAGE;
1445053Sgtb       krb5_free_context(context);
1455053Sgtb       return(GSS_S_FAILURE);
1460Sstevel@tonic-gate     }
1470Sstevel@tonic-gate 
1480Sstevel@tonic-gate     /* check that desired_mech isn't already in the credential */
1490Sstevel@tonic-gate 
1500Sstevel@tonic-gate     if ((g_OID_equal(desired_mech, gss_mech_krb5_old) && cred->prerfc_mech) ||
1510Sstevel@tonic-gate 	(g_OID_equal(desired_mech, gss_mech_krb5) && cred->rfc_mech)) {
1520Sstevel@tonic-gate 	*minor_status = 0;
1535053Sgtb 	krb5_free_context(context);
1545053Sgtb 	return(GSS_S_DUPLICATE_ELEMENT);
1555053Sgtb     }
1565053Sgtb 
1575053Sgtb     if (GSS_ERROR(kg_sync_ccache_name(context, minor_status))) {
158*13132SGlenn.Barry@oracle.com         save_error_info(*minor_status, context);
1595053Sgtb 	krb5_free_context(context);
1605053Sgtb 	return GSS_S_FAILURE;
1610Sstevel@tonic-gate     }
1620Sstevel@tonic-gate 
1630Sstevel@tonic-gate     /* verify the desired_name */
1640Sstevel@tonic-gate 
1650Sstevel@tonic-gate     /*SUPPRESS 29*/
1660Sstevel@tonic-gate     if ((desired_name != (gss_name_t) NULL) &&
1670Sstevel@tonic-gate 	(! kg_validate_name(desired_name))) {
168*13132SGlenn.Barry@oracle.com 	*minor_status = (OM_uint32) G_VALIDATE_FAILED;
1695053Sgtb 	krb5_free_context(context);
1705053Sgtb 	return(GSS_S_CALL_BAD_STRUCTURE|GSS_S_BAD_NAME);
1710Sstevel@tonic-gate     }
1720Sstevel@tonic-gate 
1730Sstevel@tonic-gate     /* make sure the desired_name is the same as the existing one */
1740Sstevel@tonic-gate 
1750Sstevel@tonic-gate     if (desired_name &&
1760Sstevel@tonic-gate 	!krb5_principal_compare(context, (krb5_principal) desired_name,
1770Sstevel@tonic-gate 				cred->princ)) {
178*13132SGlenn.Barry@oracle.com         /* Solaris Kerberos: spruce-up the err msg */
179*13132SGlenn.Barry@oracle.com         krb5_principal dname = (krb5_principal) desired_name;
180*13132SGlenn.Barry@oracle.com 	char *s_name = NULL, *s_princ= NULL;
181*13132SGlenn.Barry@oracle.com 	int kret = krb5_unparse_name(context, dname, &s_name);
182*13132SGlenn.Barry@oracle.com 	int kret1 = krb5_unparse_name(context, cred->princ, &s_princ);
183*13132SGlenn.Barry@oracle.com 	*minor_status = (OM_uint32) G_BAD_USAGE;
184*13132SGlenn.Barry@oracle.com 	if (kret == 0 && kret1 == 0) {
185*13132SGlenn.Barry@oracle.com 	    krb5_set_error_message(context, *minor_status,
186*13132SGlenn.Barry@oracle.com 				dgettext(TEXT_DOMAIN,
187*13132SGlenn.Barry@oracle.com 					"Desired name principal '%s' does not match '%s'"),
188*13132SGlenn.Barry@oracle.com 				s_name, s_princ);
189*13132SGlenn.Barry@oracle.com 	    save_error_info(*minor_status, context);
190*13132SGlenn.Barry@oracle.com 	}
191*13132SGlenn.Barry@oracle.com 	if (s_name)
192*13132SGlenn.Barry@oracle.com 	    krb5_free_unparsed_name(context, s_name);
193*13132SGlenn.Barry@oracle.com 	if (s_princ)
194*13132SGlenn.Barry@oracle.com 	    krb5_free_unparsed_name(context, s_princ);
195*13132SGlenn.Barry@oracle.com 
1965053Sgtb 	krb5_free_context(context);
1975053Sgtb 	return(GSS_S_BAD_NAME);
1980Sstevel@tonic-gate     }
1990Sstevel@tonic-gate 
2000Sstevel@tonic-gate     /* copy the cred if necessary */
2010Sstevel@tonic-gate 
2020Sstevel@tonic-gate     if (output_cred_handle) {
2030Sstevel@tonic-gate 	/* make a copy */
2040Sstevel@tonic-gate 	krb5_gss_cred_id_t new_cred;
2050Sstevel@tonic-gate 	char *kttype, ktboth[1024];
206781Sgtb 	const char *cctype, *ccname;
207781Sgtb 	char ccboth[1024];
2080Sstevel@tonic-gate 
2090Sstevel@tonic-gate 	if ((new_cred =
2100Sstevel@tonic-gate 	     (krb5_gss_cred_id_t) xmalloc(sizeof(krb5_gss_cred_id_rec)))
2110Sstevel@tonic-gate 	    == NULL) {
2120Sstevel@tonic-gate 	    *minor_status = ENOMEM;
2135053Sgtb 	    krb5_free_context(context);
2145053Sgtb 	    return(GSS_S_FAILURE);
2150Sstevel@tonic-gate 	}
2160Sstevel@tonic-gate 	memset(new_cred, 0, sizeof(krb5_gss_cred_id_rec));
2170Sstevel@tonic-gate 
2180Sstevel@tonic-gate 	new_cred->usage = cred_usage;
2190Sstevel@tonic-gate 	new_cred->prerfc_mech = cred->prerfc_mech;
2200Sstevel@tonic-gate 	new_cred->rfc_mech = cred->rfc_mech;
2210Sstevel@tonic-gate 	new_cred->tgt_expire = cred->tgt_expire;
2220Sstevel@tonic-gate 
2235053Sgtb 	if (cred->princ)
2245053Sgtb 	    code = krb5_copy_principal(context, cred->princ, &new_cred->princ);
2255053Sgtb 	if (code) {
2265053Sgtb 	    xfree(new_cred);
2270Sstevel@tonic-gate 
2280Sstevel@tonic-gate 	    *minor_status = code;
229*13132SGlenn.Barry@oracle.com 	    save_error_info(*minor_status, context);
2305053Sgtb 	    krb5_free_context(context);
2315053Sgtb 	    return(GSS_S_FAILURE);
2320Sstevel@tonic-gate 	}
2335053Sgtb 
2340Sstevel@tonic-gate 	if (cred->keytab) {
2350Sstevel@tonic-gate 	    kttype = krb5_kt_get_type(context, cred->keytab);
2360Sstevel@tonic-gate 	    if ((strlen(kttype)+2) > sizeof(ktboth)) {
2375053Sgtb 		if (new_cred->princ)
2385053Sgtb 		    krb5_free_principal(context, new_cred->princ);
2395053Sgtb 		xfree(new_cred);
2400Sstevel@tonic-gate 
2410Sstevel@tonic-gate 		*minor_status = ENOMEM;
2425053Sgtb 		krb5_free_context(context);
2435053Sgtb 		return(GSS_S_FAILURE);
2440Sstevel@tonic-gate 	    }
2450Sstevel@tonic-gate 
2460Sstevel@tonic-gate 	    strncpy(ktboth, kttype, sizeof(ktboth) - 1);
2470Sstevel@tonic-gate 	    ktboth[sizeof(ktboth) - 1] = '\0';
2480Sstevel@tonic-gate 	    strncat(ktboth, ":", sizeof(ktboth) - 1 - strlen(ktboth));
2490Sstevel@tonic-gate 
2505053Sgtb 	    code = krb5_kt_get_name(context, cred->keytab,
2515053Sgtb 				    ktboth+strlen(ktboth),
2525053Sgtb 				    sizeof(ktboth)-strlen(ktboth));
2530Sstevel@tonic-gate 	    if (code) {
2545053Sgtb 		if(new_cred->princ)
2555053Sgtb 		    krb5_free_principal(context, new_cred->princ);
2565053Sgtb 		xfree(new_cred);
2570Sstevel@tonic-gate 
2580Sstevel@tonic-gate 		*minor_status = code;
259*13132SGlenn.Barry@oracle.com 		save_error_info(*minor_status, context);
2605053Sgtb 		krb5_free_context(context);
2615053Sgtb 		return(GSS_S_FAILURE);
2620Sstevel@tonic-gate 	    }
2630Sstevel@tonic-gate 
2645053Sgtb 	    code = krb5_kt_resolve(context, ktboth, &new_cred->keytab);
2655053Sgtb 	    if (code) {
2665053Sgtb 		if (new_cred->princ)
2670Sstevel@tonic-gate 		krb5_free_principal(context, new_cred->princ);
2685053Sgtb 		xfree(new_cred);
2690Sstevel@tonic-gate 
2700Sstevel@tonic-gate 		*minor_status = code;
271*13132SGlenn.Barry@oracle.com 		save_error_info(*minor_status, context);
2725053Sgtb 		krb5_free_context(context);
2735053Sgtb 		return(GSS_S_FAILURE);
2740Sstevel@tonic-gate 	    }
2750Sstevel@tonic-gate 	} else {
2760Sstevel@tonic-gate 	    new_cred->keytab = NULL;
2770Sstevel@tonic-gate 	}
2780Sstevel@tonic-gate 
2790Sstevel@tonic-gate 	if (cred->rcache) {
2800Sstevel@tonic-gate 	    /* Open the replay cache for this principal. */
2810Sstevel@tonic-gate 	    if ((code = krb5_get_server_rcache(context,
2820Sstevel@tonic-gate 					       krb5_princ_component(context, cred->princ, 0),
2830Sstevel@tonic-gate 					       &new_cred->rcache))) {
2840Sstevel@tonic-gate 		if (new_cred->keytab)
2850Sstevel@tonic-gate 		    krb5_kt_close(context, new_cred->keytab);
2865053Sgtb 		if (new_cred->princ)
2875053Sgtb 		    krb5_free_principal(context, new_cred->princ);
2885053Sgtb 		xfree(new_cred);
2890Sstevel@tonic-gate 
290*13132SGlenn.Barry@oracle.com 		*minor_status = code;
291*13132SGlenn.Barry@oracle.com 		save_error_info(*minor_status, context);
2925053Sgtb 		krb5_free_context(context);
2935053Sgtb 		return(GSS_S_FAILURE);
2940Sstevel@tonic-gate 	    }
2950Sstevel@tonic-gate 	} else {
2960Sstevel@tonic-gate 	    new_cred->rcache = NULL;
2970Sstevel@tonic-gate 	}
2980Sstevel@tonic-gate 
2990Sstevel@tonic-gate 	if (cred->ccache) {
3000Sstevel@tonic-gate 	    cctype = krb5_cc_get_type(context, cred->ccache);
3010Sstevel@tonic-gate 	    ccname = krb5_cc_get_name(context, cred->ccache);
3020Sstevel@tonic-gate 
3030Sstevel@tonic-gate 	    if ((strlen(cctype)+strlen(ccname)+2) > sizeof(ccboth)) {
3040Sstevel@tonic-gate 		if (new_cred->rcache)
3050Sstevel@tonic-gate 		    krb5_rc_close(context, new_cred->rcache);
3060Sstevel@tonic-gate 		if (new_cred->keytab)
3070Sstevel@tonic-gate 		    krb5_kt_close(context, new_cred->keytab);
3085053Sgtb 		if (new_cred->princ)
3090Sstevel@tonic-gate 		krb5_free_principal(context, new_cred->princ);
3105053Sgtb 		xfree(new_cred);
3110Sstevel@tonic-gate 
3125053Sgtb 		krb5_free_context(context);
3130Sstevel@tonic-gate 		*minor_status = ENOMEM;
3145053Sgtb 		return(GSS_S_FAILURE);
3150Sstevel@tonic-gate 	    }
3160Sstevel@tonic-gate 
3170Sstevel@tonic-gate 	    strncpy(ccboth, cctype, sizeof(ccboth) - 1);
3180Sstevel@tonic-gate 	    ccboth[sizeof(ccboth) - 1] = '\0';
3190Sstevel@tonic-gate 	    strncat(ccboth, ":", sizeof(ccboth) - 1 - strlen(ccboth));
3200Sstevel@tonic-gate 	    strncat(ccboth, ccname, sizeof(ccboth) - 1 - strlen(ccboth));
3210Sstevel@tonic-gate 
3225053Sgtb 	    code = krb5_cc_resolve(context, ccboth, &new_cred->ccache);
3235053Sgtb 	    if (code) {
3240Sstevel@tonic-gate 		if (new_cred->rcache)
3250Sstevel@tonic-gate 		    krb5_rc_close(context, new_cred->rcache);
3260Sstevel@tonic-gate 		if (new_cred->keytab)
3270Sstevel@tonic-gate 		    krb5_kt_close(context, new_cred->keytab);
3285053Sgtb 		if (new_cred->princ)
3295053Sgtb 		    krb5_free_principal(context, new_cred->princ);
3305053Sgtb 		xfree(new_cred);
331*13132SGlenn.Barry@oracle.com 		*minor_status = code;
332*13132SGlenn.Barry@oracle.com 		save_error_info(*minor_status, context);
3335053Sgtb 		krb5_free_context(context);
3345053Sgtb 		return(GSS_S_FAILURE);
3350Sstevel@tonic-gate 	    }
3360Sstevel@tonic-gate 	} else {
3370Sstevel@tonic-gate 	    new_cred->ccache = NULL;
3380Sstevel@tonic-gate 	}
3390Sstevel@tonic-gate 
3400Sstevel@tonic-gate 	/* intern the credential handle */
3410Sstevel@tonic-gate 
3420Sstevel@tonic-gate 	if (! kg_save_cred_id((gss_cred_id_t) new_cred)) {
3430Sstevel@tonic-gate 	    if (new_cred->ccache)
3440Sstevel@tonic-gate 		krb5_cc_close(context, new_cred->ccache);
3450Sstevel@tonic-gate 	    if (new_cred->rcache)
3460Sstevel@tonic-gate 		krb5_rc_close(context, new_cred->rcache);
3470Sstevel@tonic-gate 	    if (new_cred->keytab)
3480Sstevel@tonic-gate 		krb5_kt_close(context, new_cred->keytab);
3495053Sgtb 	    if (new_cred->princ)
3500Sstevel@tonic-gate 	    krb5_free_principal(context, new_cred->princ);
3515053Sgtb 	    xfree(new_cred);
3525053Sgtb 	    krb5_free_context(context);
3530Sstevel@tonic-gate 
3540Sstevel@tonic-gate 	    *minor_status = (OM_uint32) G_VALIDATE_FAILED;
3555053Sgtb 	    return(GSS_S_FAILURE);
3560Sstevel@tonic-gate 	}
3570Sstevel@tonic-gate 
3580Sstevel@tonic-gate 	/* modify new_cred */
3590Sstevel@tonic-gate 
3600Sstevel@tonic-gate 	cred = new_cred;
3610Sstevel@tonic-gate     }
3620Sstevel@tonic-gate 
3630Sstevel@tonic-gate     /* set the flag for the new mechanism */
3640Sstevel@tonic-gate 
3650Sstevel@tonic-gate     if (g_OID_equal(desired_mech, gss_mech_krb5_old))
3660Sstevel@tonic-gate 	cred->prerfc_mech = 1;
3670Sstevel@tonic-gate     else if (g_OID_equal(desired_mech, gss_mech_krb5))
3680Sstevel@tonic-gate 	cred->rfc_mech = 1;
3690Sstevel@tonic-gate 
3700Sstevel@tonic-gate     /* set the outputs */
3710Sstevel@tonic-gate 
3725053Sgtb     if (GSS_ERROR(major_status = krb5_gss_inquire_cred(minor_status,
3737934SMark.Phalan@Sun.COM 						       (gss_cred_id_t)cred,
3745053Sgtb 						       NULL, &lifetime,
3755053Sgtb 						       NULL, actual_mechs))) {
3760Sstevel@tonic-gate 	OM_uint32 dummy;
3770Sstevel@tonic-gate 
3780Sstevel@tonic-gate 	if (output_cred_handle)
3795053Sgtb 	    (void) krb5_gss_release_cred(&dummy, (gss_cred_id_t *) &cred);
3805053Sgtb 	krb5_free_context(context);
3810Sstevel@tonic-gate 
3825053Sgtb 	return(major_status);
3830Sstevel@tonic-gate     }
3840Sstevel@tonic-gate 
3850Sstevel@tonic-gate     if (initiator_time_rec)
3860Sstevel@tonic-gate 	*initiator_time_rec = lifetime;
3870Sstevel@tonic-gate     if (acceptor_time_rec)
3880Sstevel@tonic-gate 	*acceptor_time_rec = lifetime;
3890Sstevel@tonic-gate 
3900Sstevel@tonic-gate     if (output_cred_handle)
3917934SMark.Phalan@Sun.COM 	*output_cred_handle = (gss_cred_id_t)cred;
3920Sstevel@tonic-gate 
3935053Sgtb     krb5_free_context(context);
3945053Sgtb     *minor_status = 0;
3955053Sgtb     return(GSS_S_COMPLETE);
3960Sstevel@tonic-gate }
397