From dfaaf9c93fe02ddb216a4dd3764fdcd41e063025 Mon Sep 17 00:00:00 2001 From: Luke Howard Date: Fri, 4 Jan 2019 15:47:29 +1100 Subject: [PATCH] gssapi: honor acceptor credential in SPNEGO (#506) SPNEGO uses the callback function acceptor_approved() in order to determine which mechanisms to advertise to the initiator in the case that the initiator sent an empty initial context token. Prior to this commit, that function was not passed in the acceptor credential (if present), so always uses a default credential. For correctness, we should only advertise the availability of mechanisms for which we have a credential. --- lib/gssapi/spnego/accept_sec_context.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/lib/gssapi/spnego/accept_sec_context.c b/lib/gssapi/spnego/accept_sec_context.c index 545492480..4f9bc4f1e 100644 --- a/lib/gssapi/spnego/accept_sec_context.c +++ b/lib/gssapi/spnego/accept_sec_context.c @@ -63,7 +63,7 @@ send_reject (OM_uint32 *minor_status, } static OM_uint32 -acceptor_approved(gss_const_cred_id_t cred_unused, +acceptor_approved(gss_const_cred_id_t input_cred, gss_name_t target_name, gss_OID mech) { @@ -74,6 +74,11 @@ acceptor_approved(gss_const_cred_id_t cred_unused, if (target_name == GSS_C_NO_NAME) return GSS_S_COMPLETE; + if (input_cred != GSS_C_NO_CREDENTIAL) { + return gss_inquire_cred_by_mech(&junk, input_cred, mech, + NULL, NULL, NULL, NULL); + } + gss_create_empty_oid_set(&junk, &oidset); gss_add_oid_set_member(&junk, mech, &oidset); @@ -89,6 +94,7 @@ acceptor_approved(gss_const_cred_id_t cred_unused, static OM_uint32 send_supported_mechs (OM_uint32 *minor_status, + gss_const_cred_id_t acceptor_cred, gss_buffer_t output_token) { NegotiationTokenWin nt; @@ -104,7 +110,7 @@ send_supported_mechs (OM_uint32 *minor_status, nt.u.negTokenInit.negHints = NULL; ret = _gss_spnego_indicate_mechtypelist(minor_status, GSS_C_NO_NAME, - acceptor_approved, 1, NULL, + acceptor_approved, 1, acceptor_cred, &nt.u.negTokenInit.mechTypes, NULL); if (ret != GSS_S_COMPLETE) { return ret; @@ -501,7 +507,8 @@ acceptor_start mech_buf.value = NULL; if (input_token_buffer->length == 0) - return send_supported_mechs (minor_status, output_token); + return send_supported_mechs (minor_status, + acceptor_cred_handle, output_token); ret = _gss_spnego_alloc_sec_context(minor_status, context_handle); if (ret != GSS_S_COMPLETE)