Repository: cloudstack Updated Branches: refs/heads/saml-production-grade b8b21aa99 -> de9407e13
CLOUDSTACK-8538: Add new global config for SAML request sig algorithm Signed-off-by: Rohit Yadav <rohit.ya...@shapeblue.com> Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/de9407e1 Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/de9407e1 Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/de9407e1 Branch: refs/heads/saml-production-grade Commit: de9407e13e6b41ea21532e6082bdadee2078d91a Parents: b8b21aa Author: Rohit Yadav <rohit.ya...@shapeblue.com> Authored: Thu Jun 4 16:07:27 2015 +0200 Committer: Rohit Yadav <rohit.ya...@shapeblue.com> Committed: Thu Jun 4 16:07:27 2015 +0200 ---------------------------------------------------------------------- .../command/SAML2LoginAPIAuthenticatorCmd.java | 2 +- .../cloudstack/saml/SAML2AuthManager.java | 3 +++ .../cloudstack/saml/SAML2AuthManagerImpl.java | 2 +- .../org/apache/cloudstack/saml/SAMLUtils.java | 25 ++++++++++++++++---- 4 files changed, 25 insertions(+), 7 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/cloudstack/blob/de9407e1/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LoginAPIAuthenticatorCmd.java ---------------------------------------------------------------------- diff --git a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LoginAPIAuthenticatorCmd.java b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LoginAPIAuthenticatorCmd.java index ee7bfc9..43b4da2 100644 --- a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LoginAPIAuthenticatorCmd.java +++ b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/api/command/SAML2LoginAPIAuthenticatorCmd.java @@ -154,7 +154,7 @@ public class SAML2LoginAPIAuthenticatorCmd extends BaseCmd implements APIAuthent "IdP ID (" + idpId + ") is not found in our list of supported IdPs, cannot proceed.", params, responseType)); } - String redirectUrl = SAMLUtils.buildAuthnRequestUrl(spMetadata, idpMetadata); + String redirectUrl = SAMLUtils.buildAuthnRequestUrl(spMetadata, idpMetadata, SAML2AuthManager.SAMLSignatureAlgorithm.value()); resp.sendRedirect(redirectUrl); return ""; } if (params.containsKey("SAMLart")) { http://git-wip-us.apache.org/repos/asf/cloudstack/blob/de9407e1/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManager.java ---------------------------------------------------------------------- diff --git a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManager.java b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManager.java index 6c856d5..3b0998b 100644 --- a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManager.java +++ b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManager.java @@ -63,6 +63,9 @@ public interface SAML2AuthManager extends PluggableAPIAuthenticator { public static final ConfigKey<String> SAMLDefaultIdentityProviderId = new ConfigKey<String>("Advanced", String.class, "saml2.default.idpid", "https://openidp.feide.no", "The default IdP entity ID to use only in case of multiple IdPs", true); + public static final ConfigKey<String> SAMLSignatureAlgorithm = new ConfigKey<String>("Advanced", String.class, "saml2.sigalg", "SHA1", + "The algorithm to use to when signing a SAML request. Default is SHA1, allowed algorithms: SHA1, SHA256, SHA384, SHA512", true); + public static final ConfigKey<Integer> SAMLTimeout = new ConfigKey<Integer>("Advanced", Integer.class, "saml2.timeout", "30000", "SAML2 IDP Metadata Downloading and parsing etc. activity timeout in milliseconds", true); http://git-wip-us.apache.org/repos/asf/cloudstack/blob/de9407e1/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManagerImpl.java ---------------------------------------------------------------------- diff --git a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManagerImpl.java b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManagerImpl.java index 6797bed..fdbf089 100644 --- a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManagerImpl.java +++ b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAML2AuthManagerImpl.java @@ -384,6 +384,6 @@ public class SAML2AuthManagerImpl extends AdapterBase implements SAML2AuthManage SAMLCloudStackRedirectionUrl, SAMLUserAttributeName, SAMLDefaultDomain, SAMLIdentityProviderMetadataURL, SAMLDefaultIdentityProviderId, - SAMLTimeout}; + SAMLSignatureAlgorithm, SAMLTimeout}; } } http://git-wip-us.apache.org/repos/asf/cloudstack/blob/de9407e1/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAMLUtils.java ---------------------------------------------------------------------- diff --git a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAMLUtils.java b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAMLUtils.java index e2a9dbc..fde57fc 100644 --- a/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAMLUtils.java +++ b/plugins/user-authenticators/saml2/src/org/apache/cloudstack/saml/SAMLUtils.java @@ -133,7 +133,7 @@ public class SAMLUtils { return null; } - public static String buildAuthnRequestUrl(SAMLProviderMetadata spMetadata, SAMLProviderMetadata idpMetadata) { + public static String buildAuthnRequestUrl(final SAMLProviderMetadata spMetadata, final SAMLProviderMetadata idpMetadata, final String signatureAlgorithm) { String redirectUrl = ""; try { DefaultBootstrap.bootstrap(); @@ -142,7 +142,7 @@ public class SAMLUtils { if (spMetadata.getKeyPair() != null) { privateKey = spMetadata.getKeyPair().getPrivate(); } - redirectUrl = idpMetadata.getSsoUrl() + "?" + SAMLUtils.generateSAMLRequestSignature("SAMLRequest=" + SAMLUtils.encodeSAMLRequest(authnRequest), privateKey); + redirectUrl = idpMetadata.getSsoUrl() + "?" + SAMLUtils.generateSAMLRequestSignature("SAMLRequest=" + SAMLUtils.encodeSAMLRequest(authnRequest), privateKey, signatureAlgorithm); } catch (ConfigurationException | FactoryConfigurationError | MarshallingException | IOException | NoSuchAlgorithmException | InvalidKeyException | java.security.SignatureException e) { s_logger.error("SAML AuthnRequest message building error: " + e.getMessage()); } @@ -233,13 +233,28 @@ public class SAMLUtils { return (Response) unmarshaller.unmarshall(element); } - public static String generateSAMLRequestSignature(String urlEncodedString, PrivateKey signingKey) + public static String generateSAMLRequestSignature(final String urlEncodedString, final PrivateKey signingKey, final String sigAlgorithmName) throws NoSuchAlgorithmException, SignatureException, InvalidKeyException, UnsupportedEncodingException { if (signingKey == null) { return urlEncodedString; } - String url = urlEncodedString + "&SigAlg=" + URLEncoder.encode(SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA1, HttpUtils.UTF_8); - Signature signature = Signature.getInstance("SHA1withRSA"); + + String opensamlAlgoIdSignature = SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA1; + String javaSignatureAlgorithmName = "SHA1withRSA"; + + if (sigAlgorithmName.equalsIgnoreCase("SHA256")) { + opensamlAlgoIdSignature = SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA256; + javaSignatureAlgorithmName = "SHA256withRSA"; + } else if (sigAlgorithmName.equalsIgnoreCase("SHA384")) { + opensamlAlgoIdSignature = SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA384; + javaSignatureAlgorithmName = "SHA384withRSA"; + } else if (sigAlgorithmName.equalsIgnoreCase("SHA512")) { + opensamlAlgoIdSignature = SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA512; + javaSignatureAlgorithmName = "SHA512withRSA"; + } + + String url = urlEncodedString + "&SigAlg=" + URLEncoder.encode(opensamlAlgoIdSignature, HttpUtils.UTF_8); + Signature signature = Signature.getInstance(javaSignatureAlgorithmName); signature.initSign(signingKey); signature.update(url.getBytes()); String signatureString = Base64.encodeBytes(signature.sign(), Base64.DONT_BREAK_LINES);