X-Git-Url: http://www.project-moonshot.org/gitweb/?a=blobdiff_plain;f=shibsp%2Fhandler%2Fimpl%2FSAML2LogoutInitiator.cpp;h=24b8bfa3a1b373e02214889fafa3d8173fb18b33;hb=2b8daf0f4fd3e5035ab3babdc76fe676e8823f93;hp=249eb8f7032820d5d6d8a8dc66da9524df90d81c;hpb=a5b1914f888d2ac8992cc4985d65e9d727aa8df4;p=shibboleth%2Fsp.git diff --git a/shibsp/handler/impl/SAML2LogoutInitiator.cpp b/shibsp/handler/impl/SAML2LogoutInitiator.cpp index 249eb8f..24b8bfa 100644 --- a/shibsp/handler/impl/SAML2LogoutInitiator.cpp +++ b/shibsp/handler/impl/SAML2LogoutInitiator.cpp @@ -1,5 +1,5 @@ /* - * Copyright 2001-2007 Internet2 + * Copyright 2001-2009 Internet2 * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -25,17 +25,24 @@ #include "Application.h" #include "ServiceProvider.h" #include "SessionCache.h" +#include "SPRequest.h" #include "handler/AbstractHandler.h" #include "handler/LogoutHandler.h" #ifndef SHIBSP_LITE # include "binding/SOAPClient.h" # include "metadata/MetadataProviderCriteria.h" +# include "security/SecurityPolicy.h" +# include # include # include # include # include +# include # include +# include +# include +# include using namespace opensaml::saml2; using namespace opensaml::saml2p; using namespace opensaml::saml2md; @@ -282,7 +289,7 @@ pair SAML2LogoutInitiator::doRequest( if (!notifyBackChannel(application, httpRequest.getRequestURL(), sessions, false)) { session->unlock(); application.getServiceProvider().getSessionCache()->remove(application, httpRequest, &httpResponse); - return sendLogoutPage(application, httpRequest, httpResponse, true, "Partial logout failure."); + return sendLogoutPage(application, httpRequest, httpResponse, "partial"); } #ifndef SHIBSP_LITE @@ -317,7 +324,7 @@ pair SAML2LogoutInitiator::doRequest( } } if (!ep || !encoder) { - m_log.warn("no compatible front channel SingleLogoutService, trying back channel..."); + m_log.debug("no compatible front channel SingleLogoutService, trying back channel..."); shibsp::SecurityPolicy policy(application); shibsp::SOAPClient soaper(policy); MetadataCredentialCriteria mcc(*role); @@ -346,27 +353,32 @@ pair SAML2LogoutInitiator::doRequest( } } + // No answer at all? if (!logoutResponse) { - ret = sendLogoutPage( - application, httpRequest, httpResponse, false, - endpoints.empty() ? - "Identity provider does not support SAML 2 Single Logout protocol." : - "Identity provider did not respond to logout request." - ); + if (endpoints.empty()) + m_log.info("IdP doesn't support single logout protocol over a compatible binding"); + else + m_log.warn("IdP didn't respond to logout request"); + ret = sendLogoutPage(application, httpRequest, httpResponse, "partial"); } - else if (!logoutResponse->getStatus() || !logoutResponse->getStatus()->getStatusCode() || - !XMLString::equals(logoutResponse->getStatus()->getStatusCode()->getValue(), saml2p::StatusCode::SUCCESS)) { - delete logoutResponse; - ret = sendLogoutPage(application, httpRequest, httpResponse, false, "Identity provider returned a SAML error in response to logout request."); + + // Check the status, looking for non-success or a partial logout code. + const StatusCode* sc = logoutResponse->getStatus() ? logoutResponse->getStatus()->getStatusCode() : NULL; + bool partial = (!sc || !XMLString::equals(sc->getValue(), StatusCode::SUCCESS)); + if (!partial) { + // Success, but still need to check for partial. + partial = XMLString::equals(sc->getStatusCode()->getValue(), StatusCode::PARTIAL_LOGOUT); } + delete logoutResponse; + if (partial) + ret = sendLogoutPage(application, httpRequest, httpResponse, "partial"); else { - delete logoutResponse; const char* returnloc = httpRequest.getParameter("return"); if (returnloc) { ret.second = httpResponse.sendRedirect(returnloc); ret.first = true; } - ret = sendLogoutPage(application, httpRequest, httpResponse, false, "Logout completed successfully."); + ret = sendLogoutPage(application, httpRequest, httpResponse, "global"); } if (session) {