X-Git-Url: http://www.project-moonshot.org/gitweb/?p=shibboleth%2Fcpp-sp-resolver.git;a=blobdiff_plain;f=src%2Fshibresolver%2Fresolver.cpp;h=0c7ec522df580dd0ffe2c4a81128fc21850f746b;hp=83b6269f852dcaf8585de7f94da045f8cac8e2c0;hb=94dc42e014828225e443697ff44f8b6112d701c9;hpb=42027b967a3db8d5136c2e0b3b13f7dc45b2b1e1 diff --git a/src/shibresolver/resolver.cpp b/src/shibresolver/resolver.cpp index 83b6269..0c7ec52 100644 --- a/src/shibresolver/resolver.cpp +++ b/src/shibresolver/resolver.cpp @@ -22,6 +22,12 @@ #include "internal.h" +#ifdef SHIBRESOLVER_HAVE_GSSAPI_NAMINGEXTS +# ifdef SHIBRESOLVER_HAVE_GSSMIT +# include +# endif +#endif + #include #include #include @@ -116,7 +122,9 @@ void ShibbolethResolver::setRequest(const SPRequest* request) if (request) { const GSSRequest* gss = dynamic_cast(request); if (gss) { - addToken(gss->getGSSContext()); + // TODO: fix API to prevent destruction of contexts + gss_ctx_id_t ctx = gss->getGSSContext(); + addToken(&ctx); } } #endif @@ -143,19 +151,17 @@ void ShibbolethResolver::addToken(const XMLObject* token) } #ifdef SHIBRESOLVER_HAVE_GSSAPI -void ShibbolethResolver::addToken(gss_ctx_id_t ctx) +void ShibbolethResolver::addToken(gss_ctx_id_t* ctx) { if (m_gsswrapper) { delete m_gsswrapper; m_gsswrapper = NULL; } - if (ctx != GSS_C_NO_CONTEXT) { + if (ctx && *ctx != GSS_C_NO_CONTEXT) { OM_uint32 minor; - gss_buffer_desc contextbuf; - contextbuf.length = 0; - contextbuf.value = NULL; - OM_uint32 major = gss_export_sec_context(&minor, &ctx, &contextbuf); + gss_buffer_desc contextbuf = GSS_C_EMPTY_BUFFER; + OM_uint32 major = gss_export_sec_context(&minor, ctx, &contextbuf); if (major == GSS_S_COMPLETE) { xsecsize_t len=0; XMLByte* out=Base64::encode(reinterpret_cast(contextbuf.value), contextbuf.length, &len); @@ -168,19 +174,69 @@ void ShibbolethResolver::addToken(gss_ctx_id_t ctx) #else XMLString::release((char**)&out); #endif - static const XMLCh _GSSAPI[] = UNICODE_LITERAL_6(G,S,S,A,P,I); + static const XMLCh _GSSAPI[] = UNICODE_LITERAL_13(G,S,S,A,P,I,C,o,n,t,e,x,t); m_gsswrapper = new AnyElementImpl(shibspconstants::SHIB2ATTRIBUTEMAP_NS, _GSSAPI); m_gsswrapper->setTextContent(temp.get()); } else { Category::getInstance(SHIBRESOLVER_LOGCAT).error("error while base64-encoding GSS context"); } + gss_release_buffer(&minor, &contextbuf); } else { Category::getInstance(SHIBRESOLVER_LOGCAT).error("error exporting GSS context"); } } } + +#ifdef SHIBRESOLVER_HAVE_GSSAPI_NAMINGEXTS +void ShibbolethResolver::addToken(gss_name_t name) +{ + if (m_gsswrapper) { + delete m_gsswrapper; + m_gsswrapper = NULL; + } + + OM_uint32 minor; + gss_buffer_desc namebuf = GSS_C_EMPTY_BUFFER; + OM_uint32 major = gss_export_name_composite(&minor, name, &namebuf); + if (major == GSS_S_COMPLETE) { + addToken(&namebuf); + gss_release_buffer(&minor, &namebuf); + } + else { + Category::getInstance(SHIBRESOLVER_LOGCAT).error("error exporting GSS name"); + } +} +#endif + +void ShibbolethResolver::addToken(const gss_buffer_t contextbuf) +{ + if (m_gsswrapper) { + delete m_gsswrapper; + m_gsswrapper = NULL; + } + + xsecsize_t len=0; + XMLByte* out=Base64::encode(reinterpret_cast(contextbuf->value), contextbuf->length, &len); + if (out) { + string s; + s.append(reinterpret_cast(out), len); + auto_ptr_XMLCh temp(s.c_str()); +#ifdef SHIBSP_XERCESC_HAS_XMLBYTE_RELEASE + XMLString::release(&out); +#else + XMLString::release((char**)&out); +#endif + static const XMLCh _GSSAPI[] = UNICODE_LITERAL_10(G,S,S,A,P,I,N,a,m,e); + m_gsswrapper = new AnyElementImpl(shibspconstants::SHIB2ATTRIBUTEMAP_NS, _GSSAPI); + m_gsswrapper->setTextContent(temp.get()); + } + else { + Category::getInstance(SHIBRESOLVER_LOGCAT).error("error while base64-encoding GSS name"); + } +} + #endif void ShibbolethResolver::addAttribute(Attribute* attr) @@ -216,7 +272,7 @@ void ShibbolethResolver::resolve() if (!app) throw ConfigurationException("Unable to locate application for resolution."); -#ifdef HAVE_GSSAPI +#ifdef SHIBRESOLVER_HAVE_GSSAPI if (m_gsswrapper) m_tokens.push_back(m_gsswrapper); #endif @@ -341,21 +397,45 @@ void RemotedResolver::resolve( { #ifndef SHIBSP_LITE Category& log = Category::getInstance(SHIBRESOLVER_LOGCAT); + string issuerstr(issuer ? issuer : ""); pair entity = make_pair((EntityDescriptor*)NULL, (RoleDescriptor*)NULL); MetadataProvider* m = app.getMetadataProvider(false); Locker locker(m); if (!m) { log.warn("no metadata providers are configured"); } - else if (issuer && *issuer) { - // Lookup metadata for the issuer. - MetadataProviderCriteria mc(app, issuer, &IDPSSODescriptor::ELEMENT_QNAME, samlconstants::SAML20P_NS); - entity = m->getEntityDescriptor(mc); - if (!entity.first) { - log.warn("unable to locate metadata for provider (%s)", issuer); + else { + if (!issuerstr.empty()) { + // Attempt to locate an issuer based on input token. + for (vector::const_iterator t = tokens.begin(); t!=tokens.end(); ++t) { + const saml2::Assertion* assertion = dynamic_cast(*t); + if (assertion && assertion->getIssuer()) { + auto_ptr_char iss(assertion->getIssuer()->getName()); + if (iss.get() && *iss.get()) { + issuerstr = iss.get(); + break; + } + } + } + if (!issuerstr.empty()) { + log.info("setting issuer based on input token (%s)", issuerstr.c_str()); + } } - else if (!entity.second) { - log.warn("unable to locate SAML 2.0 identity provider role for provider (%s)", issuer); + + if (!issuerstr.empty()) { + // Lookup metadata for the issuer. + MetadataProviderCriteria idpmc(app, issuerstr.c_str(), &IDPSSODescriptor::ELEMENT_QNAME, samlconstants::SAML20P_NS); + entity = m->getEntityDescriptor(idpmc); + if (!entity.first) { + log.warn("unable to locate metadata for provider (%s)", issuerstr.c_str()); + } + else if (!entity.second) { + MetadataProviderCriteria aamc(app, issuerstr.c_str(), &AttributeAuthorityDescriptor::ELEMENT_QNAME, samlconstants::SAML20P_NS); + entity = m->getEntityDescriptor(aamc); + if (!entity.second) { + log.warn("unable to locate SAML 2.0 IdP or AA role for provider (%s)", issuerstr.c_str()); + } + } } }