diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/pom.xml b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/pom.xml
new file mode 100644
index 0000000000..72647601ae
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/pom.xml
@@ -0,0 +1,152 @@
+
+
+
+
+
+ org.wso2.carbon.devicemgt
+ certificate-mgt
+ 0.9.2-SNAPSHOT
+ ../pom.xml
+
+
+ 4.0.0
+ org.wso2.carbon.devicemgt
+ org.wso2.carbon.certificate.mgt.core
+ 0.9.2-SNAPSHOT
+ bundle
+ WSO2 Carbon - Certificate Management Core
+ WSO2 Carbon - Certificate Management Core
+ http://wso2.org
+
+
+
+
+ org.apache.felix
+ maven-scr-plugin
+
+
+ org.apache.felix
+ maven-bundle-plugin
+ 1.4.0
+ true
+
+
+ ${project.artifactId}
+ ${project.artifactId}
+ ${carbon.device.mgt.version}
+ Device Management Core Bundle
+ org.wso2.carbon.certificate.mgt.core.internal
+
+ org.osgi.framework,
+ org.osgi.service.component,
+ org.apache.commons.logging,
+ javax.security.auth.x500,
+ javax.xml.parsers,
+ org.apache.commons.codec.binary,
+ org.bouncycastle.asn1,
+ org.bouncycastle.asn1.x500,
+ org.bouncycastle.asn1.x509,
+ org.bouncycastle.cert,
+ org.bouncycastle.cert.jcajce,
+ org.bouncycastle.cms,
+ org.bouncycastle.jce.provider,
+ org.bouncycastle.operator,
+ org.bouncycastle.operator.jcajce,
+ org.bouncycastle.pkcs,
+ org.bouncycastle.util,
+ org.jscep.message,
+ org.jscep.transaction,
+ org.w3c.dom,
+ org.xml.sax
+
+
+ !org.wso2.carbon.certificate.mgt.core.internal.*,
+ org.wso2.carbon.certificate.mgt.core.dto.*,
+ org.wso2.carbon.certificate.mgt.core.exception.*,
+ org.wso2.carbon.certificate.mgt.core.impl.*,
+ org.wso2.carbon.certificate.mgt.core.service.*,
+ org.wso2.carbon.certificate.mgt.core.util.*
+
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+ 2.18
+
+
+ file:src/test/resources/log4j.properties
+
+
+ src/test/resources/testng.xml
+
+
+
+
+
+
+
+
+
+ org.eclipse.osgi
+ org.eclipse.osgi
+
+
+ org.eclipse.osgi
+ org.eclipse.osgi.services
+
+
+ org.testng
+ testng
+
+
+ org.wso2.carbon
+ org.wso2.carbon.logging
+
+
+ org.bouncycastle.wso2
+ bcprov-jdk15on
+
+
+ org.bouncycastle.wso2
+ bcpkix-jdk15on
+
+
+ org.bouncycastle.wso2
+ bcmail-jdk15on
+
+
+ com.google.code.jscep.wso2
+ jscep
+
+
+ commons-codec.wso2
+ commons-codec
+
+
+ commons-io.wso2
+ commons-io
+
+
+
+
+
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/CAStatus.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/CAStatus.java
new file mode 100755
index 0000000000..e3439c17d1
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/CAStatus.java
@@ -0,0 +1,26 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.dto;
+
+public enum CAStatus {
+
+ CA_CERT_FAILED,
+ CA_CERT_RECEIVED,
+ CA_RA_CERT_RECEIVED
+
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/SCEPResponse.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/SCEPResponse.java
new file mode 100755
index 0000000000..e3aa25c805
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/dto/SCEPResponse.java
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.dto;
+
+public class SCEPResponse {
+
+ private byte[] encodedResponse;
+ private CAStatus resultCriteria;
+
+ public byte[] getEncodedResponse() {
+ return encodedResponse;
+ }
+
+ public void setEncodedResponse(byte[] encodedResponse) {
+ this.encodedResponse = encodedResponse;
+ }
+
+ public CAStatus getResultCriteria() {
+ return resultCriteria;
+ }
+
+ public void setResultCriteria(CAStatus resultCriteria) {
+ this.resultCriteria = resultCriteria;
+ }
+
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/exception/KeystoreException.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/exception/KeystoreException.java
new file mode 100644
index 0000000000..ddc61c9699
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/exception/KeystoreException.java
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.exception;
+
+public class KeystoreException extends Exception {
+
+ private static final long serialVersionUID = -8935640983869122660L;
+ private String errorMessage;
+
+ public String getErrorMessage() {
+ return errorMessage;
+ }
+
+ public void setErrorMessage(String errorMessage) {
+ this.errorMessage = errorMessage;
+ }
+
+ public KeystoreException(String msg, Exception nestedEx) {
+ super(msg, nestedEx);
+ setErrorMessage(msg);
+ }
+
+ public KeystoreException(String message, Throwable cause) {
+ super(message, cause);
+ setErrorMessage(message);
+ }
+
+ public KeystoreException(String msg) {
+ super(msg);
+ setErrorMessage(msg);
+ }
+
+ public KeystoreException() {
+ super();
+ }
+
+ public KeystoreException(Throwable cause) {
+ super(cause);
+ }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGenerator.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGenerator.java
new file mode 100755
index 0000000000..de17582905
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGenerator.java
@@ -0,0 +1,452 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.impl;
+
+import org.apache.commons.codec.binary.Base64;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.bouncycastle.asn1.x500.X500Name;
+import org.bouncycastle.asn1.x509.KeyUsage;
+import org.bouncycastle.asn1.x509.X509Extension;
+import org.bouncycastle.cert.CertIOException;
+import org.bouncycastle.cert.X509CertificateHolder;
+import org.bouncycastle.cert.X509v3CertificateBuilder;
+import org.bouncycastle.cert.jcajce.JcaCertStore;
+import org.bouncycastle.cert.jcajce.JcaX509CertificateConverter;
+import org.bouncycastle.cert.jcajce.JcaX509v3CertificateBuilder;
+import org.bouncycastle.cms.CMSAbsentContent;
+import org.bouncycastle.cms.CMSException;
+import org.bouncycastle.cms.CMSSignedData;
+import org.bouncycastle.cms.CMSSignedDataGenerator;
+import org.bouncycastle.jce.provider.BouncyCastleProvider;
+import org.bouncycastle.operator.ContentSigner;
+import org.bouncycastle.operator.OperatorCreationException;
+import org.bouncycastle.operator.jcajce.JcaContentSignerBuilder;
+import org.bouncycastle.pkcs.PKCS10CertificationRequest;
+import org.bouncycastle.util.Store;
+import org.jscep.message.CertRep;
+import org.jscep.message.MessageDecodingException;
+import org.jscep.message.MessageEncodingException;
+import org.jscep.message.PkcsPkiEnvelopeDecoder;
+import org.jscep.message.PkcsPkiEnvelopeEncoder;
+import org.jscep.message.PkiMessage;
+import org.jscep.message.PkiMessageDecoder;
+import org.jscep.message.PkiMessageEncoder;
+import org.jscep.transaction.FailInfo;
+import org.jscep.transaction.Nonce;
+import org.jscep.transaction.TransactionId;
+import org.wso2.carbon.certificate.mgt.core.dto.CAStatus;
+import org.wso2.carbon.certificate.mgt.core.dto.SCEPResponse;
+import org.wso2.carbon.certificate.mgt.core.util.ConfigurationUtil;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+import org.wso2.carbon.certificate.mgt.core.util.CommonUtil;
+
+import javax.security.auth.x500.X500Principal;
+import java.io.ByteArrayInputStream;
+import java.io.DataInputStream;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.math.BigInteger;
+import java.security.InvalidKeyException;
+import java.security.KeyFactory;
+import java.security.KeyPair;
+import java.security.KeyPairGenerator;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.PrivateKey;
+import java.security.SecureRandom;
+import java.security.Security;
+import java.security.SignatureException;
+import java.security.cert.CertificateEncodingException;
+import java.security.cert.CertificateException;
+import java.security.cert.CertificateExpiredException;
+import java.security.cert.CertificateFactory;
+import java.security.cert.CertificateNotYetValidException;
+import java.security.cert.X509Certificate;
+import java.security.spec.InvalidKeySpecException;
+import java.security.spec.PKCS8EncodedKeySpec;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
+import java.util.List;
+
+public class CertificateGenerator {
+
+ private static final Log log = LogFactory.getLog(CertificateGenerator.class);
+
+ public List getRootCertificates(byte[] ca, byte[] ra) throws KeystoreException {
+
+ if (ca == null) {
+ throw new KeystoreException("CA certificate is mandatory");
+ }
+
+ if (ra == null) {
+ throw new KeystoreException("RA certificate is mandatory");
+ }
+
+ List certificateList = new ArrayList();
+ InputStream caInputStream = null;
+ InputStream raInputStream = null;
+
+ try {
+ CertificateFactory certificateFactory = CertificateFactory.getInstance(ConfigurationUtil.X_509);
+ caInputStream = new ByteArrayInputStream(ca);
+ raInputStream = new ByteArrayInputStream(ra);
+
+ X509Certificate caCert = (X509Certificate) certificateFactory.generateCertificate(caInputStream);
+ X509Certificate raCert = (X509Certificate) certificateFactory.generateCertificate(raInputStream);
+
+ certificateList.add(caCert);
+ certificateList.add(raCert);
+ } catch (CertificateException e) {
+ String errorMsg = "Error occurred while fetching root certificates";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } finally {
+ if (caInputStream != null) {
+ try {
+ caInputStream.close();
+ } catch (IOException e) {
+ log.error("Error occurred when closing CA input stream");
+ }
+ }
+
+ if (raInputStream != null) {
+ try {
+ raInputStream.close();
+ } catch (IOException e) {
+ log.error("Error occurred when closing RA input stream");
+ }
+ }
+ }
+
+ return certificateList;
+ }
+
+ public X509Certificate generateX509Certificate() throws KeystoreException {
+
+ CommonUtil commonUtil = new CommonUtil();
+ Date validityBeginDate = commonUtil.getValidityStartDate();
+ Date validityEndDate = commonUtil.getValidityEndDate();
+
+ Security.addProvider(new BouncyCastleProvider());
+
+ try {
+ KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance(
+ ConfigurationUtil.RSA, ConfigurationUtil.PROVIDER);
+ keyPairGenerator.initialize(ConfigurationUtil.RSA_KEY_LENGTH, new SecureRandom());
+ KeyPair pair = keyPairGenerator.generateKeyPair();
+ X500Principal principal = new X500Principal(ConfigurationUtil.DEFAULT_PRINCIPAL);
+ BigInteger serial = BigInteger.valueOf(System.currentTimeMillis());
+
+ X509v3CertificateBuilder certificateBuilder = new JcaX509v3CertificateBuilder(
+ principal, serial, validityBeginDate, validityEndDate,
+ principal, pair.getPublic());
+ ContentSigner contentSigner = new JcaContentSignerBuilder(ConfigurationUtil.SHA256_RSA)
+ .setProvider(ConfigurationUtil.PROVIDER).build(
+ pair.getPrivate());
+ X509Certificate certificate = new JcaX509CertificateConverter()
+ .setProvider(ConfigurationUtil.PROVIDER).getCertificate(
+ certificateBuilder.build(contentSigner));
+
+ // cert.checkValidity();
+
+ certificate.verify(certificate.getPublicKey());
+
+ return certificate;
+ } catch (NoSuchAlgorithmException e) {
+ String errorMsg = "No such algorithm found when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (NoSuchProviderException e) {
+ String errorMsg = "No such provider found when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (OperatorCreationException e) {
+ String errorMsg = "Issue in operator creation when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CertificateExpiredException e) {
+ String errorMsg = "Certificate expired after generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CertificateNotYetValidException e) {
+ String errorMsg = "Certificate not yet valid when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CertificateException e) {
+ String errorMsg = "Certificate issue occurred when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (InvalidKeyException e) {
+ String errorMsg = "Invalid key used when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (SignatureException e) {
+ String errorMsg = "Signature related issue occurred when generating certificate";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+ public byte[] getPKIMessage(InputStream inputStream) throws KeystoreException {
+
+ try {
+ CMSSignedData signedData = new CMSSignedData(inputStream);
+ Store reqStore = signedData.getCertificates();
+ @SuppressWarnings("unchecked")
+ Collection reqCerts = reqStore.getMatches(null);
+
+ KeyStoreReader keyStoreReader = new KeyStoreReader();
+ PrivateKey privateKeyRA = keyStoreReader.getRAPrivateKey();
+ PrivateKey privateKeyCA = keyStoreReader.getCAPrivateKey();
+ X509Certificate certRA = (X509Certificate) keyStoreReader.getRACertificate();
+ X509Certificate certCA = (X509Certificate) keyStoreReader.getCACertificate();
+
+ CertificateFactory certificateFactory = CertificateFactory.getInstance(ConfigurationUtil.X_509);
+ X509CertificateHolder holder = reqCerts.iterator().next();
+ ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(holder.getEncoded());
+ X509Certificate reqCert = (X509Certificate) certificateFactory.generateCertificate(byteArrayInputStream);
+
+ PkcsPkiEnvelopeDecoder envelopeDecoder = new PkcsPkiEnvelopeDecoder(certRA, privateKeyRA);
+ PkiMessageDecoder messageDecoder = new PkiMessageDecoder(reqCert, envelopeDecoder);
+ PkiMessage> pkiMessage = messageDecoder.decode(signedData);
+ Object msgData = pkiMessage.getMessageData();
+
+ Nonce senderNonce = Nonce.nextNonce();
+ TransactionId transId = pkiMessage.getTransactionId();
+ Nonce recipientNonce = pkiMessage.getSenderNonce();
+ CertRep certRep;
+
+ PKCS10CertificationRequest certRequest = (PKCS10CertificationRequest) msgData;
+ X509Certificate generatedCert = generateCertificateFromCSR(
+ privateKeyCA, certRequest, certCA.getIssuerX500Principal().getName());
+
+ List issued = new ArrayList();
+ issued.add(generatedCert);
+
+ if (issued.size() == 0) {
+ certRep = new CertRep(transId, senderNonce, recipientNonce, FailInfo.badCertId);
+ } else {
+ CMSSignedData messageData = getMessageData(issued);
+ certRep = new CertRep(transId, senderNonce, recipientNonce, messageData);
+ }
+
+ PkcsPkiEnvelopeEncoder envEncoder = new PkcsPkiEnvelopeEncoder(reqCert, ConfigurationUtil.DES_EDE);
+ PkiMessageEncoder encoder = new PkiMessageEncoder(privateKeyRA, certRA, envEncoder);
+ CMSSignedData cmsSignedData = encoder.encode(certRep);
+
+ return cmsSignedData.getEncoded();
+
+ } catch (CertificateException e) {
+ String errorMsg = "Certificate issue occurred when generating getPKIMessage";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (MessageEncodingException e) {
+ String errorMsg = "Message encoding issue occurred when generating getPKIMessage";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (IOException e) {
+ String errorMsg = "Input output issue occurred when generating getPKIMessage";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (MessageDecodingException e) {
+ String errorMsg = "Message decoding issue occurred when generating getPKIMessage";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CMSException e) {
+ String errorMsg = "CMS issue occurred when generating getPKIMessage";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+ public static X509Certificate generateCertificateFromCSR(PrivateKey privateKey,
+ PKCS10CertificationRequest request,
+ String issueSubject)
+ throws KeystoreException {
+
+ CommonUtil commonUtil = new CommonUtil();
+ Date validityBeginDate = commonUtil.getValidityStartDate();
+ Date validityEndDate = commonUtil.getValidityEndDate();
+
+ X509v3CertificateBuilder certificateBuilder = new X509v3CertificateBuilder(
+ new X500Name(issueSubject), BigInteger.valueOf(System.currentTimeMillis()),
+ validityBeginDate, validityEndDate, request.getSubject(), request.getSubjectPublicKeyInfo());
+
+ ContentSigner sigGen;
+ X509Certificate issuedCert;
+ try {
+ certificateBuilder.addExtension(X509Extension.keyUsage, true, new KeyUsage(
+ KeyUsage.digitalSignature | KeyUsage.keyEncipherment));
+ sigGen = new JcaContentSignerBuilder(ConfigurationUtil.SHA256_RSA)
+ .setProvider(ConfigurationUtil.PROVIDER).build(privateKey);
+ issuedCert = new JcaX509CertificateConverter().setProvider(
+ ConfigurationUtil.PROVIDER).getCertificate(
+ certificateBuilder.build(sigGen));
+ } catch (CertIOException e) {
+ String errorMsg = "Certificate Input output issue occurred when generating generateCertificateFromCSR";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (OperatorCreationException e) {
+ String errorMsg = "Operator creation issue occurred when generating generateCertificateFromCSR";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CertificateException e) {
+ String errorMsg = "Certificate issue occurred when generating generateCertificateFromCSR";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+
+ return issuedCert;
+ }
+
+ private CMSSignedData getMessageData(final List certs) throws KeystoreException {
+
+ CMSSignedDataGenerator generator = new CMSSignedDataGenerator();
+ JcaCertStore store;
+ try {
+ store = new JcaCertStore(certs);
+ generator.addCertificates(store);
+
+ return generator.generate(new CMSAbsentContent());
+ } catch (CertificateEncodingException e) {
+ String errorMsg = "Certificate encoding issue occurred when generating getMessageData";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CMSException e) {
+ String errorMsg = "Message decoding issue occurred when generating getMessageData";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+ private PrivateKey getSignerKey(String signerPrivateKeyPath) throws KeystoreException {
+
+ File file = new File(signerPrivateKeyPath);
+ FileInputStream fis;
+
+ try {
+ fis = new FileInputStream(file);
+ DataInputStream dis = new DataInputStream(fis);
+ byte[] keyBytes = new byte[(int) file.length()];
+ dis.readFully(keyBytes);
+ dis.close();
+
+ String temp = new String(keyBytes);
+ String privateKeyPEM = temp.replace(
+ ConfigurationUtil.RSA_PRIVATE_KEY_BEGIN_TEXT, ConfigurationUtil.EMPTY_TEXT);
+ privateKeyPEM = privateKeyPEM
+ .replace(ConfigurationUtil.RSA_PRIVATE_KEY_END_TEXT, ConfigurationUtil.EMPTY_TEXT);
+
+ byte[] decoded = Base64.decodeBase64(privateKeyPEM);
+ PKCS8EncodedKeySpec encodedKeySpec = new PKCS8EncodedKeySpec(decoded);
+ KeyFactory keyFactory = KeyFactory.getInstance(ConfigurationUtil.RSA);
+
+ return keyFactory.generatePrivate(encodedKeySpec);
+ } catch (FileNotFoundException e) {
+ String errorMsg = "Private key file not found in getSignerKey";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (IOException e) {
+ String errorMsg = "Input output issue in getSignerKey";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (NoSuchAlgorithmException e) {
+ String errorMsg = "Algorithm not not found in getSignerKey";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (InvalidKeySpecException e) {
+ String errorMsg = "Invalid key found in getSignerKey";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+ private X509Certificate getSigner(String signerCertificatePath) throws KeystoreException {
+
+ X509Certificate certificate;
+ try {
+ CertificateFactory certificateFactory = CertificateFactory.getInstance(ConfigurationUtil.X_509);
+ certificate = (X509Certificate) certificateFactory.generateCertificate(
+ new FileInputStream(signerCertificatePath));
+
+ return certificate;
+ } catch (CertificateException e) {
+ String errorMsg = "Certificate related issue occurred in getSigner";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (FileNotFoundException e) {
+ String errorMsg = "Signer certificate path not found in getSigner";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+ public SCEPResponse getCACert() throws KeystoreException {
+
+ try {
+ SCEPResponse scepResponse = new SCEPResponse();
+ KeyStoreReader keyStoreReader = new KeyStoreReader();
+
+ byte[] caBytes = keyStoreReader.getCACertificate().getEncoded();
+ byte[] raBytes = keyStoreReader.getRACertificate().getEncoded();
+
+ final List certs = getRootCertificates(caBytes, raBytes);
+
+ byte[] bytes;
+ if (certs.size() == 0) {
+ scepResponse.setResultCriteria(CAStatus.CA_CERT_FAILED);
+ bytes = new byte[0];
+ } else if (certs.size() == 1) {
+ scepResponse.setResultCriteria(CAStatus.CA_CERT_RECEIVED);
+ bytes = certs.get(0).getEncoded();
+ } else {
+ scepResponse.setResultCriteria(CAStatus.CA_RA_CERT_RECEIVED);
+ CMSSignedDataGenerator generator = new CMSSignedDataGenerator();
+ JcaCertStore store = new JcaCertStore(certs);
+ generator.addCertificates(store);
+ CMSSignedData degenerateSd = generator.generate(new CMSAbsentContent());
+ bytes = degenerateSd.getEncoded();
+ }
+ scepResponse.setEncodedResponse(bytes);
+
+ return scepResponse;
+ } catch (CertificateEncodingException e) {
+ String errorMsg = "Certificate encoding issue occurred in getCACert";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CMSException e) {
+ String errorMsg = "CMS issue occurred in getCACert";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (IOException e) {
+ String errorMsg = "Input output issue occurred in getCACert";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (KeystoreException e) {
+ String errorMsg = "Keystore reading error occurred when handling profile request";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+ }
+
+}
\ No newline at end of file
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/KeyStoreReader.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/KeyStoreReader.java
new file mode 100755
index 0000000000..684b91b336
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/impl/KeyStoreReader.java
@@ -0,0 +1,186 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.impl;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.wso2.carbon.certificate.mgt.core.util.ConfigurationUtil;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.PrivateKey;
+import java.security.UnrecoverableKeyException;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateException;
+
+public class KeyStoreReader {
+
+ private static final Log log = LogFactory.getLog(KeyStoreReader.class);
+
+ private KeyStore loadKeyStore(String configEntryKeyStoreType, String configEntryKeyStorePath,
+ String configEntryKeyStorePassword) throws KeystoreException {
+
+ InputStream inputStream = null;
+ KeyStore keystore;
+
+ try {
+ keystore = KeyStore.getInstance(ConfigurationUtil.getConfigEntry(configEntryKeyStoreType));
+ inputStream = new FileInputStream(ConfigurationUtil.getConfigEntry(configEntryKeyStorePath));
+ keystore.load(inputStream, ConfigurationUtil.getConfigEntry(configEntryKeyStorePassword).toCharArray());
+
+ } catch (KeyStoreException e) {
+ String errorMsg = "KeyStore issue occurred when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (FileNotFoundException e) {
+ String errorMsg = "KeyStore file not found when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (NoSuchAlgorithmException e) {
+ String errorMsg = "Algorithm not found when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (CertificateException e) {
+ String errorMsg = "Certificate expired when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (IOException e) {
+ String errorMsg = "Input output issue occurred when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } finally {
+ try {
+ if (inputStream != null) {
+ inputStream.close();
+ }
+ } catch (IOException e) {
+ log.error("Error closing KeyStore input stream", e);
+ }
+ }
+
+ return keystore;
+ }
+
+ KeyStore loadMDMKeyStore() throws KeystoreException {
+ return loadKeyStore(ConfigurationUtil.CERTIFICATE_KEYSTORE, ConfigurationUtil.PATH_CERTIFICATE_KEYSTORE,
+ ConfigurationUtil.CERTIFICATE_KEYSTORE_PASSWORD);
+ }
+
+ public Certificate getCACertificate() throws KeystoreException {
+
+ KeyStore keystore = loadMDMKeyStore();
+ Certificate caCertificate;
+
+ try {
+ caCertificate = keystore.getCertificate(ConfigurationUtil.getConfigEntry(ConfigurationUtil.CA_CERT_ALIAS));
+ } catch (KeyStoreException e) {
+ String errorMsg = "KeyStore issue occurred when loading KeyStore";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+
+ if (caCertificate == null) {
+ throw new KeystoreException("CA certificate not found in KeyStore");
+ }
+
+ return caCertificate;
+ }
+
+ PrivateKey getCAPrivateKey() throws KeystoreException {
+
+ KeyStore keyStore = loadMDMKeyStore();
+ PrivateKey caPrivateKey;
+ try {
+ caPrivateKey = (PrivateKey) (keyStore.getKey(
+ ConfigurationUtil.getConfigEntry(ConfigurationUtil.CA_CERT_ALIAS),
+ ConfigurationUtil.getConfigEntry(ConfigurationUtil.KEYSTORE_CA_CERT_PRIV_PASSWORD).toCharArray()));
+ } catch (UnrecoverableKeyException e) {
+ String errorMsg = "Key is unrecoverable when retrieving CA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (KeyStoreException e) {
+ String errorMsg = "KeyStore issue occurred when retrieving CA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (NoSuchAlgorithmException e) {
+ String errorMsg = "Algorithm not found when retrieving CA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+
+ if (caPrivateKey == null) {
+ throw new KeystoreException("CA private key not found in KeyStore");
+ }
+
+ return caPrivateKey;
+ }
+
+ public Certificate getRACertificate() throws KeystoreException {
+
+ KeyStore keystore = loadMDMKeyStore();
+ Certificate raCertificate;
+ try {
+ raCertificate = keystore.getCertificate(ConfigurationUtil.getConfigEntry(ConfigurationUtil.RA_CERT_ALIAS));
+ } catch (KeyStoreException e) {
+ String errorMsg = "KeyStore issue occurred when retrieving RA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+
+ if (raCertificate == null) {
+ throw new KeystoreException("RA certificate not found in KeyStore");
+ }
+
+ return raCertificate;
+ }
+
+ PrivateKey getRAPrivateKey() throws KeystoreException {
+
+ KeyStore keystore = loadMDMKeyStore();
+ PrivateKey raPrivateKey;
+ try {
+ raPrivateKey = (PrivateKey) (keystore.getKey(
+ ConfigurationUtil.getConfigEntry(ConfigurationUtil.RA_CERT_ALIAS),
+ ConfigurationUtil.getConfigEntry(ConfigurationUtil.KEYSTORE_RA_CERT_PRIV_PASSWORD).toCharArray()));
+ } catch (UnrecoverableKeyException e) {
+ String errorMsg = "Key is unrecoverable when retrieving RA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (KeyStoreException e) {
+ String errorMsg = "KeyStore issue occurred when retrieving RA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ } catch (NoSuchAlgorithmException e) {
+ String errorMsg = "Algorithm not found when retrieving RA private key";
+ log.error(errorMsg, e);
+ throw new KeystoreException(errorMsg, e);
+ }
+
+ if (raPrivateKey == null) {
+ throw new KeystoreException("RA private key not found in KeyStore");
+ }
+
+ return raPrivateKey;
+ }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/internal/CertificateManagementServiceComponent.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/internal/CertificateManagementServiceComponent.java
new file mode 100644
index 0000000000..5996028f7d
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/internal/CertificateManagementServiceComponent.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.internal;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.osgi.framework.BundleContext;
+import org.osgi.service.component.ComponentContext;
+import org.wso2.carbon.certificate.mgt.core.service.CertificateManagementServiceImpl;
+
+/**
+ * @scr.component name="org.wso2.carbon.certificate.mgt" immediate="true"
+ */
+public class CertificateManagementServiceComponent {
+
+ private static Log log = LogFactory.getLog(CertificateManagementServiceComponent.class);
+
+ @SuppressWarnings("unused")
+ protected void activate(ComponentContext componentContext) {
+ try {
+ if (log.isDebugEnabled()) {
+ log.debug("Initializing certificate management core bundle");
+ }
+
+ BundleContext bundleContext = componentContext.getBundleContext();
+ bundleContext.registerService(CertificateManagementServiceImpl.class.getName(),
+ CertificateManagementServiceImpl.getInstance(), null);
+
+ if (log.isDebugEnabled()) {
+ log.debug("Certificate management core bundle has been successfully initialized");
+ }
+ } catch (Throwable e) {
+ log.error("Error occurred while initializing certificate management core bundle", e);
+ }
+ }
+
+ @SuppressWarnings("unused")
+ protected void deactivate(ComponentContext componentContext) {
+ //do nothing
+ }
+
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementService.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementService.java
new file mode 100644
index 0000000000..c9b1ca5c96
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementService.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.service;
+
+import org.bouncycastle.pkcs.PKCS10CertificationRequest;
+import org.wso2.carbon.certificate.mgt.core.dto.SCEPResponse;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+
+import java.io.InputStream;
+import java.security.PrivateKey;
+import java.security.cert.Certificate;
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+public interface CertificateManagementService {
+
+ Certificate getCACertificate() throws KeystoreException;
+
+ Certificate getRACertificate() throws KeystoreException;
+
+ public List getRootCertificates(byte[] ca, byte[] ra) throws KeystoreException;
+
+ public X509Certificate generateX509Certificate() throws KeystoreException;
+
+ public SCEPResponse getCACertSCEP() throws KeystoreException;
+
+ public byte[] getCACapsSCEP();
+
+ public byte[] getPKIMessageSCEP(InputStream inputStream) throws KeystoreException;
+
+ public X509Certificate generateCertificateFromCSR(PrivateKey privateKey,
+ PKCS10CertificationRequest request,
+ String issueSubject) throws KeystoreException;
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementServiceImpl.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementServiceImpl.java
new file mode 100644
index 0000000000..a294acbc16
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/service/CertificateManagementServiceImpl.java
@@ -0,0 +1,87 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.service;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.bouncycastle.pkcs.PKCS10CertificationRequest;
+import org.wso2.carbon.certificate.mgt.core.dto.SCEPResponse;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+import org.wso2.carbon.certificate.mgt.core.impl.CertificateGenerator;
+import org.wso2.carbon.certificate.mgt.core.impl.KeyStoreReader;
+import org.wso2.carbon.certificate.mgt.core.util.ConfigurationUtil;
+
+import java.io.InputStream;
+import java.security.PrivateKey;
+import java.security.cert.Certificate;
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+public class CertificateManagementServiceImpl implements CertificateManagementService {
+
+ private static final Log log = LogFactory.getLog(CertificateManagementServiceImpl.class);
+ private static CertificateManagementServiceImpl certificateManagementServiceImpl;
+ private static KeyStoreReader keyStoreReader;
+ private static CertificateGenerator certificateGenerator;
+
+ private CertificateManagementServiceImpl() {}
+
+ public static CertificateManagementServiceImpl getInstance() {
+
+ if (certificateManagementServiceImpl == null) {
+ certificateManagementServiceImpl = new CertificateManagementServiceImpl();
+ keyStoreReader = new KeyStoreReader();
+ certificateGenerator = new CertificateGenerator();
+ }
+ return certificateManagementServiceImpl;
+ }
+
+ public Certificate getCACertificate() throws KeystoreException {
+ return keyStoreReader.getCACertificate();
+ }
+
+ public Certificate getRACertificate() throws KeystoreException {
+ return keyStoreReader.getRACertificate();
+ }
+
+ public List getRootCertificates(byte[] ca, byte[] ra) throws KeystoreException {
+ return certificateGenerator.getRootCertificates(ca, ra);
+ }
+
+ public X509Certificate generateX509Certificate() throws KeystoreException {
+ return certificateGenerator.generateX509Certificate();
+ }
+
+ public SCEPResponse getCACertSCEP() throws KeystoreException {
+ return certificateGenerator.getCACert();
+ }
+
+ public byte[] getCACapsSCEP() {
+ return ConfigurationUtil.POST_BODY_CA_CAPS.getBytes();
+ }
+
+ public byte[] getPKIMessageSCEP(InputStream inputStream) throws KeystoreException {
+ return certificateGenerator.getPKIMessage(inputStream);
+ }
+
+ public X509Certificate generateCertificateFromCSR(PrivateKey privateKey,
+ PKCS10CertificationRequest request,
+ String issueSubject) throws KeystoreException {
+ return certificateGenerator.generateCertificateFromCSR(privateKey, request, issueSubject);
+ }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtil.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtil.java
new file mode 100755
index 0000000000..a149c92569
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtil.java
@@ -0,0 +1,43 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.util;
+
+import java.util.Calendar;
+import java.util.Date;
+
+public class CommonUtil {
+
+ public Date getValidityStartDate() {
+ Date targetDate = new Date();
+ Calendar calendar = Calendar.getInstance();
+ calendar.setTime(targetDate);
+ calendar.add(Calendar.DATE, -2);
+
+ return calendar.getTime();
+ }
+
+ public Date getValidityEndDate() {
+ Date targetDate = new Date();
+ Calendar calendar = Calendar.getInstance();
+ calendar.setTime(targetDate);
+ calendar.add(Calendar.YEAR, 100);
+
+ return calendar.getTime();
+ }
+
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/ConfigurationUtil.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/ConfigurationUtil.java
new file mode 100644
index 0000000000..a9a55d9b12
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/main/java/org/wso2/carbon/certificate/mgt/core/util/ConfigurationUtil.java
@@ -0,0 +1,137 @@
+/*
+ * Copyright (c) 2015, WSO2 Inc. (http://www.wso2.org) All Rights Reserved.
+ *
+ * WSO2 Inc. licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except
+ * in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.wso2.carbon.certificate.mgt.core.util;
+
+import org.w3c.dom.Document;
+import org.w3c.dom.NodeList;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+import org.xml.sax.SAXException;
+import javax.xml.parsers.DocumentBuilder;
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+import java.io.File;
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.Map;
+
+public class ConfigurationUtil {
+
+ public static final String PATH_CERTIFICATE_KEYSTORE = "CertificateKeystoreLocation";
+ public static final String CERTIFICATE_KEYSTORE_PASSWORD = "CertificateKeystorePassword";
+ public static final String KEYSTORE_CA_CERT_PRIV_PASSWORD = "CAPrivateKeyPassword";
+ public static final String KEYSTORE_RA_CERT_PRIV_PASSWORD = "RAPrivateKeyPassword";
+ public static final String CA_CERT_ALIAS = "CACertAlias";
+ public static final String RA_CERT_ALIAS = "RACertAlias";
+ public static final String SIGNATUREALGO = "SHA1withRSA";
+ public static final String PROVIDER = "BC";
+ public static final String KEYSTORE = "Type";
+ public static final String CERTIFICATE_KEYSTORE = "CertificateKeystoreType";
+ public static final String RSA = "RSA";
+ public static final String UTF_8 = "UTF-8";
+ public static final String SHA256_RSA = "SHA256WithRSAEncryption";
+ public static final String X_509 = "X.509";
+ public static final String POST_BODY_CA_CAPS = "POSTPKIOperation\nSHA-1\nDES3\n";
+ public static final String DES_EDE = "DESede";
+ public static final String CONF_LOCATION = "conf.location";
+ private static final String CARBON_HOME = "carbon.home";
+ private static final String CERTIFICATE_CONFIG_XML = "certificate-config.xml";
+ private static final String CARBON_HOME_ENTRY = "${carbon.home}";
+ public static final String DEFAULT_PRINCIPAL = "O=WSO2, OU=Mobile, C=LK";
+ public static final String RSA_PRIVATE_KEY_BEGIN_TEXT = "-----BEGIN RSA PRIVATE KEY-----\n";
+ public static final String RSA_PRIVATE_KEY_END_TEXT = "-----END RSA PRIVATE KEY-----";
+ public static final String EMPTY_TEXT = "";
+ public static final int RSA_KEY_LENGTH = 1024;
+
+
+ private static ConfigurationUtil configurationUtil;
+ private static final String[] emmConfigEntryNames = { CA_CERT_ALIAS, RA_CERT_ALIAS,
+ CERTIFICATE_KEYSTORE, PATH_CERTIFICATE_KEYSTORE, CERTIFICATE_KEYSTORE_PASSWORD,
+ KEYSTORE_CA_CERT_PRIV_PASSWORD, KEYSTORE_RA_CERT_PRIV_PASSWORD };
+
+ private static Map configMap;
+
+ private static Map readEMMConfigurations() throws KeystoreException {
+
+ String emmConfLocation = System.getProperty(CONF_LOCATION) + File.separator + CERTIFICATE_CONFIG_XML;
+
+ if (configurationUtil == null || configMap == null) {
+
+ configurationUtil = new ConfigurationUtil();
+ configMap = new HashMap();
+
+ Document document;
+ try {
+ File fXmlFile = new File(emmConfLocation);
+ DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
+ DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();
+ document = documentBuilder.parse(fXmlFile);
+ } catch (ParserConfigurationException e) {
+ throw new KeystoreException("Error parsing configuration in ios-config.xml file");
+ } catch (SAXException e) {
+ throw new KeystoreException("SAX exception in ios-config.xml file");
+ } catch (IOException e) {
+ throw new KeystoreException("Error reading ios-config.xml file");
+ }
+
+ for (String configEntry : emmConfigEntryNames) {
+ NodeList elements = document.getElementsByTagName(configEntry);
+ if (elements != null && elements.getLength() > 0) {
+ configMap.put(configEntry, elements.item(0).getTextContent());
+ }
+ }
+
+ String emmKeyStoreLocation = replaceCarbonHomeEnvEntry(configMap.get(PATH_CERTIFICATE_KEYSTORE));
+ if (emmKeyStoreLocation != null) {
+ configMap.put(PATH_CERTIFICATE_KEYSTORE, emmKeyStoreLocation);
+ }
+ }
+
+ return configMap;
+ }
+
+ public static String getConfigEntry(final String entry) throws KeystoreException {
+
+ Map configurationMap = readEMMConfigurations();
+ String configValue = configurationMap.get(entry);
+
+ if (configValue == null) {
+ throw new KeystoreException(String.format("Configuration entry %s not available", entry));
+ }
+
+ return configValue.trim();
+ }
+
+ private static String replaceCarbonHomeEnvEntry(String entry) {
+ if (entry != null && entry.toLowerCase().contains(CARBON_HOME_ENTRY)) {
+ return entry.replace(CARBON_HOME_ENTRY, System.getProperty(CARBON_HOME));
+ }
+
+ return null;
+ }
+
+ public static ConfigurationUtil getInstance() {
+ if (configurationUtil == null) {
+ synchronized (ConfigurationUtil.class) {
+ if (configurationUtil == null) {
+ configurationUtil = new ConfigurationUtil();
+ }
+ }
+ }
+ return configurationUtil;
+ }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGeneratorTestSuite.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGeneratorTestSuite.java
new file mode 100644
index 0000000000..8d12f336fe
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/impl/CertificateGeneratorTestSuite.java
@@ -0,0 +1,101 @@
+package org.wso2.carbon.certificate.mgt.core.impl;
+
+import org.apache.commons.io.FileUtils;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.testng.Assert;
+import org.testng.annotations.Test;
+import org.wso2.carbon.certificate.mgt.core.exception.KeystoreException;
+import org.wso2.carbon.certificate.mgt.core.util.ConfigurationUtil;
+
+import java.io.File;
+import java.io.IOException;
+import java.security.cert.X509Certificate;
+import java.util.List;
+
+public class CertificateGeneratorTestSuite {
+
+ private static Log log = LogFactory.getLog(CertificateGeneratorTestSuite.class);
+ private static final String CA_CERT_PEM = "src/test/resources/ca_cert.pem";
+ private static final String RA_CERT_PEM = "src/test/resources/ra_cert.pem";
+ private static final String CA_PRIVATE_KEY_PATH = "src/test/resources/ca_private.key";
+ private final CertificateGenerator certificateGenerator = new CertificateGenerator();
+
+ @Test
+ public void testGetRootCertificates() {
+ try {
+ File caPemFile = new File(CA_CERT_PEM);
+ File raPemFile = new File(RA_CERT_PEM);
+
+ byte[] ca = FileUtils.readFileToByteArray(caPemFile);
+ byte[] ra = FileUtils.readFileToByteArray(raPemFile);
+
+ List rootCertificates = certificateGenerator.getRootCertificates(ca, ra);
+ Assert.assertNotNull(rootCertificates, "Root certificates retrieved");
+
+ Assert.assertEquals(rootCertificates.get(0).getType(), ConfigurationUtil.X_509);
+ Assert.assertEquals(rootCertificates.get(1).getType(), ConfigurationUtil.X_509);
+ } catch (IOException e) {
+ Assert.fail("Error reading byte streams for CA and RA ", e);
+ } catch (KeystoreException e) {
+ Assert.fail("Error retrieving root certificates ", e);
+ }
+ }
+
+ @Test
+ public void testGenerateX509Certificate() {
+ try {
+ X509Certificate certificate = certificateGenerator.generateX509Certificate();
+
+ Assert.assertNotNull(certificate, "Certificate received");
+ Assert.assertEquals(certificate.getType(), ConfigurationUtil.X_509);
+ } catch (KeystoreException e) {
+ Assert.fail("Error occurred while generating X509 certificate ", e);
+ }
+ }
+
+// @Test
+// public void testGetPKIMessage() {
+// try {
+// byte[] pkiMessage = certificateGenerator.getPKIMessage(null);
+// } catch (IOSEnrollmentException e) {
+// Assert.fail("Error occurred while retrieving PKI Message ", e);
+// }
+// }
+
+ @Test
+ public void testGenerateCertificateFromCSR() {
+ try {
+ X509Certificate certificate = certificateGenerator.generateX509Certificate();
+
+ Assert.assertNotNull(certificate, "Certificate received");
+ Assert.assertEquals(certificate.getType(), ConfigurationUtil.X_509);
+ } catch (KeystoreException e) {
+ Assert.fail("Error occurred while generating certificate ", e);
+ }
+ }
+
+// @Test
+// public void testGetSignerKey() {
+// try {
+// PrivateKey privateKey = certificateGenerator.getSignerKey(CA_PRIVATE_KEY_PATH);
+//
+// Assert.assertNotNull(privateKey, "Private key received");
+// Assert.assertEquals(privateKey.getAlgorithm(), ConfigurationUtil.RSA);
+// } catch (KeystoreException e) {
+// Assert.fail("Error occurred while generating certificate ", e);
+// }
+// }
+//
+// @Test
+// public void testGetSigner() {
+// try {
+// X509Certificate certificate = certificateGenerator.getSigner(CA_CERT_PEM);
+//
+// Assert.assertNotNull(certificate, "Certificate received");
+// Assert.assertEquals(certificate.getType(), ConfigurationUtil.X_509);
+// } catch (KeystoreException e) {
+// Assert.fail("Error while retrieving certificate ", e);
+// }
+// }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtilTestSuite.java b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtilTestSuite.java
new file mode 100644
index 0000000000..45ab597868
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/java/org/wso2/carbon/certificate/mgt/core/util/CommonUtilTestSuite.java
@@ -0,0 +1,38 @@
+package org.wso2.carbon.certificate.mgt.core.util;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.testng.Assert;
+import org.testng.annotations.Test;
+
+import java.util.Date;
+
+public class CommonUtilTestSuite {
+
+ private static Log log = LogFactory.getLog(CommonUtilTestSuite.class);
+ private final CommonUtil commonUtil = new CommonUtil();
+
+ @Test
+ public void testValidityStartDate() {
+ Date validityStartDate = commonUtil.getValidityStartDate();
+
+ if(validityStartDate == null) {
+ Assert.fail("Validity start date is empty");
+ }
+
+ Date todayDate = new Date();
+ Assert.assertTrue(validityStartDate.before(todayDate), "Validity start date is valid");
+ }
+
+ @Test
+ public void testValidityEndDate() {
+ Date validityEndDate = commonUtil.getValidityEndDate();
+
+ if(validityEndDate == null) {
+ Assert.fail("Validity end date is empty");
+ }
+
+ Date todayDate = new Date();
+ Assert.assertTrue(validityEndDate.after(todayDate), "Validity end date is valid");
+ }
+}
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_cert.pem b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_cert.pem
new file mode 100644
index 0000000000..417394bb96
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_cert.pem
@@ -0,0 +1,34 @@
+-----BEGIN CERTIFICATE-----
+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
+-----END CERTIFICATE-----
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_private.key b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_private.key
new file mode 100644
index 0000000000..d216007d3c
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ca_private.key
@@ -0,0 +1,51 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIJKgIBAAKCAgEA0nvnrOOWQ0ol/07zSrAVbGXCvi85rzShoZdo7wu6Pxk1vvPI
+YBOmlOZmLZutFV808YeE3/RERvn4Zx/TG+TVvlangT4mgMp9kzA5VCwxWYpgeqim
+CKITbwv9ig13ReZkDQnTed9DivNiCDBBfuhGxb8Cm2R1RFXiLzEPdKyoMYNnJjFB
+UOSPnmevB4R3kVY6di++l1sUnhZqcmYZ7VZG0swnSMWLu3D1Zztb/n5+8gD1u8cM
+egbVWV/KNBRK9MuUA3tSLTO1dNw5m43ccjSm60xBHJoAPsuOXsTVE6KoyE3/PzQF
+yTxiLsQs6ar5wk6Kv/gIBqaPxK6BnSJej3bayWtJ6ZYv22M1PswWaMVeaAh9WZok
+Xs7ErLEeE7yAkpOVTYpIkkfYLMzCcZ1EWsOWwCi1WMYtgVYdQ3gdba4DZysQSaT5
+R27CdUxrOpTAEXG/4g1/RTnluxdO/sLcvTohRpMG/GHEpCbOP0F5AbBYALYKjizm
+uJPa22K9JGVeKM8gQNN+a8T9+OPgp9BA5Njf4R6Npwx7qBv+pWwJnWD1NuTtYuCN
+gcG45BIDPeXA8+o9j7oJqR4vb3BbI+DukbNHqUxxgi1R0cm42xOKOzTHpeLU7mIi
+4vajS+XwVEf61kWbe6O0IgemuNSByfpo5H0yz82RQkLOIooBvgqiiE0WCv8CAwEA
+AQKCAgBAyt+AOvawdAzKULVX0mhl29Vc0hDBvEPdCEzG+Sc18T64LzcJTENFJr9h
+XsCjCZG0n/DpN7ok1yH+LK/BsGmTk/0wLb+QecS6IGglXw058PzOBUhG9A1ja596
+dba3j7pQwSuWIoIaLd2Jg8FFnZ7blHbq+ruWc5GS0Vleox+LTlXcTeE7U4BaVLRu
+bfqYhKCubPgQg3sPRvsxh/iHNL3MegfFwPnIk3cXdhBVgP725BDA4v8WOTBHuNL3
+wR9px5kikT20qGw9MuWQ2tR3W3neiLSqZ0WYDvUeexzUVIf8UPY3sH3vemUG3GCu
+9XC4vZC8k091LKSo+MbxZfkR1JZ4R2CEMcFJaz/jc6VN2bTOWuWWczReOzq0Xx7P
+GbsmcQNBhY8qBoz+cOWifxBWZzKSWfcNMgwnNyAKlDrOehpp+gZ1yH7dk9fL/wrE
+jSEEnhq4SVDeGEOo7gEi17Px8/256PKwQB4wELPBwODBslPzJ0PPDKk4mxBq3JQP
+EJKnBhu15KGJuoUZ42GcYSn55Zu/Rujqhn9cWbwhq0KrExwVI3EWnd89dYv360Mu
+RskqPTuEpAUOUCQPIUT0p3f1PBgML6L5HxjJDUt6n2N8Y1xT8sKF6FKnbvdizcqz
+v0+xdBk0xpSoazHzH1lnia3fZ6EPzMPHbLrz4ga0eUdaGwbSEQKCAQEA6sUljKKH
+7EsKsXaQ6igqQ2TkZWTu+xqRlFjb2tTmyHt99O4w3L45ae0la7ApygTRFHs3z9XB
+ws12bVkXdA35txKk97SNmWDrZbxpswHmTSnrOLGD2VFD4J/YifuBkT8K7PEJno9U
+Ewi70RHGQEFfL3VL1TOa2WnJELOLkzoCkBL/NaVawtbK7O7KIrCu3jFCq3zu+uku
+XVHTzXi+gr+uknGraxKcyLhCu6/7Uot+uYrtCzFsk4vTs2bovWuL2KLi/MAP8x3K
+FcNNj2SPr+PzwzlqthiW/rtZjg7MFMdN9RAhImjbIJt3svzWsB4nr7VQxHYStfFJ
+xIwbFp233qFKjQKCAQEA5YSK9L9o4LRDilwCz3p1tZ1tgY9tMUbG2wx0dG9xrETY
+4yGwTPAc++Tp3aOnbO544ZpnGLBoQTgtOc1p4jyj/Md2CwlP8UfbYhEdYEN9Gn5H
+ylu1b0cRwHeO4Bfnekqk8EL0rl3KUUsAk2uKEwCBwsuxjFurMDasyoA5T5gcsa4p
+EhEF5D7t5sJb7f8hP+vMBa2yUKQT9dflF8xN7iHvxhun1qipX1AzZ341H94QbgRb
+rYdfxzBr4aa5UZe5Ls9ofQf0S3zXVEXah/Pg+3o0BppdIrtLXTWcI/yeE6L8/Ebr
+jMXLiTzd4bwWjbTijEJ/MKb/UsPQqbZsXNzMiyxuuwKCAQEAvs0xQkYJr+ohK6+Q
+AS5ZguJpmVpZu6yRKn65V/V2BvQOn1RCU/Up1kQNCKNooy4c+sdVyc0RJ5AyspYY
+sJJ3I+m8NzD/b+tMBSgGw5xEnuv1puLmpGUehF2E8Ed+uxwAdidDySD1lG6hrj4C
+4NAAWyK6WfER5abK6Y7yXdpkoNE/p0rXI8jLrZo4n872n9BrPdJQq419yAwr1i9O
+rha4+330chXzZFIUslNJL4H9oTAejN1DP/sBOCnn96KDSrK/RemWTOEmD1/mFicF
+fE8IGt78Mjhz510+YGz4Qd7lJclRFJUhmjOgKdDBbutjF7OFi9XmSQZsDJhNn6jY
++dAeNQKCAQEAsAFpUfCq644xMRwIJ7VAKQrVnAIx+RTOj9JIR7XilPmi3OLLwORt
+RZmw4f+K99UUK+Vs5Bj7ifAbdnUYmp5oHwOSeTol7OBu0xBO17BJcpSeVwbm5rO4
+YEEO9rg+EaDGRV0DJ+fSq255vZM9Kf88gvYTbJArgeibrxqPWINMldD5u9oEC5la
+dJhdSPBaPhuDtGMUGBULHX73Nr28kT3DEsfIeKuUXvwwv0+gS5TOQp/i8fqbLzPp
+tvxUpsZUAxqYhTEhXPYaZoy+3Xze7dozpVCg1W6Nh6gB2fLyAhr+KDP2lFhmEhL0
+EBRds0Oga3De+p9FsuFo1YyIItpLnPpw2wKCAQEArUQM9k0Qprczx9sKf/YF+ulx
+tiiGyRUV7kAcrQiQAjB88wPoB/ovnW4VCI4y/mNeZGvyCWeQx9g+Ntc5BJlIlJYi
+wviyQ5Lq1OlOWQlWIkKCI2Z+s5uYKTSgZRp7VLnvKswHnxBy2Bxq3i9taP6QYlZz
+3ff/plfK3ZM6moc89wl/aQgdhWsV/WV7bKcnncM9K2N7dpKzRcZ+6iuJt9PNKo5V
+6GUYEvn04twumzgqGtYQbiq63YfHe8QLvX/j8ffGH8O0rUAIrQnrNl0n0SoE9ECU
+lUCVCXzypT+MKAeHfI4aFeWG48sdfnHPWOkyRHXWFLAwkHUVnqmYhXLpmJBtMw==
+-----END RSA PRIVATE KEY-----
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/certificate-config.xml b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/certificate-config.xml
new file mode 100755
index 0000000000..b8202f2a2e
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/certificate-config.xml
@@ -0,0 +1,19 @@
+
+
+
+
+ ${carbon.home}/repository/resources/security/wso2cert.jks
+
+ JKS
+
+ wso2carbon
+
+ cacert
+
+ cacert
+
+ racert
+
+ racert
+
+
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/log4j.properties b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/log4j.properties
new file mode 100644
index 0000000000..2143753b40
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/log4j.properties
@@ -0,0 +1,33 @@
+#
+# Copyright 2015 WSO2, Inc. (http://wso2.com)
+#
+# WSO2 Inc. licenses this file to you under the Apache License,
+# version 2.0 (the "License"); you may not use this file except
+# in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+
+#
+# This is the log4j configuration file used by WSO2 Carbon
+#
+# IMPORTANT : Please do not remove or change the names of any
+# of the Appenders defined here. The layout pattern & log file
+# can be changed using the WSO2 Carbon Management Console, and those
+# settings will override the settings in this file.
+#
+
+log4j.rootLogger=INFO, STD_OUT
+
+# Redirect log messages to console
+log4j.appender.STD_OUT=org.apache.log4j.ConsoleAppender
+log4j.appender.STD_OUT.Target=System.out
+log4j.appender.STD_OUT.layout=org.apache.log4j.PatternLayout
+log4j.appender.STD_OUT.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss} %-5p %c{1}:%L - %m%n
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ra_cert.pem b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ra_cert.pem
new file mode 100644
index 0000000000..516b08ccee
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/ra_cert.pem
@@ -0,0 +1,33 @@
+-----BEGIN CERTIFICATE-----
+MIIFqDCCA5CgAwIBAgIBAjANBgkqhkiG9w0BAQUFADCBizELMAkGA1UEBhMCVVMx
+DTALBgNVBAgTBFRlc3QxDTALBgNVBAcTBFRlc3QxETAPBgNVBAoTCFRlc3QgT3Jn
+MRYwFAYDVQQLEw1UZXN0IG9yZyB1bml0MRUwEwYDVQQDEwxXU08yIFJvb3QgQ0Ex
+HDAaBgkqhkiG9w0BCQEWDXJvb3RAd3NvMi5jb20wHhcNMTUwMTI3MTI1MzAxWhcN
+MTcxMDIzMTI1MzAxWjCBgzELMAkGA1UEBhMCVVMxGTAXBgNVBAgTEFRlc3QgUkEg
+UHJvdmluY2UxFTATBgNVBAcTDFRlc3QgUkEgQ2l0eTEUMBIGA1UEChMLVGVzdCBS
+QSBPcmcxGTAXBgNVBAsTEFRlc3QgUkEgb3JnIHVuaXQxETAPBgNVBAMTCFdTTzIg
+UkEgMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAtUMgUlYYU3/TPfEe
+zNAvBaiOi/jUjfZ9IbxvMl7obDT17/5vU68TCGkZRjyfYUEiGNBisUEFWjSk/sGL
+/ofYKUAxw33cd456FLMjaJX/4Zk4y8eYB1m1GGlHejoDyjPhq8S6GDmy+PXbJr8n
+lSTROR2mQHkGwYrCreWeU4AYWzdctIFk7U2DKeIvZYSidIIjfSpDXURxrt9LPvig
+fMzr5l/WkZfjvk5S+W7rgMtpllxlEPgyDc07pNAdNSq5FB990oaUsVX8o6l6wdCw
+grYz83edPOKwZa04fsVztz2oF3ZYSGGjD3lwh0KS/jUL+awRyhMx5p/O1hySg6PP
+pJjeqRuobNTuwSAXxp3nsNSY0DkGW04pSxWoDQqhnpaqBbAf71l6ya2e3so1SHm/
+jouWSYTHncq5bmGE4AN7ZGVGZvfx84+UR8fNxJxxLo+DFFE0oJNzpPGNxILpHxgT
+V7IOII6mhfkrQk+AFQiW2Y5FXLVYv8r+SPXW8pYsjaWl971XZeM/HC3L9IZkCrrr
+a0ID5oT6vt+xTmdo4yiBqIP5TBYm+1a9YzMAy7XGtPih9k6cufMLcfzvUZdOXw9x
+3T05nM5ZtcDq0gHvUzQ7sfHTguWVnuHVEdb2ox4x2L5NzEA475fbSdXpMok9z/z7
+Xa71vIZi28InDAFBQehUlJnFtf0CAwEAAaMdMBswDAYDVR0TBAUwAwEB/zALBgNV
+HQ8EBAMCBaAwDQYJKoZIhvcNAQEFBQADggIBAAO0TwnQBMJvL8wbfsnTqAGCCHM4
+x1cpW+KgTmflPEliYGOn/dJYDz/dUowCgoj5mrSxjQ3G1/qL+9Y7E33h0tyw37vH
+YDL1p2Tn+fwmXRHrk+CHoPHNcImEfSIDWbbG7ehBR6erVfbQSZjmj4fwPkItp8rP
+nyUtXHOLpfFYoAxYkNP9+C8vpC9W/H1pj3rzmQFA1z+EZAKVV7vDAxbe6sun84nf
+YAaMSIzHx1B+XLHokgChmnZr3wV7EypBEmmKp4ITvJqK7WsIG9t1M6hI7OTPCURR
+mdy+DJtIoIUbZxHyIyC9nPcVJFkdBusnfXq4uMb0KMaWYCU8ESqZPySukF2qZ5KA
+acB+0ZhY+EGQ6QF/hB6iiUj96BlQ7XAPXFU6xUt6nRjDiJmb3vW1IEv0hpbs7PRl
+UMlbOwQk37rXpFqQc6ZW7lsxI2RmfkD4DOkQIGH3q5foVr+PEp0uSPWrFX62eBet
+1S4c/opVv6BcuUgilYABHTYxb45GfYwJAI9Qw2uQWT8DmhtVbcYu6GLYGlnRyaOC
+EPzc0z0KQTjhsgHWzi60IYBBh+fy+Z7w5X1rTTvhFOoU5J7kedGEqiBatIZmhF5t
+UFbT0u350ET5a0Kg83gu5aLwXdoIP9o7bp3XzLBMVNny2RX3tOHUA2HBe/p0h0OU
+Ggt3G6oD0gBe9pZI
+-----END CERTIFICATE-----
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/testng.xml b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/testng.xml
new file mode 100644
index 0000000000..8d91ced59f
--- /dev/null
+++ b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/testng.xml
@@ -0,0 +1,10 @@
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/wso2cert.jks b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/wso2cert.jks
new file mode 100644
index 0000000000..c1e9ace3c2
Binary files /dev/null and b/components/certificate-mgt/org.wso2.carbon.certificate.mgt.core/src/test/resources/wso2cert.jks differ
diff --git a/components/certificate-mgt/pom.xml b/components/certificate-mgt/pom.xml
new file mode 100644
index 0000000000..7316cac2e4
--- /dev/null
+++ b/components/certificate-mgt/pom.xml
@@ -0,0 +1,60 @@
+
+
+
+
+
+
+ org.wso2.carbon.devicemgt
+ carbon-devicemgt
+ 0.9.2-SNAPSHOT
+ ../../pom.xml
+
+
+ 4.0.0
+ org.wso2.carbon.devicemgt
+ certificate-mgt
+ 0.9.2-SNAPSHOT
+ pom
+ WSO2 Carbon - Certificate Management Component
+ http://wso2.org
+
+
+ org.wso2.carbon.certificate.mgt.core
+
+
+
+
+
+
+ org.apache.felix
+ maven-scr-plugin
+ 1.7.2
+
+
+ generate-scr-scrdescriptor
+
+ scr
+
+
+
+
+
+
+
+
diff --git a/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/pom.xml b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/pom.xml
new file mode 100644
index 0000000000..a5ca2039ad
--- /dev/null
+++ b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/pom.xml
@@ -0,0 +1,156 @@
+
+
+
+
+
+
+ org.wso2.carbon.devicemgt
+ device-mgt-feature
+ 0.9.2-SNAPSHOT
+ ../pom.xml
+
+
+ 4.0.0
+ org.wso2.carbon.certificate.mgt.server.feature
+ pom
+ 0.9.2-SNAPSHOT
+ WSO2 Carbon - Certificate Management Server Feature
+ http://wso2.org
+ This feature contains the core bundles required for back-end Certificate Management functionality
+
+
+
+
+ org.wso2.carbon.devicemgt
+ org.wso2.carbon.certificate.mgt.core
+
+
+ org.bouncycastle.wso2
+ bcprov-jdk15on
+
+
+ org.bouncycastle.wso2
+ bcpkix-jdk15on
+
+
+ org.bouncycastle.wso2
+ bcmail-jdk15on
+
+
+ com.google.code.jscep.wso2
+ jscep
+
+
+ commons-io.wso2
+ commons-io
+
+
+ commons-lang.wso2
+ commons-lang
+
+
+ commons-codec.wso2
+ commons-codec
+
+
+
+
+
+
+ maven-resources-plugin
+ 2.6
+
+
+ copy-resources
+ generate-resources
+
+ copy-resources
+
+
+ src/main/resources
+
+
+ resources
+
+ build.properties
+ p2.inf
+
+
+
+
+
+
+
+
+ org.wso2.maven
+ carbon-p2-plugin
+ ${carbon.p2.plugin.version}
+
+
+ p2-feature-generation
+ package
+
+ p2-feature-gen
+
+
+ org.wso2.carbon.device.mgt.server
+ ../../../features/etc/feature.properties
+
+
+ org.wso2.carbon.p2.category.type:server
+ org.eclipse.equinox.p2.type.group:false
+
+
+
+
+ org.wso2.carbon.devicemgt:org.wso2.carbon.certificate.mgt.core:${carbon.device.mgt.version}
+
+
+ org.bouncycastle.wso2:bcprov-jdk15on:${bcprov.wso2.version}
+
+
+ org.bouncycastle.wso2:bcpkix-jdk15on:${bcpkix.wso2.version}
+
+
+ org.bouncycastle.wso2:bcmail-jdk15on:${bcmail.wso2.version}
+
+
+ com.google.code.jscep.wso2:jscep:${jscep.version}
+
+
+ commons-io.wso2:commons-io:${version.commons.io}
+
+
+ commons-lang.wso2:commons-lang:${version.commons.lang}
+
+
+ commons-codec.wso2:commons-codec:${version.commons.codec}
+
+
+
+ org.wso2.carbon.core.server:${carbon.kernel.version}
+
+
+
+
+
+
+
+
diff --git a/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/build.properties b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/build.properties
new file mode 100644
index 0000000000..9c86577d76
--- /dev/null
+++ b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/build.properties
@@ -0,0 +1 @@
+custom = true
diff --git a/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/conf/certificate-config.xml b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/conf/certificate-config.xml
new file mode 100755
index 0000000000..b8202f2a2e
--- /dev/null
+++ b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/conf/certificate-config.xml
@@ -0,0 +1,19 @@
+
+
+
+
+ ${carbon.home}/repository/resources/security/wso2cert.jks
+
+ JKS
+
+ wso2carbon
+
+ cacert
+
+ cacert
+
+ racert
+
+ racert
+
+
diff --git a/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/p2.inf b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/p2.inf
new file mode 100644
index 0000000000..8ee7eea2af
--- /dev/null
+++ b/features/certificate-mgt/org.wso2.carbon.certificate.mgt.server.feature/src/main/resources/p2.inf
@@ -0,0 +1,2 @@
+instructions.configure = \
+org.eclipse.equinox.p2.touchpoint.natives.copy(source:${installFolder}/../features/org.wso2.carbon.certificate.mgt.server_${feature.version}/conf/certificate-config.xml,target:${installFolder}/../../conf/certificate-config.xml,overwrite:true);\
\ No newline at end of file
diff --git a/features/certificate-mgt/pom.xml b/features/certificate-mgt/pom.xml
new file mode 100644
index 0000000000..b34fa8d76e
--- /dev/null
+++ b/features/certificate-mgt/pom.xml
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+ org.wso2.carbon.devicemgt
+ carbon-devicemgt
+ 0.9.2-SNAPSHOT
+ ../../pom.xml
+
+
+ 4.0.0
+ org.wso2.carbon.devicemgt
+ certificate-mgt-feature
+ 0.9.2-SNAPSHOT
+ pom
+ WSO2 Carbon - Certificate Management Feature
+ http://wso2.org
+
+
+ org.wso2.carbon.certificate.mgt.server.feature
+
+
+
diff --git a/pom.xml b/pom.xml
index c44b195add..de9a5a3a90 100644
--- a/pom.xml
+++ b/pom.xml
@@ -37,13 +37,14 @@
components/device-mgt
- components/apimgt-extensions
+ components/apimgt-extensions
components/policy-mgt
+ components/certificate-mgt
components/webapp-authenticator-framework
components/oauth-extensions
features/device-mgt
features/apimgt-extensions
- features/policy-mgt
+ features/policy-mgt
features/webapp-authenticator-framework
features/oauth-extensions
@@ -931,6 +932,39 @@
+
+ org.bouncycastle.wso2
+ bcprov-jdk15on
+ ${bcprov.wso2.version}
+
+
+ org.bouncycastle.wso2
+ bcpkix-jdk15on
+ ${bcpkix.wso2.version}
+
+
+ org.bouncycastle.wso2
+ bcmail-jdk15on
+ ${bcmail.wso2.version}
+
+
+ com.google.code.jscep.wso2
+ jscep
+ ${jscep.version}
+
+
+
+ commons-codec.wso2
+ commons-codec
+ ${version.commons.codec}
+
+
+
+ commons-io.wso2
+ commons-io
+ ${version.commons.io}
+
+
@@ -1184,6 +1218,8 @@
4.4.0
+ 1.4.0.wso2v1
+ 2.4.0.wso2v1
1.4.0
@@ -1193,6 +1229,16 @@
2.5.11
1.1.wso2v1
1.9.0
+
+
+ 1.49.wso2v1
+ 1.49.wso2v1
+ 1.49.wso2v1
+ [1.40.wso2v1, 1.50.0)
+ 1.49.wso2v1
+
+
+ 2.0.2.wso2v2