From: Luke Howard Date: Wed, 16 Mar 2011 04:14:52 +0000 (+1100) Subject: refactor OID interning code X-Git-Tag: dvd/201105~12^2~103 X-Git-Url: http://www.project-moonshot.org/gitweb/?p=mech_eap.orig;a=commitdiff_plain;h=41837238438574671f24bf354c61aebe02274643 refactor OID interning code --- diff --git a/accept_sec_context.c b/accept_sec_context.c index 9ef0fc9..5d2c113 100644 --- a/accept_sec_context.c +++ b/accept_sec_context.c @@ -871,8 +871,14 @@ gss_accept_sec_context(OM_uint32 *minor, goto cleanup; if (mech_type != NULL) { - if (!gssEapInternalizeOid(ctx->mechanismUsed, mech_type)) - duplicateOid(&tmpMinor, ctx->mechanismUsed, mech_type); + OM_uint32 tmpMajor; + + tmpMajor = gssEapCanonicalizeOid(&tmpMinor, ctx->mechanismUsed, 0, mech_type); + if (GSS_ERROR(tmpMajor)) { + major = tmpMajor; + *minor = tmpMinor; + goto cleanup; + } } if (ret_flags != NULL) *ret_flags = ctx->gssFlags; diff --git a/canonicalize_name.c b/canonicalize_name.c index 390864b..82d96b6 100644 --- a/canonicalize_name.c +++ b/canonicalize_name.c @@ -56,7 +56,7 @@ gss_canonicalize_name(OM_uint32 *minor, GSSEAP_MUTEX_LOCK(&input_name->mutex); - major = gssEapDuplicateName(minor, input_name, output_name); + major = gssEapCanonicalizeName(minor, input_name, mech_type, output_name); GSSEAP_MUTEX_UNLOCK(&input_name->mutex); diff --git a/import_sec_context.c b/import_sec_context.c index 08c5005..df52410 100644 --- a/import_sec_context.c +++ b/import_sec_context.c @@ -121,16 +121,9 @@ importMechanismOid(OM_uint32 *minor, oidBuf.elements = &p[4]; - if (!gssEapIsConcreteMechanismOid(&oidBuf)) { - *minor = GSSEAP_WRONG_MECH; - return GSS_S_BAD_MECH; - } - - if (!gssEapInternalizeOid(&oidBuf, pOid)) { - major = duplicateOid(minor, &oidBuf, pOid); - if (GSS_ERROR(major)) - return major; - } + major = gssEapCanonicalizeOid(minor, &oidBuf, 0, pOid); + if (GSS_ERROR(major)) + return major; *pBuf += 4 + oidBuf.length; *pRemain -= 4 + oidBuf.length; diff --git a/init_sec_context.c b/init_sec_context.c index c42fa88..a731833 100644 --- a/init_sec_context.c +++ b/init_sec_context.c @@ -362,15 +362,10 @@ initBegin(OM_uint32 *minor, GSSEAP_MUTEX_UNLOCK(&target->mutex); } - if (mech == GSS_C_NULL_OID) { - major = gssEapDefaultMech(minor, &ctx->mechanismUsed); - } else if (gssEapIsConcreteMechanismOid(mech)) { - if (!gssEapInternalizeOid(mech, &ctx->mechanismUsed)) - major = duplicateOid(minor, mech, &ctx->mechanismUsed); - } else { - major = GSS_S_BAD_MECH; - *minor = GSSEAP_WRONG_MECH; - } + major = gssEapCanonicalizeOid(minor, + mech, + OID_FLAG_NULL_VALID | OID_FLAG_MAP_NULL_TO_DEFAULT_MECH, + &ctx->mechanismUsed); if (GSS_ERROR(major)) return major; @@ -974,8 +969,14 @@ gss_init_sec_context(OM_uint32 *minor, goto cleanup; if (actual_mech_type != NULL) { - if (!gssEapInternalizeOid(ctx->mechanismUsed, actual_mech_type)) - duplicateOid(&tmpMinor, ctx->mechanismUsed, actual_mech_type); + OM_uint32 tmpMajor; + + tmpMajor = gssEapCanonicalizeOid(&tmpMinor, ctx->mechanismUsed, 0, actual_mech_type); + if (GSS_ERROR(tmpMajor)) { + major = tmpMajor; + *minor = tmpMinor; + goto cleanup; + } } if (ret_flags != NULL) *ret_flags = ctx->gssFlags; diff --git a/inquire_context.c b/inquire_context.c index 796f450..0e7b586 100644 --- a/inquire_context.c +++ b/inquire_context.c @@ -84,11 +84,9 @@ gss_inquire_context(OM_uint32 *minor, } if (mech_type != NULL) { - if (!gssEapInternalizeOid(ctx->mechanismUsed, mech_type)) { - major = duplicateOid(minor, ctx->mechanismUsed, mech_type); - if (GSS_ERROR(major)) - goto cleanup; - } + major = gssEapCanonicalizeOid(minor, ctx->mechanismUsed, 0, mech_type); + if (GSS_ERROR(major)) + goto cleanup; } if (ctx_flags != NULL) { diff --git a/inquire_name.c b/inquire_name.c index c62ff9e..2a4e0e3 100644 --- a/inquire_name.c +++ b/inquire_name.c @@ -47,9 +47,9 @@ OM_uint32 gss_inquire_name(OM_uint32 *minor, *minor = 0; if (name_is_MN != NULL) - *name_is_MN = 1; + *name_is_MN = 0; if (MN_mech != NULL) - *MN_mech = GSS_EAP_MECHANISM; + *MN_mech = GSS_C_NO_OID; if (attrs != NULL) *attrs = GSS_C_NO_BUFFER_SET; diff --git a/util.h b/util.h index 8756c95..0f0c99c 100644 --- a/util.h +++ b/util.h @@ -205,12 +205,6 @@ gssEapContextTime(OM_uint32 *minor, gss_ctx_id_t context_handle, OM_uint32 *time_rec); -OM_uint32 -gssEapDisplayName(OM_uint32 *minor, - gss_name_t name, - gss_buffer_t output_name_buffer, - gss_OID *output_name_type); - /* util_cred.c */ OM_uint32 gssEapAllocCred(OM_uint32 *minor, gss_cred_id_t *pCred); OM_uint32 gssEapReleaseCred(OM_uint32 *minor, gss_cred_id_t *pCred); @@ -410,9 +404,16 @@ gssEapExportLucidSecContext(OM_uint32 *minor, /* util_mech.c */ extern gss_OID GSS_EAP_MECHANISM; -int -gssEapInternalizeOid(const gss_OID oid, - gss_OID *const pInternalizedOid); +#define OID_FLAG_NULL_VALID 0x00000001 +#define OID_FLAG_FAMILY_MECH_VALID 0x00000002 +#define OID_FLAG_MAP_NULL_TO_DEFAULT_MECH 0x00000004 +#define OID_FLAG_MAP_FAMILY_MECH_TO_NULL 0x00000008 + +OM_uint32 +gssEapCanonicalizeOid(OM_uint32 *minor, + const gss_OID oid, + OM_uint32 flags, + gss_OID *pOid); OM_uint32 gssEapReleaseOid(OM_uint32 *minor, gss_OID *oid); @@ -478,6 +479,18 @@ gssEapDuplicateName(OM_uint32 *minor, const gss_name_t input_name, gss_name_t *dest_name); +OM_uint32 +gssEapCanonicalizeName(OM_uint32 *minor, + const gss_name_t input_name, + const gss_OID mech_type, + gss_name_t *dest_name); + +OM_uint32 +gssEapDisplayName(OM_uint32 *minor, + gss_name_t name, + gss_buffer_t output_name_buffer, + gss_OID *output_name_type); + /* util_oid.c */ OM_uint32 composeOid(OM_uint32 *minor_status, diff --git a/util_attr.cpp b/util_attr.cpp index 28065ac..a24064a 100644 --- a/util_attr.cpp +++ b/util_attr.cpp @@ -760,10 +760,22 @@ gss_eap_attr_ctx::composeAttributeName(unsigned int type, OM_uint32 gssEapInquireName(OM_uint32 *minor, gss_name_t name, - int *name_is_MN GSSEAP_UNUSED, - gss_OID *MN_mech GSSEAP_UNUSED, + int *name_is_MN, + gss_OID *MN_mech, gss_buffer_set_t *attrs) { + OM_uint32 major; + + if (name_is_MN != NULL) + *name_is_MN = (name->mechanismUsed != GSS_C_NULL_OID); + + if (MN_mech != NULL) { + major = gssEapCanonicalizeOid(minor, name->mechanismUsed, + OID_FLAG_NULL_VALID, MN_mech); + if (GSS_ERROR(major)) + return major; + } + if (name->attrCtx == NULL) { *minor = GSSEAP_NO_ATTR_CONTEXT; return GSS_S_UNAVAILABLE; diff --git a/util_mech.c b/util_mech.c index 8ce658e..e12fa54 100644 --- a/util_mech.c +++ b/util_mech.c @@ -71,6 +71,10 @@ gss_OID GSS_EAP_MECHANISM = &gssEapMechOids[0]; gss_OID GSS_EAP_AES128_CTS_HMAC_SHA1_96_MECHANISM = &gssEapMechOids[1]; gss_OID GSS_EAP_AES256_CTS_HMAC_SHA1_96_MECHANISM = &gssEapMechOids[2]; +static int +internalizeOid(const gss_OID oid, + gss_OID *const pInternalizedOid); + /* * Returns TRUE is the OID is a concrete mechanism OID, that is, one * with a Kerberos enctype as the last element. @@ -167,7 +171,7 @@ gssEapEnctypeToOid(OM_uint32 *minor, enctype, oid); if (major == GSS_S_COMPLETE) { - gssEapInternalizeOid(oid, pOid); + internalizeOid(oid, pOid); *pOid = oid; } else { GSSEAP_FREE(oid->elements); @@ -240,7 +244,7 @@ gssEapDefaultMech(OM_uint32 *minor, return GSS_S_BAD_MECH; } - if (!gssEapInternalizeOid(&mechs->elements[0], oid)) { + if (!internalizeOid(&mechs->elements[0], oid)) { /* don't double-free if we didn't internalize it */ mechs->elements[0].length = 0; mechs->elements[0].elements = NULL; @@ -252,9 +256,9 @@ gssEapDefaultMech(OM_uint32 *minor, return GSS_S_COMPLETE; } -int -gssEapInternalizeOid(const gss_OID oid, - gss_OID *const pInternalizedOid) +static int +internalizeOid(const gss_OID oid, + gss_OID *const pInternalizedOid) { int i; @@ -289,7 +293,7 @@ gssEapReleaseOid(OM_uint32 *minor, gss_OID *oid) *minor = 0; - if (gssEapInternalizeOid(*oid, &internalizedOid)) { + if (internalizeOid(*oid, &internalizedOid)) { /* OID was internalized, so we can mark it as "freed" */ *oid = GSS_C_NO_OID; return GSS_S_COMPLETE; @@ -299,6 +303,47 @@ gssEapReleaseOid(OM_uint32 *minor, gss_OID *oid) return GSS_S_CONTINUE_NEEDED; } +OM_uint32 +gssEapCanonicalizeOid(OM_uint32 *minor, + const gss_OID oid, + OM_uint32 flags, + gss_OID *pOid) +{ + OM_uint32 major; + int mapToNull = 0; + + major = GSS_S_COMPLETE; + *minor = 0; + *pOid = GSS_C_NULL_OID; + + if (oid == GSS_C_NULL_OID) { + if ((flags & OID_FLAG_NULL_VALID) == 0) { + *minor = GSSEAP_WRONG_MECH; + return GSS_S_BAD_MECH; + } else if (flags & OID_FLAG_MAP_NULL_TO_DEFAULT_MECH) { + return gssEapDefaultMech(minor, pOid); + } + } else if (oidEqual(oid, GSS_EAP_MECHANISM)) { + if ((flags & OID_FLAG_FAMILY_MECH_VALID) == 0) { + *minor = GSSEAP_WRONG_MECH; + return GSS_S_BAD_MECH; + } else if (flags & OID_FLAG_MAP_FAMILY_MECH_TO_NULL) { + mapToNull = 1; + } + } else if (!gssEapIsConcreteMechanismOid(oid)) { + *minor = GSSEAP_WRONG_MECH; + return GSS_S_BAD_MECH; + } + + if (!mapToNull && oid != GSS_C_NO_OID) { + if (!internalizeOid(oid, pOid)) + major = duplicateOid(minor, oid, pOid); + } + + assert(!GSS_ERROR(major)); + return major; +} + static gss_buffer_desc gssEapSaslMechs[] = { { sizeof("EAP") - 1, "EAP", }, /* not used */ { sizeof("EAP-AES128") - 1, "EAP-AES128" }, diff --git a/util_name.c b/util_name.c index dad8fb9..85f8b3f 100644 --- a/util_name.c +++ b/util_name.c @@ -276,6 +276,7 @@ gssEapImportNameInternal(OM_uint32 *minor, gss_buffer_desc buf; enum gss_eap_token_type tokType; gss_name_t name = GSS_C_NO_NAME; + gss_OID mechanismUsed = GSS_C_NO_OID; GSSEAP_KRB_INIT(&krbContext); @@ -314,19 +315,13 @@ gssEapImportNameInternal(OM_uint32 *minor, CHECK_REMAIN(mech.length); - if (!gssEapIsMechanismOid(&mech)) { - major = GSS_S_BAD_NAME; - *minor = GSSEAP_WRONG_MECH; + major = gssEapCanonicalizeOid(minor, + &mech, + OID_FLAG_FAMILY_MECH_VALID | + OID_FLAG_MAP_FAMILY_MECH_TO_NULL, + &mechanismUsed); + if (GSS_ERROR(major)) goto cleanup; - } - - if (oidEqual(&mech, GSS_EAP_MECHANISM)) { - name->mechanismUsed = GSS_C_NO_OID; - } else if (!gssEapInternalizeOid(&mech, &name->mechanismUsed)) { - major = duplicateOid(minor, &mech, &name->mechanismUsed); - if (GSS_ERROR(major)) - goto cleanup; - } UPDATE_REMAIN(2 + mech.length); } @@ -346,6 +341,9 @@ gssEapImportNameInternal(OM_uint32 *minor, if (GSS_ERROR(major)) goto cleanup; + name->mechanismUsed = mechanismUsed; + mechanismUsed = GSS_C_NO_OID; + if (flags & EXPORT_NAME_FLAG_COMPOSITE) { gss_buffer_desc buf; @@ -361,10 +359,12 @@ gssEapImportNameInternal(OM_uint32 *minor, *minor = 0; cleanup: - if (GSS_ERROR(major)) + if (GSS_ERROR(major)) { + gssEapReleaseOid(&tmpMinor, &mechanismUsed); gssEapReleaseName(&tmpMinor, &name); - else + } else { *pName = name; + } return major; } @@ -433,9 +433,7 @@ gssEapImportName(OM_uint32 *minor, assert(gssEapIsConcreteMechanismOid(mechType)); assert(name->mechanismUsed == GSS_C_NO_OID); - if (!gssEapInternalizeOid(mechType, &name->mechanismUsed)) { - major = duplicateOid(minor, mechType, &name->mechanismUsed); - } + major = gssEapCanonicalizeOid(minor, mechType, 0, &name->mechanismUsed); } if (GSS_ERROR(major)) @@ -553,13 +551,15 @@ cleanup: } OM_uint32 -gssEapDuplicateName(OM_uint32 *minor, - const gss_name_t input_name, - gss_name_t *dest_name) +gssEapCanonicalizeName(OM_uint32 *minor, + const gss_name_t input_name, + const gss_OID mech_type, + gss_name_t *dest_name) { OM_uint32 major, tmpMinor; krb5_context krbContext; gss_name_t name; + gss_OID mech_used; if (input_name == GSS_C_NO_NAME) { *minor = EINVAL; @@ -573,21 +573,17 @@ gssEapDuplicateName(OM_uint32 *minor, return major; } - if (input_name->mechanismUsed == GSS_C_NO_OID) { - name->mechanismUsed = GSS_C_NO_OID; - } else if (gssEapIsConcreteMechanismOid(input_name->mechanismUsed)) { - if (!gssEapInternalizeOid(input_name->mechanismUsed, - &name->mechanismUsed)) { - major = duplicateOid(minor, input_name->mechanismUsed, - &name->mechanismUsed); - if (GSS_ERROR(major)) - goto cleanup; - } - } else { - major = GSS_S_BAD_MECH; - *minor = GSSEAP_WRONG_MECH; + if (mech_type != GSS_C_NO_OID) + mech_used = mech_type; + else + mech_used = input_name->mechanismUsed; + + major = gssEapCanonicalizeOid(minor, + mech_used, + OID_FLAG_NULL_VALID, + &name->mechanismUsed); + if (GSS_ERROR(major)) goto cleanup; - } name->flags = input_name->flags; @@ -615,6 +611,15 @@ cleanup: } OM_uint32 +gssEapDuplicateName(OM_uint32 *minor, + const gss_name_t input_name, + gss_name_t *dest_name) +{ + return gssEapCanonicalizeName(minor, input_name, + GSS_C_NO_OID, dest_name); +} + +OM_uint32 gssEapDisplayName(OM_uint32 *minor, gss_name_t name, gss_buffer_t output_name_buffer,