/// <summary>Creates SSL configuration.</summary> /// <param name="mode">SSLFactory.Mode mode to configure</param> /// <param name="keystore">String keystore file</param> /// <param name="password"> /// String store password, or null to avoid setting store /// password /// </param> /// <param name="keyPassword"> /// String key password, or null to avoid setting key /// password /// </param> /// <param name="trustKS">String truststore file</param> /// <returns>Configuration for SSL</returns> private static Configuration CreateSSLConfig(SSLFactory.Mode mode, string keystore , string password, string keyPassword, string trustKS) { string trustPassword = "******"; Configuration sslConf = new Configuration(false); if (keystore != null) { sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslKeystoreLocationTplKey), keystore); } if (password != null) { sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslKeystorePasswordTplKey), password); } if (keyPassword != null) { sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslKeystoreKeypasswordTplKey), keyPassword); } if (trustKS != null) { sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslTruststoreLocationTplKey), trustKS); } if (trustPassword != null) { sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslTruststorePasswordTplKey), trustPassword); } sslConf.Set(FileBasedKeyStoresFactory.ResolvePropertyName(mode, FileBasedKeyStoresFactory .SslTruststoreReloadIntervalTplKey), "1000"); return(sslConf); }
private Configuration ReadSSLConfiguration(SSLFactory.Mode mode) { Configuration sslConf = new Configuration(false); sslConf.SetBoolean(SslRequireClientCertKey, requireClientCert); string sslConfResource; if (mode == SSLFactory.Mode.Client) { sslConfResource = conf.Get(SslClientConfKey, "ssl-client.xml"); } else { sslConfResource = conf.Get(SslServerConfKey, "ssl-server.xml"); } sslConf.AddResource(sslConfResource); return(sslConf); }
/// <summary>Creates an SSLFactory.</summary> /// <param name="mode">SSLFactory mode, client or server.</param> /// <param name="conf"> /// Hadoop configuration from where the SSLFactory configuration /// will be read. /// </param> public SSLFactory(SSLFactory.Mode mode, Configuration conf) { this.conf = conf; if (mode == null) { throw new ArgumentException("mode cannot be NULL"); } this.mode = mode; requireClientCert = conf.GetBoolean(SslRequireClientCertKey, DefaultSslRequireClientCert ); Configuration sslConf = ReadSSLConfiguration(mode); Type klass = conf.GetClass <KeyStoresFactory>(KeystoresFactoryClassKey, typeof(FileBasedKeyStoresFactory )); keystoresFactory = ReflectionUtils.NewInstance(klass, sslConf); enabledProtocols = conf.GetStrings(SslEnabledProtocols, DefaultSslEnabledProtocols ); }
/// <summary> /// Checks that SSLFactory initialization is successful with the given /// arguments. /// </summary> /// <remarks> /// Checks that SSLFactory initialization is successful with the given /// arguments. This is a helper method for writing test cases that cover /// different combinations of settings for the store password and key password. /// It takes care of bootstrapping a keystore, a truststore, and SSL client or /// server configuration. Then, it initializes an SSLFactory. If no exception /// is thrown, then initialization was successful. /// </remarks> /// <param name="mode">SSLFactory.Mode mode to test</param> /// <param name="password">String store password to set on keystore</param> /// <param name="keyPassword">String key password to set on keystore</param> /// <param name="confPassword"> /// String store password to set in SSL config file, or null /// to avoid setting in SSL config file /// </param> /// <param name="confKeyPassword"> /// String key password to set in SSL config file, or /// null to avoid setting in SSL config file /// </param> /// <param name="useCredProvider"> /// boolean to indicate whether passwords should be set /// into the config or not. When set to true nulls are set and aliases are /// expected to be resolved through credential provider API through the /// Configuration.getPassword method /// </param> /// <exception cref="System.Exception">for any error</exception> private void CheckSSLFactoryInitWithPasswords(SSLFactory.Mode mode, string password , string keyPassword, string confPassword, string confKeyPassword, bool useCredProvider ) { string keystore = new FilePath(KeystoresDir, "keystore.jks").GetAbsolutePath(); string truststore = new FilePath(KeystoresDir, "truststore.jks").GetAbsolutePath( ); string trustPassword = "******"; // Create keys, certs, keystore, and truststore. KeyPair keyPair = KeyStoreTestUtil.GenerateKeyPair("RSA"); X509Certificate cert = KeyStoreTestUtil.GenerateCertificate("CN=Test", keyPair, 30 , "SHA1withRSA"); KeyStoreTestUtil.CreateKeyStore(keystore, password, keyPassword, "Test", keyPair. GetPrivate(), cert); IDictionary <string, X509Certificate> certs = Collections.SingletonMap("server", cert ); KeyStoreTestUtil.CreateTrustStore(truststore, trustPassword, certs); // Create SSL configuration file, for either server or client. string sslConfFileName; Configuration sslConf; // if the passwords are provisioned in a cred provider then don't set them // in the configuration properly - expect them to be resolved through the // provider if (useCredProvider) { confPassword = null; confKeyPassword = null; } if (mode == SSLFactory.Mode.Server) { sslConfFileName = "ssl-server.xml"; sslConf = KeyStoreTestUtil.CreateServerSSLConfig(keystore, confPassword, confKeyPassword , truststore); if (useCredProvider) { FilePath testDir = new FilePath(Runtime.GetProperty("test.build.data", "target/test-dir" )); Path jksPath = new Path(testDir.ToString(), "test.jks"); string ourUrl = JavaKeyStoreProvider.SchemeName + "://file" + jksPath.ToUri(); sslConf.Set(CredentialProviderFactory.CredentialProviderPath, ourUrl); } } else { sslConfFileName = "ssl-client.xml"; sslConf = KeyStoreTestUtil.CreateClientSSLConfig(keystore, confPassword, confKeyPassword , truststore); } KeyStoreTestUtil.SaveConfig(new FilePath(sslConfsDir, sslConfFileName), sslConf); // Create the master configuration for use by the SSLFactory, which by // default refers to the ssl-server.xml or ssl-client.xml created above. Configuration conf = new Configuration(); conf.SetBoolean(SSLFactory.SslRequireClientCertKey, true); // Try initializing an SSLFactory. SSLFactory sslFactory = new SSLFactory(mode, conf); try { sslFactory.Init(); } finally { sslFactory.Destroy(); } }
/// <summary> /// Checks that SSLFactory initialization is successful with the given /// arguments. /// </summary> /// <remarks> /// Checks that SSLFactory initialization is successful with the given /// arguments. This is a helper method for writing test cases that cover /// different combinations of settings for the store password and key password. /// It takes care of bootstrapping a keystore, a truststore, and SSL client or /// server configuration. Then, it initializes an SSLFactory. If no exception /// is thrown, then initialization was successful. /// </remarks> /// <param name="mode">SSLFactory.Mode mode to test</param> /// <param name="password">String store password to set on keystore</param> /// <param name="keyPassword">String key password to set on keystore</param> /// <param name="confPassword"> /// String store password to set in SSL config file, or null /// to avoid setting in SSL config file /// </param> /// <param name="confKeyPassword"> /// String key password to set in SSL config file, or /// null to avoid setting in SSL config file /// </param> /// <exception cref="System.Exception">for any error</exception> private void CheckSSLFactoryInitWithPasswords(SSLFactory.Mode mode, string password , string keyPassword, string confPassword, string confKeyPassword) { CheckSSLFactoryInitWithPasswords(mode, password, keyPassword, confPassword, confKeyPassword , false); }
/// <summary>Initializes the keystores of the factory.</summary> /// <param name="mode">if the keystores are to be used in client or server mode.</param> /// <exception cref="System.IO.IOException"> /// thrown if the keystores could not be initialized due /// to an IO error. /// </exception> /// <exception cref="GeneralSecurityException"> /// thrown if the keystores could not be /// initialized due to a security error. /// </exception> public virtual void Init(SSLFactory.Mode mode) { bool requireClientCert = conf.GetBoolean(SSLFactory.SslRequireClientCertKey, SSLFactory .DefaultSslRequireClientCert); // certificate store string keystoreType = conf.Get(ResolvePropertyName(mode, SslKeystoreTypeTplKey), DefaultKeystoreType); KeyStore keystore = KeyStore.GetInstance(keystoreType); string keystoreKeyPassword = null; if (requireClientCert || mode == SSLFactory.Mode.Server) { string locationProperty = ResolvePropertyName(mode, SslKeystoreLocationTplKey); string keystoreLocation = conf.Get(locationProperty, string.Empty); if (keystoreLocation.IsEmpty()) { throw new GeneralSecurityException("The property '" + locationProperty + "' has not been set in the ssl configuration file." ); } string passwordProperty = ResolvePropertyName(mode, SslKeystorePasswordTplKey); string keystorePassword = GetPassword(conf, passwordProperty, string.Empty); if (keystorePassword.IsEmpty()) { throw new GeneralSecurityException("The property '" + passwordProperty + "' has not been set in the ssl configuration file." ); } string keyPasswordProperty = ResolvePropertyName(mode, SslKeystoreKeypasswordTplKey ); // Key password defaults to the same value as store password for // compatibility with legacy configurations that did not use a separate // configuration property for key password. keystoreKeyPassword = GetPassword(conf, keyPasswordProperty, keystorePassword); Log.Debug(mode.ToString() + " KeyStore: " + keystoreLocation); InputStream @is = new FileInputStream(keystoreLocation); try { keystore.Load(@is, keystorePassword.ToCharArray()); } finally { @is.Close(); } Log.Debug(mode.ToString() + " Loaded KeyStore: " + keystoreLocation); } else { keystore.Load(null, null); } KeyManagerFactory keyMgrFactory = KeyManagerFactory.GetInstance(SSLFactory.Sslcertificate ); keyMgrFactory.Init(keystore, (keystoreKeyPassword != null) ? keystoreKeyPassword. ToCharArray() : null); keyManagers = keyMgrFactory.GetKeyManagers(); //trust store string truststoreType = conf.Get(ResolvePropertyName(mode, SslTruststoreTypeTplKey ), DefaultKeystoreType); string locationProperty_1 = ResolvePropertyName(mode, SslTruststoreLocationTplKey ); string truststoreLocation = conf.Get(locationProperty_1, string.Empty); if (!truststoreLocation.IsEmpty()) { string passwordProperty = ResolvePropertyName(mode, SslTruststorePasswordTplKey); string truststorePassword = GetPassword(conf, passwordProperty, string.Empty); if (truststorePassword.IsEmpty()) { throw new GeneralSecurityException("The property '" + passwordProperty + "' has not been set in the ssl configuration file." ); } long truststoreReloadInterval = conf.GetLong(ResolvePropertyName(mode, SslTruststoreReloadIntervalTplKey ), DefaultSslTruststoreReloadInterval); Log.Debug(mode.ToString() + " TrustStore: " + truststoreLocation); trustManager = new ReloadingX509TrustManager(truststoreType, truststoreLocation, truststorePassword, truststoreReloadInterval); trustManager.Init(); Log.Debug(mode.ToString() + " Loaded TrustStore: " + truststoreLocation); trustManagers = new TrustManager[] { trustManager }; } else { Log.Debug("The property '" + locationProperty_1 + "' has not been set, " + "no TrustStore will be loaded" ); trustManagers = null; } }
public static string ResolvePropertyName(SSLFactory.Mode mode, string template) { return(MessageFormat.Format(template, StringUtils.ToLowerCase(mode.ToString()))); }