From 784ffbfa6abd04dfa67903489c3b12b68de9867a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Love=20H=C3=B6rnquist=20=C3=85strand?= Date: Sun, 16 Mar 2008 11:33:58 +0000 Subject: [PATCH] Make delegated credentials delegated directly, Oleg Sharoiko pointed out that it always didnt work with the old code. Also add som missing cred and context pass-thou functions in the SPNEGO layer git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@22688 ec53bebd-3082-4978-b11e-865c3cabbd6b --- lib/gssapi/spnego/accept_sec_context.c | 59 +++++++++----------------- lib/gssapi/spnego/compat.c | 3 -- lib/gssapi/spnego/context_stubs.c | 30 ++++++++++++- lib/gssapi/spnego/cred_stubs.c | 20 +++++++++ lib/gssapi/spnego/external.c | 11 +++-- lib/gssapi/spnego/spnego_locl.h | 1 - 6 files changed, 76 insertions(+), 48 deletions(-) diff --git a/lib/gssapi/spnego/accept_sec_context.c b/lib/gssapi/spnego/accept_sec_context.c index 9af4e1b1e..0a81e0bcc 100644 --- a/lib/gssapi/spnego/accept_sec_context.c +++ b/lib/gssapi/spnego/accept_sec_context.c @@ -635,9 +635,6 @@ acceptor_start if (ctx->mech_src_name != GSS_C_NO_NAME) gss_release_name(&junk, &ctx->mech_src_name); - if (ctx->delegated_cred_id != GSS_C_NO_CREDENTIAL) - _gss_spnego_release_cred(&junk, &ctx->delegated_cred_id); - ret = gss_accept_sec_context(minor_status, &ctx->negotiated_ctx_id, mech_cred, @@ -649,19 +646,20 @@ acceptor_start &ctx->mech_flags, &ctx->mech_time_rec, &mech_delegated_cred); + + if (mech_delegated_cred && delegated_cred_handle) { + _gss_spnego_alloc_cred(&junk, + mech_delegated_cred, + delegated_cred_handle); + } else if (mech_delegated_cred != GSS_C_NO_CREDENTIAL) + gss_release_cred(&junk, &mech_delegated_cred); + if (ret == GSS_S_COMPLETE || ret == GSS_S_CONTINUE_NEEDED) { ctx->preferred_mech_type = preferred_mech_type; ctx->negotiated_mech_type = preferred_mech_type; if (ret == GSS_S_COMPLETE) ctx->open = 1; - if (mech_delegated_cred && delegated_cred_handle) - ret = _gss_spnego_alloc_cred(&junk, - mech_delegated_cred, - delegated_cred_handle); - else - gss_release_cred(&junk, &mech_delegated_cred); - ret = acceptor_complete(minor_status, ctx, &get_mic, @@ -740,10 +738,6 @@ out: *src_name = (gss_name_t)name; } } - if (delegated_cred_handle != NULL) { - *delegated_cred_handle = ctx->delegated_cred_id; - ctx->delegated_cred_id = GSS_C_NO_CREDENTIAL; - } } if (mech_type != NULL) @@ -780,7 +774,7 @@ acceptor_continue gss_cred_id_t *delegated_cred_handle ) { - OM_uint32 ret, ret2, minor; + OM_uint32 ret, ret2, minor, junk; NegotiationToken nt; size_t nt_len; NegTokenResp *na; @@ -836,27 +830,16 @@ acceptor_continue if (mech_input_token != GSS_C_NO_BUFFER) { gss_cred_id_t mech_cred; - gss_cred_id_t mech_delegated_cred; - gss_cred_id_t *mech_delegated_cred_p; + gss_cred_id_t mech_delegated_cred = GSS_C_NO_CREDENTIAL; if (acceptor_cred != NULL) mech_cred = acceptor_cred->negotiated_cred_id; else mech_cred = GSS_C_NO_CREDENTIAL; - if (delegated_cred_handle != NULL) { - mech_delegated_cred = GSS_C_NO_CREDENTIAL; - mech_delegated_cred_p = &mech_delegated_cred; - } else { - mech_delegated_cred_p = NULL; - } - if (ctx->mech_src_name != GSS_C_NO_NAME) gss_release_name(&minor, &ctx->mech_src_name); - if (ctx->delegated_cred_id != GSS_C_NO_CREDENTIAL) - _gss_spnego_release_cred(&minor, &ctx->delegated_cred_id); - ret = gss_accept_sec_context(&minor, &ctx->negotiated_ctx_id, mech_cred, @@ -867,16 +850,16 @@ acceptor_continue &obuf, &ctx->mech_flags, &ctx->mech_time_rec, - mech_delegated_cred_p); + &mech_delegated_cred); + + if (mech_delegated_cred && delegated_cred_handle) { + _gss_spnego_alloc_cred(&junk, + mech_delegated_cred, + delegated_cred_handle); + } else if (mech_delegated_cred != GSS_C_NO_CREDENTIAL) + gss_release_cred(&junk, &mech_delegated_cred); + if (ret == GSS_S_COMPLETE || ret == GSS_S_CONTINUE_NEEDED) { - if (mech_delegated_cred_p != NULL && - mech_delegated_cred != GSS_C_NO_CREDENTIAL) { - ret2 = _gss_spnego_alloc_cred(minor_status, - mech_delegated_cred, - &ctx->delegated_cred_id); - if (ret2 != GSS_S_COMPLETE) - ret = ret2; - } mech_output_token = &obuf; } if (ret != GSS_S_COMPLETE && ret != GSS_S_CONTINUE_NEEDED) { @@ -958,10 +941,6 @@ acceptor_continue *src_name = (gss_name_t)name; } } - if (delegated_cred_handle != NULL) { - *delegated_cred_handle = ctx->delegated_cred_id; - ctx->delegated_cred_id = GSS_C_NO_CREDENTIAL; - } } if (mech_type != NULL) diff --git a/lib/gssapi/spnego/compat.c b/lib/gssapi/spnego/compat.c index a92940d48..67d9b202a 100644 --- a/lib/gssapi/spnego/compat.c +++ b/lib/gssapi/spnego/compat.c @@ -76,7 +76,6 @@ OM_uint32 _gss_spnego_alloc_sec_context (OM_uint32 * minor_status, ctx->mech_flags = 0; ctx->mech_time_rec = 0; ctx->mech_src_name = GSS_C_NO_NAME; - ctx->delegated_cred_id = GSS_C_NO_CREDENTIAL; ctx->open = 0; ctx->local = 0; @@ -124,8 +123,6 @@ OM_uint32 _gss_spnego_internal_delete_sec_context if (ctx->initiator_mech_types.val != NULL) free_MechTypeList(&ctx->initiator_mech_types); - _gss_spnego_release_cred(&minor, &ctx->delegated_cred_id); - gss_release_oid(&minor, &ctx->preferred_mech_type); ctx->negotiated_mech_type = GSS_C_NO_OID; diff --git a/lib/gssapi/spnego/context_stubs.c b/lib/gssapi/spnego/context_stubs.c index 7a15caf2a..60c53058b 100644 --- a/lib/gssapi/spnego/context_stubs.c +++ b/lib/gssapi/spnego/context_stubs.c @@ -907,7 +907,7 @@ OM_uint32 _gss_spnego_set_sec_context_option return GSS_S_NO_CONTEXT; } - ctx = (gssspnego_ctx)context_handle; + ctx = (gssspnego_ctx)*context_handle; if (ctx->negotiated_ctx_id == GSS_C_NO_CONTEXT) { return GSS_S_NO_CONTEXT; @@ -919,3 +919,31 @@ OM_uint32 _gss_spnego_set_sec_context_option value); } + +OM_uint32 +_gss_spnego_pseudo_random(OM_uint32 *minor_status, + gss_ctx_id_t context_handle, + int prf_key, + const gss_buffer_t prf_in, + ssize_t desired_output_len, + gss_buffer_t prf_out) +{ + gssspnego_ctx ctx; + + *minor_status = 0; + + if (context_handle == GSS_C_NO_CONTEXT) + return GSS_S_NO_CONTEXT; + + ctx = (gssspnego_ctx)context_handle; + + if (ctx->negotiated_ctx_id == GSS_C_NO_CONTEXT) + return GSS_S_NO_CONTEXT; + + return gss_pseudo_random(minor_status, + ctx->negotiated_ctx_id, + prf_key, + prf_in, + desired_output_len, + prf_out); +} diff --git a/lib/gssapi/spnego/cred_stubs.c b/lib/gssapi/spnego/cred_stubs.c index 9ce16587b..836b63f43 100644 --- a/lib/gssapi/spnego/cred_stubs.c +++ b/lib/gssapi/spnego/cred_stubs.c @@ -334,3 +334,23 @@ OM_uint32 _gss_spnego_inquire_cred_by_oid return ret; } +OM_uint32 +_gss_spnego_set_cred_option (OM_uint32 *minor_status, + gss_cred_id_t *cred_handle, + const gss_OID object, + const gss_buffer_t value) +{ + gssspnego_cred cred; + + if (cred_handle == NULL || *cred_handle == GSS_C_NO_CREDENTIAL) { + *minor_status = 0; + return GSS_S_NO_CRED; + } + + cred = (gssspnego_cred)*cred_handle; + return gss_set_cred_option(minor_status, + &cred->negotiated_cred_id, + object, + value); +} + diff --git a/lib/gssapi/spnego/external.c b/lib/gssapi/spnego/external.c index 58824a7f0..d5718c3fd 100644 --- a/lib/gssapi/spnego/external.c +++ b/lib/gssapi/spnego/external.c @@ -57,8 +57,8 @@ static gssapi_mech_interface_desc spnego_mech = { _gss_spnego_verify_mic, _gss_spnego_wrap, _gss_spnego_unwrap, - NULL, - NULL, + NULL, /* gm_display_status */ + NULL, /* gm_indicate_mechs */ _gss_spnego_compare_name, _gss_spnego_display_name, _gss_spnego_import_name, @@ -74,7 +74,12 @@ static gssapi_mech_interface_desc spnego_mech = { _gss_spnego_inquire_names_for_mech, _gss_spnego_inquire_mechs_for_name, _gss_spnego_canonicalize_name, - _gss_spnego_duplicate_name + _gss_spnego_duplicate_name, + _gss_spnego_inquire_sec_context_by_oid, + _gss_spnego_inquire_cred_by_oid, + _gss_spnego_set_sec_context_option, + _gss_spnego_set_cred_option, + _gss_spnego_pseudo_random }; gssapi_mech_interface diff --git a/lib/gssapi/spnego/spnego_locl.h b/lib/gssapi/spnego/spnego_locl.h index 84e6e7729..8344e750a 100644 --- a/lib/gssapi/spnego/spnego_locl.h +++ b/lib/gssapi/spnego/spnego_locl.h @@ -86,7 +86,6 @@ typedef struct { OM_uint32 mech_flags; OM_uint32 mech_time_rec; gss_name_t mech_src_name; - gss_cred_id_t delegated_cred_id; unsigned int open : 1; unsigned int local : 1; unsigned int require_mic : 1;