Skip to content

Commit

Permalink
Let SPNEGO display mechanism errors
Browse files Browse the repository at this point in the history
To avoid potential recursion we use a thread local variable that tells
us whether the ancestor was called via spnego_gss_display_name().  If
we detect recursion, we assume that we returned a com_err code like
ENOMEM and call error_message(); in the worst case that will result in
an "Unknown error" message.

[ghudson@mit.edu: Edited comments and commit message; removed an
unneeded line of code.]

ticket: 7045
target_version: 1.12.1
tags: pullup
  • Loading branch information
simo5 authored and greghudson committed Dec 18, 2013
1 parent c91f2a2 commit d160bc7
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 8 deletions.
1 change: 1 addition & 0 deletions src/include/k5-thread.h
Original file line number Diff line number Diff line change
Expand Up @@ -406,6 +406,7 @@ typedef enum {
K5_KEY_GSS_KRB5_SET_CCACHE_OLD_NAME,
K5_KEY_GSS_KRB5_CCACHE_NAME,
K5_KEY_GSS_KRB5_ERROR_MESSAGE,
K5_KEY_GSS_SPNEGO_STATUS,
#if defined(__MACH__) && defined(__APPLE__)
K5_KEY_IPC_CONNECTION_INFO,
#endif
Expand Down
42 changes: 34 additions & 8 deletions src/lib/gssapi/spnego/spnego_mech.c
Original file line number Diff line number Diff line change
Expand Up @@ -85,8 +85,8 @@ extern int gssint_put_der_length(unsigned int, unsigned char **, unsigned int);


/* private routines for spnego_mechanism */
static spnego_token_t make_spnego_token(char *);
static gss_buffer_desc make_err_msg(char *);
static spnego_token_t make_spnego_token(const char *);
static gss_buffer_desc make_err_msg(const char *);
static int g_token_size(gss_OID_const, unsigned int);
static int g_make_token_header(gss_OID_const, unsigned int,
unsigned char **, unsigned int);
Expand Down Expand Up @@ -316,6 +316,12 @@ int gss_krb5int_lib_init(void);

int gss_spnegoint_lib_init(void)
{
int err;

err = k5_key_register(K5_KEY_GSS_SPNEGO_STATUS, NULL);
if (err)
return err;

#ifdef _GSS_STATIC_LINK
return gss_spnegomechglue_init();
#else
Expand Down Expand Up @@ -1791,7 +1797,6 @@ spnego_gss_accept_sec_context(
}
#endif /* LEAN_CLIENT */


/*ARGSUSED*/
OM_uint32 KRB5_CALLCONV
spnego_gss_display_status(
Expand All @@ -1802,6 +1807,9 @@ spnego_gss_display_status(
OM_uint32 *message_context,
gss_buffer_t status_string)
{
OM_uint32 maj = GSS_S_COMPLETE;
int ret;

dsyslog("Entering display_status\n");

*message_context = 0;
Expand Down Expand Up @@ -1832,13 +1840,31 @@ spnego_gss_display_status(
"return a valid token"));
break;
default:
status_string->length = 0;
status_string->value = "";
/* Not one of our minor codes; might be from a mech. Call back
* to gss_display_status, but first check for recursion. */
if (k5_getspecific(K5_KEY_GSS_SPNEGO_STATUS) != NULL) {
/* Perhaps we returned a com_err code like ENOMEM. */
const char *err = error_message(status_value);
*status_string = make_err_msg(err);
break;
}
/* Set a non-null pointer value; doesn't matter which one. */
ret = k5_setspecific(K5_KEY_GSS_SPNEGO_STATUS, &ret);
if (ret != 0) {
*minor_status = ret;
maj = GSS_S_FAILURE;
break;
}
maj = gss_display_status(minor_status, status_value,
status_type, mech_type,
message_context, status_string);
/* This is unlikely to fail; not much we can do if it does. */
(void)k5_setspecific(K5_KEY_GSS_SPNEGO_STATUS, NULL);
break;
}

dsyslog("Leaving display_status\n");
return (GSS_S_COMPLETE);
return maj;
}


Expand Down Expand Up @@ -3550,13 +3576,13 @@ negotiate_mech(gss_OID_set supported, gss_OID_set received,
* these routines will be changes to return the error string.
*/
static spnego_token_t
make_spnego_token(char *name)
make_spnego_token(const char *name)
{
return (spnego_token_t)strdup(name);
}

static gss_buffer_desc
make_err_msg(char *name)
make_err_msg(const char *name)
{
gss_buffer_desc buffer;

Expand Down

0 comments on commit d160bc7

Please sign in to comment.