use of com.emc.storageos.security.keystore.impl.KeyCertificateEntry in project coprhd-controller by CoprHD.
the class VirtualDataCenterService method setKeyCertificatePair.
/**
* Rotate the VIPR key and certificate chain.
*
* @param rotateKeyAndCertParam
* @return the new certificate chain being used by ViPR
* @brief Rotate the VIPR key and certificate chain to a new system self-signed or a specified input.
*/
@Path("/keystore")
@PUT
@Produces({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON })
@Consumes({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON })
@CheckPermission(roles = { Role.SECURITY_ADMIN, Role.RESTRICTED_SECURITY_ADMIN }, blockProxies = true)
public CertificateChain setKeyCertificatePair(RotateKeyAndCertParam rotateKeyAndCertParam) {
if (!coordinator.isClusterUpgradable()) {
throw SecurityException.retryables.updatingKeystoreWhileClusterIsUnstable();
}
if (!drUtil.isActiveSite()) {
SiteState state = drUtil.getLocalSite().getState();
if (state == SiteState.STANDBY_PAUSING || state == SiteState.STANDBY_PAUSED || state == SiteState.STANDBY_RESUMING) {
throw SecurityException.retryables.failToUpdateKeyStoreDueToStandbyPause();
}
}
Boolean selfsigned = rotateKeyAndCertParam.getSystemSelfSigned();
byte[] key = null;
Certificate[] chain = null;
RSAPrivateKey rsaPrivateKey = null;
try {
if (selfsigned != null && selfsigned) {
KeyCertificateEntry pair = getGenerator().generateKeyCertificatePair();
// key is needed to clear
key = pair.getKey();
chain = pair.getCertificateChain();
} else {
KeyAndCertificateChain newKey = rotateKeyAndCertParam.getKeyCertChain();
if (newKey == null || StringUtils.isBlank(newKey.getCertificateChain()) || StringUtils.isBlank(newKey.getPrivateKey())) {
throw APIException.badRequests.requiredParameterMissingOrEmpty("key_and_certificate");
}
try {
chain = KeyCertificatePairGenerator.getCertificateChainFromString(newKey.getCertificateChain());
if (ArrayUtils.isEmpty(chain)) {
throw APIException.badRequests.failedToLoadCertificateFromString(newKey.getCertificateChain());
}
X509Certificate cert = (X509Certificate) chain[0];
cert.checkValidity();
key = SecurityUtil.loadPrivateKeyFromPEMString(newKey.getPrivateKey());
rsaPrivateKey = (RSAPrivateKey) KeyCertificatePairGenerator.loadPrivateKeyFromBytes(key);
int keyLength = rsaPrivateKey.getModulus().bitLength();
if (keyLength < KeyCertificateAlgorithmValuesHolder.FIPS_MINIMAL_KEY_SIZE) {
throw APIException.badRequests.invalidParameterBelowMinimum("private_key", keyLength, KeyCertificateAlgorithmValuesHolder.FIPS_MINIMAL_KEY_SIZE, "bits");
}
KeyCertificatePairGenerator.validateKeyAndCertPairing(rsaPrivateKey, chain);
Certificate prevCert = null;
try {
prevCert = getKeyStore().getCertificate(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS);
if (cert.equals(prevCert)) {
throw APIException.badRequests.newCertificateMustBeSpecified();
}
} catch (KeyStoreException e) {
_log.error("failed to get previous certificate", e);
}
selfsigned = Boolean.FALSE;
} catch (CertificateExpiredException | CertificateNotYetValidException e) {
throw APIException.badRequests.invalidField("key_and_certificate", chain[0].toString());
} catch (CertificateException e) {
throw APIException.badRequests.failedToLoadCertificateFromString(newKey.getCertificateChain(), e);
}
}
Boolean selfSignedPrevious = KeyStoreUtil.isSelfGeneratedCertificate(coordConfigStoringHelper);
// This has to be done before the set keys entry call
KeyStoreUtil.setSelfGeneratedCertificate(coordConfigStoringHelper, selfsigned);
try {
getKeyStore().setKeyEntry(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, key, chain);
} catch (KeyStoreException e) {
_log.error("failed to rotate key and certificate chain.");
KeyStoreUtil.setSelfGeneratedCertificate(coordConfigStoringHelper, selfSignedPrevious);
throw SecurityException.fatals.failedToUpdateKeyCertificateEntry(e);
}
if (!certificateVersionHelper.updateCertificateVersion()) {
_log.error("failed to update version for new key and certificate chain.");
throw SecurityException.fatals.failedToUpdateKeyCertificateEntry();
}
return getCertificateChain();
} finally {
if (key != null) {
// SensitiveData.clear(key);
SecurityUtil.clearSensitiveData(key);
}
if (rsaPrivateKey != null) {
// SensitiveData.clear(rsaPrivateKey);
SecurityUtil.clearSensitiveData(rsaPrivateKey);
}
}
}
use of com.emc.storageos.security.keystore.impl.KeyCertificateEntry in project coprhd-controller by CoprHD.
the class VirtualDataCenterService method prepareKeyCert.
private List<Object> prepareKeyCert(KeyAndCertificateChain newKey) {
Boolean selfsigned = null;
byte[] key = null;
Certificate[] chain = null;
if (newKey != null) {
try {
chain = KeyCertificatePairGenerator.getCertificateChainFromString(newKey.getCertificateChain());
if (ArrayUtils.isEmpty(chain)) {
throw APIException.badRequests.failedToLoadCertificateFromString(newKey.getCertificateChain());
}
key = SecurityUtil.loadPrivateKeyFromPEMString(newKey.getPrivateKey());
selfsigned = Boolean.FALSE;
} catch (CertificateException e) {
throw APIException.badRequests.failedToLoadCertificateFromString(newKey.getCertificateChain(), e);
} catch (Exception e) {
throw APIException.badRequests.failedToLoadKeyFromString(e);
}
} else {
KeyCertificateEntry pair = getGenerator().generateKeyCertificatePair();
selfsigned = Boolean.TRUE;
key = pair.getKey();
chain = pair.getCertificateChain();
}
List<Object> list = new ArrayList<Object>();
list.add(selfsigned);
list.add(key);
list.add(chain);
return list;
}
use of com.emc.storageos.security.keystore.impl.KeyCertificateEntry in project coprhd-controller by CoprHD.
the class KeyCertificatePairGeneratorTest method testVerifyKeyCertificateEntry.
@Test
public void testVerifyKeyCertificateEntry() {
KeyCertificatePairGenerator gen = new KeyCertificatePairGenerator();
gen.setKeyCertificateAlgorithmValuesHolder(defaultValues);
// test a generated entry
KeyCertificateEntry entry1 = gen.generateKeyCertificatePair();
try {
new KeyCertificatePairGenerator().verifyKeyCertificateEntry(entry1);
} catch (SecurityException e) {
System.err.println(e.getMessage());
System.err.println(e);
Assert.fail();
} catch (BadRequestException e) {
System.err.println(e.getMessage());
System.err.println(e);
Assert.fail();
}
// test values from 2 different generated entries
KeyCertificateEntry entry2 = gen.generateKeyCertificatePair();
KeyCertificateEntry hybridEntry = new KeyCertificateEntry(entry1.getKey(), entry2.getCertificateChain());
boolean exceptionThrown = false;
try {
new KeyCertificatePairGenerator().verifyKeyCertificateEntry(hybridEntry);
} catch (SecurityException e) {
Assert.fail();
} catch (BadRequestException e) {
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
}
use of com.emc.storageos.security.keystore.impl.KeyCertificateEntry in project coprhd-controller by CoprHD.
the class KeystoreTest method testKeystoreEngine.
@Test
public void testKeystoreEngine() throws KeyStoreException, NoSuchAlgorithmException, CertificateException, IOException, InterruptedException, UnrecoverableEntryException {
DistributedKeyStore zookeeperKeystore = new DistributedKeyStoreImpl();
zookeeperKeystore.init(loadStoreParam);
// this is in case this test was run previously
zookeeperKeystore.setTrustedCertificates(null);
zookeeperKeystore.setKeyCertificatePair(null);
// test keystore loading
KeyStore ks = KeyStore.getInstance(SecurityProvider.KEYSTORE_TYPE, new SecurityProvider());
boolean exceptionThrown = false;
try {
ks.load(null, null);
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("Could not initialize the keystore. The ViPR keystore can only be initialized with a LoadKeyStoreParam.", e.getMessage());
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
exceptionThrown = false;
try {
ks.load(invalidLoadStoreParam);
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("Could not initialize the keystore. The ViPR keystore can only be initialized with a LoadKeyStoreParam.", e.getMessage());
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
// now it shouldn't throw
ks.load(loadStoreParam);
// ////////////////////////////////////////////////////////////////////////
// /
// / key tests
// /
// ////////////////////////////////////////////////////////////////////////
// should have by default the ViPR key
List<String> expectedAliases = new ArrayList<String>();
expectedAliases.add(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS);
assertAliasesIn(ks, expectedAliases);
// update the vipr key using ks.setEntry
Date beforeDate = new Date();
KeyCertificateEntry entry = gen.generateKeyCertificatePair();
KeyStore.PrivateKeyEntry privateKeyEntry = new PrivateKeyEntry(KeyCertificatePairGenerator.loadPrivateKeyFromBytes(entry.getKey()), entry.getCertificateChain());
KeyStore.PasswordProtection empryProtectionParam = new KeyStore.PasswordProtection("".toCharArray());
ks.setEntry(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, privateKeyEntry, new KeyStore.PasswordProtection("123".toCharArray()));
Date afterDate = new Date();
assertKeyCertificateEntryEquals(ks, entry);
assertCreationDateInTImeRange(ks, KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, beforeDate, afterDate);
// set the key entry using setKeyEntry (there are 2 versions, one with the Key
// object, and another with byte[] )
beforeDate = new Date();
entry = gen.generateKeyCertificatePair();
ks.setKeyEntry(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, entry.getKey(), entry.getCertificateChain());
afterDate = new Date();
assertKeyCertificateEntryEquals(ks, entry);
assertCreationDateInTImeRange(ks, KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, beforeDate, afterDate);
beforeDate = new Date();
entry = gen.generateKeyCertificatePair();
ks.setKeyEntry(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, KeyCertificatePairGenerator.loadPrivateKeyFromBytes(entry.getKey()), "".toCharArray(), entry.getCertificateChain());
afterDate = new Date();
assertKeyCertificateEntryEquals(ks, entry);
assertCreationDateInTImeRange(ks, KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS, beforeDate, afterDate);
// ////////////////////////////////////////////////////////////////////////
// /
// / certificates tests
// /
// ////////////////////////////////////////////////////////////////////////
String certAlias = "someCert";
// add a new trusted certificate using ks.setEntry
beforeDate = new Date();
entry = gen.generateKeyCertificatePair();
KeyStore.TrustedCertificateEntry trustedCertEntry = new KeyStore.TrustedCertificateEntry(entry.getCertificateChain()[0]);
ks.setEntry(certAlias, trustedCertEntry, null);
afterDate = new Date();
expectedAliases.add(certAlias);
assertAliasesIn(ks, expectedAliases);
assertTrustedCertEquals(ks, entry, certAlias);
assertCreationDateInTImeRange(ks, certAlias, beforeDate, afterDate);
// add a new trusted certificate using ks.setCertificateEntry
beforeDate = new Date();
entry = gen.generateKeyCertificatePair();
certAlias = "someCert1";
ks.setCertificateEntry(certAlias, entry.getCertificateChain()[0]);
afterDate = new Date();
expectedAliases.add(certAlias);
assertAliasesIn(ks, expectedAliases);
assertTrustedCertEquals(ks, entry, certAlias);
assertCreationDateInTImeRange(ks, certAlias, beforeDate, afterDate);
// remove the trusted certificate entry
ks.deleteEntry(certAlias);
expectedAliases.remove(certAlias);
assertAliasesIn(ks, expectedAliases);
// ////////////////////////////////////////////////////////////////////////
// /
// / Negative testing
// /
// ////////////////////////////////////////////////////////////////////////
String invalidEntryName = "invalidEntry";
// cannot delete the ViPR key
exceptionThrown = false;
try {
ks.deleteEntry(KeystoreEngine.ViPR_KEY_AND_CERTIFICATE_ALIAS);
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("The ViPR key and certificate cannot be deleted, it can only be updated.", e.getMessage());
exceptionThrown = true;
} catch (KeyStoreException e) {
Assert.fail();
}
Assert.assertTrue(exceptionThrown);
assertAliasesIn(ks, expectedAliases);
entry = gen.generateKeyCertificatePair();
// try to set a key that is not the vipr key
// using ks.setEntry
privateKeyEntry = new PrivateKeyEntry(KeyCertificatePairGenerator.loadPrivateKeyFromBytes(entry.getKey()), entry.getCertificateChain());
exceptionThrown = false;
try {
ks.setEntry(invalidEntryName, privateKeyEntry, empryProtectionParam);
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("Cannot update any key and certificate entry except for the ViPR key and certificate.", e.getMessage());
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
assertAliasesIn(ks, expectedAliases);
// using ks.setKey which accepts byte[]
try {
ks.setKeyEntry(invalidEntryName, entry.getKey(), entry.getCertificateChain());
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("Cannot update any key and certificate entry except for the ViPR key and certificate.", e.getMessage());
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
assertAliasesIn(ks, expectedAliases);
// using ks.setKey which accepts Key object
try {
ks.setKeyEntry(invalidEntryName, KeyCertificatePairGenerator.loadPrivateKeyFromBytes(entry.getKey()), "".toCharArray(), entry.getCertificateChain());
} catch (SecurityException e) {
Assert.assertEquals(ServiceCode.SECURITY_ERROR, e.getServiceCode());
Assert.assertEquals("Cannot update any key and certificate entry except for the ViPR key and certificate.", e.getMessage());
exceptionThrown = true;
}
Assert.assertTrue(exceptionThrown);
assertAliasesIn(ks, expectedAliases);
// try getting an invalid entry
Assert.assertFalse(ks.containsAlias(invalidEntryName));
Assert.assertFalse(ks.entryInstanceOf(invalidEntryName, KeyStore.TrustedCertificateEntry.class));
Assert.assertFalse(ks.entryInstanceOf(invalidEntryName, KeyStore.PrivateKeyEntry.class));
Assert.assertFalse(ks.entryInstanceOf(invalidEntryName, KeyStore.SecretKeyEntry.class));
Assert.assertFalse(ks.isCertificateEntry(invalidEntryName));
Assert.assertFalse(ks.isKeyEntry(invalidEntryName));
Assert.assertNull(ks.getCertificate(invalidEntryName));
Assert.assertNull(ks.getCertificateAlias(entry.getCertificateChain()[0]));
Assert.assertNull(ks.getCertificateChain(invalidEntryName));
Assert.assertNull(ks.getCreationDate(invalidEntryName));
Assert.assertNull(ks.getEntry(invalidEntryName, empryProtectionParam));
Assert.assertNull(ks.getKey(invalidEntryName, "".toCharArray()));
// try to delete an entry that does not exist
exceptionThrown = false;
try {
ks.deleteEntry(invalidEntryName);
} catch (SecurityException e) {
Assert.fail();
} catch (KeyStoreException e) {
exceptionThrown = true;
Assert.assertEquals("The specified alias " + invalidEntryName + " does not exist", e.getMessage());
}
Assert.assertTrue(exceptionThrown);
}
use of com.emc.storageos.security.keystore.impl.KeyCertificateEntry in project coprhd-controller by CoprHD.
the class KeyCertificatePairGeneratorTest method testGenerate.
@Test
public void testGenerate() throws GeneralSecurityException, IOException {
// test the defaults
KeyCertificatePairGenerator gen = new KeyCertificatePairGenerator();
gen.setKeyCertificateAlgorithmValuesHolder(defaultValues);
KeyCertificateEntry pair = gen.generateKeyCertificatePair();
assertCertInformation((X509Certificate) pair.getCertificateChain()[0], defaultValues);
}
Aggregations