diff --git a/.pki-core.metadata b/.pki-core.metadata
new file mode 100644
index 0000000..3196f00
--- /dev/null
+++ b/.pki-core.metadata
@@ -0,0 +1 @@
+249584b957fa8bd4478599b66b19bb8f5b1fd1bb SOURCES/pki-core-10.0.5.tar.gz
diff --git a/README.md b/README.md
deleted file mode 100644
index 0e7897f..0000000
--- a/README.md
+++ /dev/null
@@ -1,5 +0,0 @@
-The master branch has no content
- 
-Look at the c7 branch if you are working with CentOS-7, or the c4/c5/c6 branch for CentOS-4, 5 or 6
- 
-If you find this file in a distro specific branch, it means that no content has been checked in yet
diff --git a/SOURCES/0000-Storing-authentication-info-in-session.patch b/SOURCES/0000-Storing-authentication-info-in-session.patch
new file mode 100644
index 0000000..28362b9
--- /dev/null
+++ b/SOURCES/0000-Storing-authentication-info-in-session.patch
@@ -0,0 +1,189 @@
+From 8270ef0b8861bfc6d7a4e5bbe4e6125a221d0680 Mon Sep 17 00:00:00 2001
+From: "Endi S. Dewata" <edewata@redhat.com>
+Date: Mon, 22 Jul 2013 08:50:03 -0400
+Subject: [PATCH 0/6] Storing authentication info in session.
+
+The authenticator configuration has been modified to store the authentication
+info in the session so it can be used by the servlets. An upgrade script has
+been added to update the configuration in existing instances.
+
+The SSLAuthenticatorWithFalback was modified to propagate the configuration
+to the actual authenticator handling the request.
+---
+ base/ca/shared/webapps/ca/META-INF/context.xml     |  4 +-
+ .../cms/tomcat/SSLAuthenticatorWithFallback.java   |  5 ++
+ base/kra/shared/webapps/kra/META-INF/context.xml   |  4 +-
+ base/ocsp/shared/webapps/ocsp/META-INF/context.xml |  4 +-
+ base/server/upgrade/10.0.4/.gitignore              |  4 ++
+ .../upgrade/10.0.5/01-EnableSessionInAuthenticator | 69 ++++++++++++++++++++++
+ base/tks/shared/webapps/tks/META-INF/context.xml   |  4 +-
+ 7 files changed, 90 insertions(+), 4 deletions(-)
+ create mode 100644 base/server/upgrade/10.0.4/.gitignore
+ create mode 100755 base/server/upgrade/10.0.5/01-EnableSessionInAuthenticator
+
+diff --git a/base/ca/shared/webapps/ca/META-INF/context.xml b/base/ca/shared/webapps/ca/META-INF/context.xml
+index 032fd14..e838503 100644
+--- a/base/ca/shared/webapps/ca/META-INF/context.xml
++++ b/base/ca/shared/webapps/ca/META-INF/context.xml
+@@ -28,7 +28,9 @@
+         secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Valve className="com.netscape.cms.tomcat.SSLAuthenticatorWithFallback"
+-        secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
++        alwaysUseSession="true"
++        secureRandomProvider="Mozilla-JSS"
++        secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Realm className="com.netscape.cms.tomcat.ProxyRealm" />
+ 
+diff --git a/base/common/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java b/base/common/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java
+index d1b3dc3..20bf85d 100644
+--- a/base/common/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java
++++ b/base/common/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java
+@@ -140,8 +140,13 @@ public class SSLAuthenticatorWithFallback extends AuthenticatorBase {
+     @Override
+     protected void initInternal() throws LifecycleException {
+         log("Initializing authenticators");
++
+         super.initInternal();
++
++        sslAuthenticator.setAlwaysUseSession(alwaysUseSession);
+         sslAuthenticator.init();
++
++        fallbackAuthenticator.setAlwaysUseSession(alwaysUseSession);
+         fallbackAuthenticator.init();
+     }
+ 
+diff --git a/base/kra/shared/webapps/kra/META-INF/context.xml b/base/kra/shared/webapps/kra/META-INF/context.xml
+index 032fd14..e838503 100644
+--- a/base/kra/shared/webapps/kra/META-INF/context.xml
++++ b/base/kra/shared/webapps/kra/META-INF/context.xml
+@@ -28,7 +28,9 @@
+         secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Valve className="com.netscape.cms.tomcat.SSLAuthenticatorWithFallback"
+-        secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
++        alwaysUseSession="true"
++        secureRandomProvider="Mozilla-JSS"
++        secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Realm className="com.netscape.cms.tomcat.ProxyRealm" />
+ 
+diff --git a/base/ocsp/shared/webapps/ocsp/META-INF/context.xml b/base/ocsp/shared/webapps/ocsp/META-INF/context.xml
+index 032fd14..e838503 100644
+--- a/base/ocsp/shared/webapps/ocsp/META-INF/context.xml
++++ b/base/ocsp/shared/webapps/ocsp/META-INF/context.xml
+@@ -28,7 +28,9 @@
+         secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Valve className="com.netscape.cms.tomcat.SSLAuthenticatorWithFallback"
+-        secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
++        alwaysUseSession="true"
++        secureRandomProvider="Mozilla-JSS"
++        secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Realm className="com.netscape.cms.tomcat.ProxyRealm" />
+ 
+diff --git a/base/server/upgrade/10.0.4/.gitignore b/base/server/upgrade/10.0.4/.gitignore
+new file mode 100644
+index 0000000..5e7d273
+--- /dev/null
++++ b/base/server/upgrade/10.0.4/.gitignore
+@@ -0,0 +1,4 @@
++# Ignore everything in this directory
++*
++# Except this file
++!.gitignore
+diff --git a/base/server/upgrade/10.0.5/01-EnableSessionInAuthenticator b/base/server/upgrade/10.0.5/01-EnableSessionInAuthenticator
+new file mode 100755
+index 0000000..7aee780
+--- /dev/null
++++ b/base/server/upgrade/10.0.5/01-EnableSessionInAuthenticator
+@@ -0,0 +1,69 @@
++#!/usr/bin/python
++# Authors:
++#     Endi S. Dewata <edewata@redhat.com>
++#
++# This program is free software; you can redistribute it and/or modify
++# it under the terms of the GNU General Public License as published by
++# the Free Software Foundation; version 2 of the License.
++#
++# This program is distributed in the hope that it will be useful,
++# but WITHOUT ANY WARRANTY; without even the implied warranty of
++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++# GNU General Public License for more details.
++#
++# You should have received a copy of the GNU General Public License along
++# with this program; if not, write to the Free Software Foundation, Inc.,
++# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++#
++# Copyright (C) 2013 Red Hat, Inc.
++# All rights reserved.
++#
++
++import os
++from lxml import etree
++
++import pki.server.upgrade
++
++
++class EnableSessionInAuthenticator(pki.server.upgrade.PKIServerUpgradeScriptlet):
++
++    def __init__(self):
++
++        self.message = 'Enable session in authenticator'
++
++        self.parser = etree.XMLParser(remove_blank_text=True)
++
++    def upgrade_subsystem(self, instance, subsystem):
++
++        context_xml = os.path.join(
++            instance.base_dir, 'webapps', subsystem.name, 'META-INF', 'context.xml')
++        self.backup(context_xml)
++
++        document = etree.parse(context_xml, self.parser)
++
++        self.enable_session(document)
++
++        with open(context_xml, 'w') as f:
++            f.write(etree.tostring(document, pretty_print=True))
++
++    def enable_session(self, document):
++
++        context = document.getroot()
++        valves = context.findall('Valve')
++        authenticator = None
++
++        # Find existing authenticator
++        for valve in valves:
++            className = valve.get('className')
++            if className != 'com.netscape.cms.tomcat.SSLAuthenticatorWithFallback':
++                continue
++
++            # Found existing authenticator
++            authenticator = valve
++            break
++
++        if authenticator is None:
++            raise Exception('Missing SSLAuthenticatorWithFallback')
++
++        # Update authenticator's attributes
++        authenticator.set('alwaysUseSession', 'true')
+diff --git a/base/tks/shared/webapps/tks/META-INF/context.xml b/base/tks/shared/webapps/tks/META-INF/context.xml
+index 032fd14..e838503 100644
+--- a/base/tks/shared/webapps/tks/META-INF/context.xml
++++ b/base/tks/shared/webapps/tks/META-INF/context.xml
+@@ -28,7 +28,9 @@
+         secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Valve className="com.netscape.cms.tomcat.SSLAuthenticatorWithFallback"
+-        secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
++        alwaysUseSession="true"
++        secureRandomProvider="Mozilla-JSS"
++        secureRandomAlgorithm="pkcs11prng"/>
+ 
+     <Realm className="com.netscape.cms.tomcat.ProxyRealm" />
+ 
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0001-Fixed-error-handling-in-DoUnrevoke-servlet.patch b/SOURCES/0001-Fixed-error-handling-in-DoUnrevoke-servlet.patch
new file mode 100644
index 0000000..f00caae
--- /dev/null
+++ b/SOURCES/0001-Fixed-error-handling-in-DoUnrevoke-servlet.patch
@@ -0,0 +1,46 @@
+From 166a4b291a573d2c9f346a1b1051a2e9b45ff375 Mon Sep 17 00:00:00 2001
+From: "Endi S. Dewata" <edewata@redhat.com>
+Date: Wed, 16 Oct 2013 09:41:12 -0400
+Subject: [PATCH 1/6] Fixed error handling in DoUnrevoke servlet.
+
+The DoUnrevoke servlet has been modified to re-throw the EBaseException
+such that the error message can be returned properly to the client.
+
+Ticket #739
+---
+ base/common/src/com/netscape/cms/servlet/cert/DoUnrevoke.java | 5 +++--
+ 1 file changed, 3 insertions(+), 2 deletions(-)
+
+diff --git a/base/common/src/com/netscape/cms/servlet/cert/DoUnrevoke.java b/base/common/src/com/netscape/cms/servlet/cert/DoUnrevoke.java
+index cca8381..2b30720 100644
+--- a/base/common/src/com/netscape/cms/servlet/cert/DoUnrevoke.java
++++ b/base/common/src/com/netscape/cms/servlet/cert/DoUnrevoke.java
+@@ -40,7 +40,6 @@ import com.netscape.certsrv.authorization.AuthzToken;
+ import com.netscape.certsrv.authorization.EAuthzAccessDenied;
+ import com.netscape.certsrv.base.EBaseException;
+ import com.netscape.certsrv.base.IArgBlock;
+-import com.netscape.certsrv.base.PKIException;
+ import com.netscape.certsrv.ca.ICRLIssuingPoint;
+ import com.netscape.certsrv.ca.ICertificateAuthority;
+ import com.netscape.certsrv.dbs.certdb.CertId;
+@@ -274,7 +273,7 @@ public class DoUnrevoke extends CMSServlet {
+             processor.log(ILogger.LL_FAILURE, "Error " + e);
+             processor.auditChangeRequest(ILogger.FAILURE);
+ 
+-            throw new PKIException(e.getMessage());
++            throw e;
+         }
+ 
+         // change audit processing from "REQUEST" to "REQUEST_PROCESSED"
+@@ -419,6 +418,8 @@ public class DoUnrevoke extends CMSServlet {
+         } catch (EBaseException e) {
+             processor.log(ILogger.LL_FAILURE, "Error " + e);
+             processor.auditChangeRequestProcessed(ILogger.FAILURE);
++
++            throw e;
+         }
+     }
+ 
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0002-Fixed-errors-during-Tomcat-shutdown.patch b/SOURCES/0002-Fixed-errors-during-Tomcat-shutdown.patch
new file mode 100644
index 0000000..0bf5ce9
--- /dev/null
+++ b/SOURCES/0002-Fixed-errors-during-Tomcat-shutdown.patch
@@ -0,0 +1,88 @@
+From 981fdba088b14f975555b9dceb92db614acf631c Mon Sep 17 00:00:00 2001
+From: "Endi S. Dewata" <edewata@redhat.com>
+Date: Fri, 25 Oct 2013 09:28:05 -0400
+Subject: [PATCH 2/6] Fixed errors during Tomcat shutdown.
+
+Previously the CMS.shutdown() was called multiple times during Tomcat
+shutdown, one by CMSStarServlet.destroy() and the other by the shutdown
+hook, causing some errors. The shutdown hook should only be used in a
+standalone application, so it has been moved into CMS.main().
+
+Bugzilla #1018628
+---
+ base/common/src/com/netscape/certsrv/apps/CMS.java      | 17 +++++++++++++++++
+ .../com/netscape/cms/servlet/base/CMSStartServlet.java  |  3 +++
+ .../common/src/com/netscape/cmscore/apps/CMSEngine.java | 16 ----------------
+ 3 files changed, 20 insertions(+), 16 deletions(-)
+
+diff --git a/base/common/src/com/netscape/certsrv/apps/CMS.java b/base/common/src/com/netscape/certsrv/apps/CMS.java
+index 27cddad..fbcf65a 100644
+--- a/base/common/src/com/netscape/certsrv/apps/CMS.java
++++ b/base/common/src/com/netscape/certsrv/apps/CMS.java
+@@ -1661,5 +1661,22 @@ public final class CMS {
+             start(path);
+         } catch (EBaseException e) {
+         }
++
++        // Use shutdown hook in stand-alone application
++        // to catch SIGINT, SIGTERM, or SIGHUP.
++        Runtime.getRuntime().addShutdownHook(new Thread() {
++            public void run() {
++                /*LogDoc
++                *
++                * @phase watchdog check
++                */
++                CMS.getLogger().log(ILogger.EV_SYSTEM,
++                        ILogger.S_OTHER,
++                        ILogger.LL_INFO,
++                        "CMSEngine: Received shutdown signal");
++
++                CMS.shutdown();
++            };
++        });
+     }
+ }
+diff --git a/base/common/src/com/netscape/cms/servlet/base/CMSStartServlet.java b/base/common/src/com/netscape/cms/servlet/base/CMSStartServlet.java
+index e00f2bd..34bbb2e 100644
+--- a/base/common/src/com/netscape/cms/servlet/base/CMSStartServlet.java
++++ b/base/common/src/com/netscape/cms/servlet/base/CMSStartServlet.java
+@@ -120,6 +120,9 @@ public class CMSStartServlet extends HttpServlet {
+         return "CMS startup servlet";
+     }
+ 
++    /**
++     * This method will be called when Tomcat is shutdown.
++     */
+     public void destroy() {
+         CMS.shutdown();
+         super.destroy();
+diff --git a/base/common/src/com/netscape/cmscore/apps/CMSEngine.java b/base/common/src/com/netscape/cmscore/apps/CMSEngine.java
+index 834918a..482b5ea 100644
+--- a/base/common/src/com/netscape/cmscore/apps/CMSEngine.java
++++ b/base/common/src/com/netscape/cmscore/apps/CMSEngine.java
+@@ -262,22 +262,6 @@ public class CMSEngine implements ICMSEngine {
+      * private constructor.
+      */
+     public CMSEngine() {
+-
+-        // Shutdown on SIGINT, SIGTERM, or SIGHUP.
+-        Runtime.getRuntime().addShutdownHook(new Thread() {
+-            public void run() {
+-                /*LogDoc
+-                *
+-                * @phase watchdog check
+-                */
+-                getLogger().log(ILogger.EV_SYSTEM,
+-                        ILogger.S_OTHER,
+-                        ILogger.LL_INFO,
+-                        "OS: Received shutdown signal");
+-
+-                shutdown();
+-            };
+-        });
+     }
+ 
+     /**
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0003-Fixed-logic-for-setting-admin-cert-signing-algorithm.patch b/SOURCES/0003-Fixed-logic-for-setting-admin-cert-signing-algorithm.patch
new file mode 100644
index 0000000..2b151d1
--- /dev/null
+++ b/SOURCES/0003-Fixed-logic-for-setting-admin-cert-signing-algorithm.patch
@@ -0,0 +1,199 @@
+From fb9acc2c02ad35443eb8b6ac0f2279dddd9449ab Mon Sep 17 00:00:00 2001
+From: Ade Lee <alee@redhat.com>
+Date: Wed, 30 Oct 2013 15:50:28 -0400
+Subject: [PATCH 3/6] Fixed logic for setting admin cert signing algorithm
+
+Should now be SHA256 by default.
+Bugzilla BZ 1024445
+---
+ base/ca/shared/conf/CS.cfg.in                      |   1 +
+ base/ca/shared/profiles/ca/caAdminCert.cfg         |   2 +-
+ .../com/netscape/cms/servlet/csadmin/CertUtil.java | 123 +++++++++++++--------
+ 3 files changed, 81 insertions(+), 45 deletions(-)
+
+diff --git a/base/ca/shared/conf/CS.cfg.in b/base/ca/shared/conf/CS.cfg.in
+index c1acc57..cca5209 100644
+--- a/base/ca/shared/conf/CS.cfg.in
++++ b/base/ca/shared/conf/CS.cfg.in
+@@ -660,6 +660,7 @@ ca.notification.requestInQ.senderEmail=
+ ca.ocsp_signing.cacertnickname=ocspSigningCert cert-[PKI_INSTANCE_ID]
+ ca.ocsp_signing.defaultSigningAlgorithm=SHA256withRSA
+ ca.ocsp_signing.tokenname=internal
++ca.profiles.defaultSigningAlgsAllowed==SHA256withRSA,SHA1withRSA,SHA512withRSA,MD5withRSA,MD2withRSA,SHA1withDSA,SHA256withEC,SHA1withEC,SHA384withEC,SHA512withEC
+ ca.publish.createOwnDNEntry=false
+ ca.publish.queue.enable=true
+ ca.publish.queue.maxNumberOfThreads=3
+diff --git a/base/ca/shared/profiles/ca/caAdminCert.cfg b/base/ca/shared/profiles/ca/caAdminCert.cfg
+index c44079a..cd29703 100644
+--- a/base/ca/shared/profiles/ca/caAdminCert.cfg
++++ b/base/ca/shared/profiles/ca/caAdminCert.cfg
+@@ -81,7 +81,7 @@ policyset.adminCertSet.7.default.params.exKeyUsageCritical=false
+ policyset.adminCertSet.7.default.params.exKeyUsageOIDs=1.3.6.1.5.5.7.3.2,1.3.6.1.5.5.7.3.4
+ policyset.adminCertSet.8.constraint.class_id=signingAlgConstraintImpl
+ policyset.adminCertSet.8.constraint.name=No Constraint
+-policyset.adminCertSet.8.constraint.params.signingAlgsAllowed=SHA1withRSA,SHA256withRSA,SHA512withRSA,MD5withRSA,MD2withRSA,SHA1withDSA,SHA1withEC,SHA256withEC,SHA384withEC,SHA512withEC
++policyset.adminCertSet.8.constraint.params.signingAlgsAllowed=SHA256withRSA,SHA1withRSA,SHA512withRSA,MD5withRSA,MD2withRSA,SHA1withDSA,SHA256withEC,SHA1withEC,SHA384withEC,SHA512withEC
+ policyset.adminCertSet.8.default.class_id=signingAlgDefaultImpl
+ policyset.adminCertSet.8.default.name=Signing Alg
+ policyset.adminCertSet.8.default.params.signingAlg=-
+diff --git a/base/common/src/com/netscape/cms/servlet/csadmin/CertUtil.java b/base/common/src/com/netscape/cms/servlet/csadmin/CertUtil.java
+index 789c0aa..1936b2c 100644
+--- a/base/common/src/com/netscape/cms/servlet/csadmin/CertUtil.java
++++ b/base/common/src/com/netscape/cms/servlet/csadmin/CertUtil.java
+@@ -17,14 +17,15 @@
+ // --- END COPYRIGHT BLOCK ---
+ package com.netscape.cms.servlet.csadmin;
+ 
+-import java.io.BufferedReader;
+ import java.io.ByteArrayInputStream;
+-import java.io.DataInputStream;
+ import java.io.FileInputStream;
++import java.io.FileNotFoundException;
+ import java.io.IOException;
+-import java.io.InputStreamReader;
+ import java.math.BigInteger;
+ import java.util.Date;
++import java.util.Iterator;
++import java.util.Properties;
++import java.util.Set;
+ 
+ import javax.servlet.http.HttpServletResponse;
+ 
+@@ -36,6 +37,8 @@ import netscape.security.x509.X509CertImpl;
+ import netscape.security.x509.X509CertInfo;
+ import netscape.security.x509.X509Key;
+ 
++import org.apache.commons.lang.ArrayUtils;
++import org.apache.commons.lang.StringUtils;
+ import org.apache.velocity.context.Context;
+ import org.mozilla.jss.CryptoManager;
+ import org.mozilla.jss.crypto.PrivateKey;
+@@ -271,52 +274,84 @@ public class CertUtil {
+     }
+ 
+     /**
+-     * reads from the admin cert profile caAdminCert.profile and takes the first
+-     * entry in the list of allowed algorithms. Users that wish a different algorithm
+-     * can specify it in the profile using default.params.signingAlg
++     * reads from the admin cert profile caAdminCert.profile and determines the algorithm as follows:
++     *
++     * 1.  First gets list of allowed algorithms from profile (constraint.params.signingAlgsAllowed)
++     *     If entry does not exist, uses entry "ca.profiles.defaultSigningAlgsAllowed" from CS.cfg
++     *     If that entry does not exist, uses basic default
++     *
++     * 2.  Gets default.params.signingAlg from profile.
++     *     If entry does not exist or equals "-", selects first algorithm in allowed algorithm list 
++     *     that matches CA signing key type
++     *     Otherwise returns entry if it matches signing CA key type.
++     *
++     * @throws EBaseException
++     * @throws IOException
++     * @throws FileNotFoundException
+      */
+ 
+-    public static String getAdminProfileAlgorithm(IConfigStore config) {
+-        String algorithm = "SHA256withRSA";
+-        try {
+-            String caSigningKeyType = config.getString("preop.cert.signing.keytype", "rsa");
+-            String pfile = config.getString("profile.caAdminCert.config");
+-            FileInputStream fis = new FileInputStream(pfile);
+-            DataInputStream in = new DataInputStream(fis);
+-            BufferedReader br = new BufferedReader(new InputStreamReader(in));
+-
+-            String strLine;
+-            while ((strLine = br.readLine()) != null) {
+-                String marker2 = "default.params.signingAlg=";
+-                int indx = strLine.indexOf(marker2);
+-                if (indx != -1) {
+-                    String alg = strLine.substring(indx + marker2.length());
+-                    if ((alg.length() > 0) && (!alg.equals("-"))) {
+-                        algorithm = alg;
+-                        break;
+-                    }
+-                    ;
+-                }
+-                ;
+-
+-                String marker = "signingAlgsAllowed=";
+-                indx = strLine.indexOf(marker);
+-                if (indx != -1) {
+-                    String[] algs = strLine.substring(indx + marker.length()).split(",");
+-                    for (int i = 0; i < algs.length; i++) {
+-                        if ((caSigningKeyType.equals("rsa") && (algs[i].indexOf("RSA") != -1)) ||
+-                                (caSigningKeyType.equals("ecc") && (algs[i].indexOf("EC") != -1))) {
+-                            algorithm = algs[i];
+-                            break;
+-                        }
+-                    }
++    public static String getAdminProfileAlgorithm(IConfigStore config) throws EBaseException, FileNotFoundException,
++            IOException {
++        String caSigningKeyType = config.getString("preop.cert.signing.keytype", "rsa");
++        String pfile = config.getString("profile.caAdminCert.config");
++        Properties props = new Properties();
++        props.load(new FileInputStream(pfile));
++
++        Set<String> keys = props.stringPropertyNames();
++        Iterator<String> iter = keys.iterator();
++        String defaultAlg = null;
++        String[] algsAllowed = null;
++
++        while (iter.hasNext()) {
++            String key = iter.next();
++            if (key.endsWith("default.params.signingAlg")) {
++                defaultAlg = props.getProperty(key);
++            }
++            if (key.endsWith("constraint.params.signingAlgsAllowed")) {
++                algsAllowed = StringUtils.split(props.getProperty(key), ",");
++            }
++        }
++
++        if (algsAllowed == null) { //algsAllowed not defined in profile, use a global setting
++            algsAllowed = StringUtils.split(config.getString("ca.profiles.defaultSigningAlgsAllowed",
++                    "SHA256withRSA,SHA256withEC,SHA1withDSA"), ",");
++        }
++
++        if (ArrayUtils.isEmpty(algsAllowed)) {
++            throw new EBaseException("No allowed signing algorithms defined.");
++        }
++
++        if (StringUtils.isNotEmpty(defaultAlg) && !defaultAlg.equals("-")) {
++            // check if the defined default algorithm is valid
++            if (! isAlgorithmValid(caSigningKeyType, defaultAlg)) {
++                throw new EBaseException("Administrator cert cannot be signed by specfied algorithm." +
++                                         "Algorithm incompatible with signing key");
++            }
++
++            for (String alg : algsAllowed) {
++                if (defaultAlg.trim().equals(alg.trim())) {
++                    return defaultAlg;
+                 }
+             }
+-            in.close();
+-        } catch (Exception e) {
+-            CMS.debug("getAdminProfleAlgorithm: exception: " + e);
++            throw new EBaseException(
++                    "Administrator Certificate cannot be signed by the specified algorithm " +
++                    "as it is not one of the allowed signing algorithms.  Check the admin cert profile.");
+         }
+-        return algorithm;
++
++        // no algorithm specified.  Pick the first allowed algorithm.
++        for (String alg : algsAllowed) {
++            if (isAlgorithmValid(caSigningKeyType, alg)) return alg;
++        }
++
++        throw new EBaseException(
++                "Admin certificate cannot be signed by any of the specified possible algorithms." +
++                "Algorithm is incompatible with the CA signing key type" );
++    }
++
++    private static boolean isAlgorithmValid(String signingKeyType, String algorithm) {
++       return ((signingKeyType.equals("rsa") && algorithm.contains("RSA")) ||
++               (signingKeyType.equals("ecc") && algorithm.contains("EC"))  ||
++               (signingKeyType.equals("dsa") && algorithm.contains("DSA")));
+     }
+ 
+     public static X509CertImpl createLocalCert(IConfigStore config, X509Key x509key,
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0004-Backup-upgrade-tracker.patch b/SOURCES/0004-Backup-upgrade-tracker.patch
new file mode 100644
index 0000000..7cbb6ec
--- /dev/null
+++ b/SOURCES/0004-Backup-upgrade-tracker.patch
@@ -0,0 +1,93 @@
+From 75bf654f1023e36f67b27d8e47e077400c072b84 Mon Sep 17 00:00:00 2001
+From: "Endi S. Dewata" <edewata@redhat.com>
+Date: Mon, 28 Oct 2013 17:21:59 -0400
+Subject: [PATCH 4/6] Backup upgrade tracker.
+
+The upgrade framework has been modified to backup the files used
+to track the upgrade progress. If the tracker file is also modified
+by the upgrade scriptlet, it will only keep the initial backup
+(before any modifications were made).
+
+Ticket #763
+---
+ base/common/python/pki/upgrade.py        | 8 ++++++--
+ base/common/python/pki/util.py           | 6 +++++-
+ base/server/python/pki/server/upgrade.py | 1 +
+ 3 files changed, 12 insertions(+), 3 deletions(-)
+
+diff --git a/base/common/python/pki/upgrade.py b/base/common/python/pki/upgrade.py
+index bd78ec9..7e48180 100644
+--- a/base/common/python/pki/upgrade.py
++++ b/base/common/python/pki/upgrade.py
+@@ -110,6 +110,7 @@ class PKIUpgradeTracker(object):
+         index_key='PKI_UPGRADE_INDEX'):
+ 
+         self.name = name
++        self.filename = filename
+ 
+         self.version_key = version_key
+         self.index_key = index_key
+@@ -267,6 +268,7 @@ class PKIUpgradeScriptlet(object):
+         # in this version, update the tracker version.
+ 
+         tracker = self.upgrader.get_tracker()
++        self.backup(tracker.filename)
+ 
+         if not self.last:
+             tracker.set_index(self.index)
+@@ -389,7 +391,8 @@ class PKIUpgradeScriptlet(object):
+ 
+             if os.path.isfile(path):
+                 if verbose: print 'Saving ' + path
+-                pki.util.copyfile(path, dest)
++                # do not overwrite initial backup
++                pki.util.copyfile(path, dest, overwrite=False)
+ 
+             else:
+                 for sourcepath, _, filenames in os.walk(path):
+@@ -405,7 +408,8 @@ class PKIUpgradeScriptlet(object):
+                         targetfile = os.path.join(destpath, filename)
+ 
+                         if verbose: print 'Saving ' + sourcefile
+-                        pki.util.copyfile(sourcefile, targetfile)
++                        # do not overwrite initial backup
++                        pki.util.copyfile(sourcefile, targetfile, overwrite=False)
+ 
+         else:
+ 
+diff --git a/base/common/python/pki/util.py b/base/common/python/pki/util.py
+index 4d25390..62aec2c 100644
+--- a/base/common/python/pki/util.py
++++ b/base/common/python/pki/util.py
+@@ -53,11 +53,15 @@ def copy(source, dest):
+                 targetfile = os.path.join(destpath, filename)
+                 copyfile(sourcefile, targetfile)
+ 
+-def copyfile(source, dest):
++def copyfile(source, dest, overwrite=True):
+     """
+     Copy a file or link while preserving its attributes.
+     """
+ 
++    # if dest already exists and not overwriting, do nothing
++    if os.path.exists(dest) and not overwrite:
++        return
++
+     if os.path.islink(source):
+         target = os.readlink(source)
+         os.symlink(target, dest)
+diff --git a/base/server/python/pki/server/upgrade.py b/base/server/python/pki/server/upgrade.py
+index 940dbe4..ee0dfed 100644
+--- a/base/server/python/pki/server/upgrade.py
++++ b/base/server/python/pki/server/upgrade.py
+@@ -60,6 +60,7 @@ class PKIServerUpgradeScriptlet(pki.upgrade.PKIUpgradeScriptlet):
+         # in this version, update the tracker version.
+ 
+         tracker = self.upgrader.get_tracker(instance, subsystem)
++        self.backup(tracker.filename)
+ 
+         if not self.last:
+             tracker.set_index(self.index)
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0005-Added-CLI-command-aliases.patch b/SOURCES/0005-Added-CLI-command-aliases.patch
new file mode 100644
index 0000000..2192344
--- /dev/null
+++ b/SOURCES/0005-Added-CLI-command-aliases.patch
@@ -0,0 +1,2554 @@
+From 7efc9fbd120885109eb19bfc98d6109a98751b25 Mon Sep 17 00:00:00 2001
+From: "Endi S. Dewata" <edewata@redhat.com>
+Date: Tue, 29 Oct 2013 10:56:15 -0400
+Subject: [PATCH 5/6] Added CLI command aliases.
+
+New aliases for some CLI commands have been added for consistency:
+
+* client-cert-find       -> client-find-cert
+* client-cert-import     -> client-import-cert
+* client-cert-del        -> client-remove-cert
+* group-member-add       -> group-add-member
+* group-member-find      -> group-find-member
+* group-member-show      -> group-show-member
+* group-member-del       -> group-remove-member
+* user-cert-add          -> user-add-cert
+* user-cert-find         -> user-find-cert
+* user-cert-show         -> user-show-cert
+* user-cert-del          -> user-remove-cert
+* user-membership-add    -> user-add-membership
+* user-membership-find   -> user-find-membership
+* user-membership-show   -> user-show-membership
+* user-membership-del    -> user-remove-membership
+
+The original commands will continue to work as before.
+---
+ base/java-tools/man/man1/pki.1                     |   4 +-
+ .../src/com/netscape/cmstools/cli/CLI.java         |  55 +++++++++
+ .../com/netscape/cmstools/client/ClientCLI.java    |  24 +---
+ .../cmstools/client/ClientCertFindCLI.java         |  89 +++++++++++++++
+ .../cmstools/client/ClientCertImportCLI.java       | 124 +++++++++++++++++++++
+ .../cmstools/client/ClientCertRemoveCLI.java       |  70 ++++++++++++
+ .../cmstools/client/ClientFindCertCLI.java         |  60 +---------
+ .../cmstools/client/ClientImportCertCLI.java       |  95 +---------------
+ .../cmstools/client/ClientRemoveCertCLI.java       |  41 +------
+ .../netscape/cmstools/group/GroupAddMemberCLI.java |  32 +-----
+ .../src/com/netscape/cmstools/group/GroupCLI.java  |  23 +---
+ .../cmstools/group/GroupFindMemberCLI.java         |  79 +------------
+ .../netscape/cmstools/group/GroupMemberAddCLI.java |  61 ++++++++++
+ .../cmstools/group/GroupMemberFindCLI.java         | 108 ++++++++++++++++++
+ .../cmstools/group/GroupMemberRemoveCLI.java       |  58 ++++++++++
+ .../cmstools/group/GroupMemberShowCLI.java         |  61 ++++++++++
+ .../cmstools/group/GroupRemoveMemberCLI.java       |  29 +----
+ .../cmstools/group/GroupShowMemberCLI.java         |  32 +-----
+ .../com/netscape/cmstools/user/UserAddCertCLI.java |  72 +-----------
+ .../cmstools/user/UserAddMembershipCLI.java        |  32 +-----
+ .../src/com/netscape/cmstools/user/UserCLI.java    |  28 ++---
+ .../com/netscape/cmstools/user/UserCertAddCLI.java | 105 +++++++++++++++++
+ .../netscape/cmstools/user/UserCertFindCLI.java    | 108 ++++++++++++++++++
+ .../netscape/cmstools/user/UserCertRemoveCLI.java  |  65 +++++++++++
+ .../netscape/cmstools/user/UserCertShowCLI.java    | 100 +++++++++++++++++
+ .../netscape/cmstools/user/UserFindCertCLI.java    |  79 +------------
+ .../cmstools/user/UserFindMembershipCLI.java       |  79 +------------
+ .../cmstools/user/UserMembershipAddCLI.java        |  61 ++++++++++
+ .../cmstools/user/UserMembershipFindCLI.java       | 108 ++++++++++++++++++
+ .../cmstools/user/UserMembershipRemoveCLI.java     |  58 ++++++++++
+ .../netscape/cmstools/user/UserRemoveCertCLI.java  |  35 +-----
+ .../cmstools/user/UserRemoveMembershipCLI.java     |  29 +----
+ .../netscape/cmstools/user/UserShowCertCLI.java    |  71 +-----------
+ 33 files changed, 1290 insertions(+), 785 deletions(-)
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/client/ClientCertFindCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/client/ClientCertImportCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/client/ClientCertRemoveCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/group/GroupMemberAddCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/group/GroupMemberFindCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/group/GroupMemberRemoveCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/group/GroupMemberShowCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserCertAddCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserCertFindCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserCertRemoveCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserCertShowCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserMembershipAddCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserMembershipFindCLI.java
+ create mode 100644 base/java-tools/src/com/netscape/cmstools/user/UserMembershipRemoveCLI.java
+
+diff --git a/base/java-tools/man/man1/pki.1 b/base/java-tools/man/man1/pki.1
+index ec0af7c..b3c5356 100644
+--- a/base/java-tools/man/man1/pki.1
++++ b/base/java-tools/man/man1/pki.1
+@@ -199,11 +199,11 @@ To delete a group:
+ 
+ To add a user to a group:
+ 
+-.B pki <admin authentication> group-add-member <group ID> <Member ID>
++.B pki <admin authentication> group-member-add <group ID> <Member ID>
+ 
+ To delete a user from a group:
+ 
+-.B pki <admin authentication> group-remove-member <group ID> <Member ID>
++.B pki <admin authentication> group-member-del <group ID> <Member ID>
+ 
+ .\".SS Key Management Commands
+ .\"\fBpki\fP can be used with a KRA to find specific keys and key requests.  This will be documented in more detail at a later time.
+diff --git a/base/java-tools/src/com/netscape/cmstools/cli/CLI.java b/base/java-tools/src/com/netscape/cmstools/cli/CLI.java
+index a1fc4f7..c9c3606 100644
+--- a/base/java-tools/src/com/netscape/cmstools/cli/CLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/cli/CLI.java
+@@ -18,6 +18,8 @@
+ 
+ package com.netscape.cmstools.cli;
+ 
++import java.util.ArrayList;
++import java.util.Collection;
+ import java.util.LinkedHashMap;
+ import java.util.Map;
+ 
+@@ -25,6 +27,7 @@ import org.apache.commons.cli.CommandLineParser;
+ import org.apache.commons.cli.HelpFormatter;
+ import org.apache.commons.cli.Options;
+ import org.apache.commons.cli.PosixParser;
++import org.apache.commons.lang.StringUtils;
+ 
+ 
+ /**
+@@ -64,6 +67,10 @@ public class CLI {
+         this.description = description;
+     }
+ 
++    public boolean isDeprecated() {
++        return getClass().getAnnotation(Deprecated.class) != null;
++    }
++
+     public void addModule(CLI module) {
+         modules.put(module.getName(), module);
+     }
+@@ -75,7 +82,55 @@ public class CLI {
+     public void execute(String[] args) throws Exception {
+     }
+ 
++    public Collection<CLI> getDeprecatedModules() {
++        Collection<CLI> list = new ArrayList<CLI>();
++        for (CLI module : modules.values()) {
++            if (!module.isDeprecated()) continue;
++            list.add(module);
++        }
++        return list;
++    }
++
+     public void printHelp() {
++
++        int leftPadding = 1;
++        int rightPadding = 25;
++
++        System.out.println("Commands:");
++
++        for (CLI module : modules.values()) {
++            if (module.isDeprecated()) continue;
++
++            String label = name + "-" + module.getName();
++
++            int padding = rightPadding - leftPadding - label.length();
++            if (padding < 1)
++                padding = 1;
++
++            System.out.print(StringUtils.repeat(" ", leftPadding));
++            System.out.print(label);
++            System.out.print(StringUtils.repeat(" ", padding));
++            System.out.println(module.getDescription());
++        }
++
++        Collection<CLI> deprecatedModules = getDeprecatedModules();
++
++        if (!deprecatedModules.isEmpty()) {
++            System.out.println();
++            System.out.println("Deprecated:");
++
++            for (CLI module : deprecatedModules) {
++                String label = name+"-"+module.getName();
++
++                int padding = rightPadding - leftPadding - label.length();
++                if (padding < 1) padding = 1;
++
++                System.out.print(StringUtils.repeat(" ", leftPadding));
++                System.out.print(label);
++                System.out.print(StringUtils.repeat(" ", padding));
++                System.out.println(module.getDescription());
++            }
++        }
+     }
+ 
+     public static boolean isVerbose() {
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientCLI.java
+index 34d09f3..147b4d6 100644
+--- a/base/java-tools/src/com/netscape/cmstools/client/ClientCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientCLI.java
+@@ -20,7 +20,6 @@ package com.netscape.cmstools.client;
+ 
+ import java.util.Arrays;
+ 
+-import org.apache.commons.lang.StringUtils;
+ import org.mozilla.jss.crypto.X509Certificate;
+ 
+ import com.netscape.certsrv.dbs.certdb.CertId;
+@@ -41,27 +40,10 @@ public class ClientCLI extends CLI {
+         addModule(new ClientFindCertCLI(this));
+         addModule(new ClientImportCertCLI(this));
+         addModule(new ClientRemoveCertCLI(this));
+-    }
+-
+-    public void printHelp() {
+-
+-        System.out.println("Commands:");
+-
+-        int leftPadding = 1;
+-        int rightPadding = 25;
+ 
+-        for (CLI module : modules.values()) {
+-            String label = name + "-" + module.getName();
+-
+-            int padding = rightPadding - leftPadding - label.length();
+-            if (padding < 1)
+-                padding = 1;
+-
+-            System.out.print(StringUtils.repeat(" ", leftPadding));
+-            System.out.print(label);
+-            System.out.print(StringUtils.repeat(" ", padding));
+-            System.out.println(module.getDescription());
+-        }
++        addModule(new ClientCertFindCLI(this));
++        addModule(new ClientCertImportCLI(this));
++        addModule(new ClientCertRemoveCLI(this));
+     }
+ 
+     public void execute(String[] args) throws Exception {
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientCertFindCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientCertFindCLI.java
+new file mode 100644
+index 0000000..c4e1aca
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientCertFindCLI.java
+@@ -0,0 +1,89 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.client;
++
++import org.apache.commons.cli.CommandLine;
++import org.mozilla.jss.crypto.X509Certificate;
++
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class ClientCertFindCLI extends CLI {
++
++    public ClientCLI parent;
++
++    public ClientCertFindCLI(String name, ClientCLI parent) {
++        super(name, "Find certificates in client security database");
++        this.parent = parent;
++    }
++
++    public ClientCertFindCLI(ClientCLI parent) {
++        this("cert-find", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " [OPTIONS]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        options.addOption(null, "ca", false, "Find CA certificates only");
++
++        CommandLine cmd = null;
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        X509Certificate[] certs;
++        if (cmd.hasOption("ca")) {
++            certs = parent.parent.client.getCACerts();
++        } else {
++            certs = parent.parent.client.getCerts();
++        }
++
++        if (certs == null || certs.length == 0) {
++            MainCLI.printMessage("No certificates found");
++            System.exit(0); // valid result
++        }
++
++        MainCLI.printMessage(certs.length + " certificate(s) found");
++
++        boolean first = true;
++
++        for (X509Certificate cert : certs) {
++            if (first) {
++                first = false;
++            } else {
++                System.out.println();
++            }
++
++            ClientCLI.printCertInfo(cert);
++        }
++
++        MainCLI.printMessage("Number of entries returned " + certs.length);
++   }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientCertImportCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientCertImportCLI.java
+new file mode 100644
+index 0000000..ffd68d9
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientCertImportCLI.java
+@@ -0,0 +1,124 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.client;
++
++import java.io.File;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++import org.apache.commons.io.FileUtils;
++import org.mozilla.jss.crypto.X509Certificate;
++
++import com.netscape.certsrv.client.ClientConfig;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class ClientCertImportCLI extends CLI {
++
++    public ClientCLI parent;
++
++    public ClientCertImportCLI(String name, ClientCLI parent) {
++        super(name, "Import certificate into client security database");
++        this.parent = parent;
++    }
++
++    public ClientCertImportCLI(ClientCLI parent) {
++        this("cert-import", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " [OPTIONS]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "cert", true, "Import certificate file");
++        option.setArgName("path");
++        options.addOption(option);
++
++        option = new Option(null, "ca-cert", true, "Import CA certificate file");
++        option.setArgName("path");
++        options.addOption(option);
++
++        options.addOption(null, "ca-server", false, "Import CA certificate from CA server");
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        byte[] bytes = null;
++        X509Certificate cert = null;
++
++        String certPath = cmd.getOptionValue("cert");
++        String caCertPath = cmd.getOptionValue("ca-cert");
++        boolean importFromCAServer = cmd.hasOption("ca-server");
++
++        boolean isCACert = false;
++
++        // load the certificate
++        if (certPath != null) {
++            if (verbose) System.out.println("Loading certificate from " + certPath + ".");
++            bytes = FileUtils.readFileToByteArray(new File(certPath));
++
++
++        } else if (caCertPath != null) {
++            if (verbose) System.out.println("Loading CA certificate from " + caCertPath + ".");
++            bytes = FileUtils.readFileToByteArray(new File(caCertPath));
++
++            isCACert = true;
++
++        } else if (importFromCAServer) {
++            ClientConfig config = parent.parent.config;
++            String caServerURI = "http://" + config.getServerURI().getHost() + ":8080/ca";
++
++            if (verbose) System.out.println("Downloading CA certificate from " + caServerURI + ".");
++            bytes = parent.parent.client.downloadCACertChain(caServerURI);
++
++            isCACert = true;
++
++        } else {
++            System.err.println("Error: Missing certificate to import");
++            printHelp();
++            System.exit(1);
++        }
++
++        // import the certificate
++        if (isCACert) {
++            if (verbose) System.out.println("Importing CA certificate.");
++            cert = parent.parent.client.importCACertPackage(bytes);
++
++        } else {
++            if (verbose) System.out.println("Importing certificate.");
++            cert = parent.parent.client.importCertPackage(bytes, parent.parent.client.config.getCertNickname());
++        }
++
++        MainCLI.printMessage("Imported certificate \"" + cert.getNickname() + "\"");
++        ClientCLI.printCertInfo(cert);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientCertRemoveCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientCertRemoveCLI.java
+new file mode 100644
+index 0000000..2c05446
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientCertRemoveCLI.java
+@@ -0,0 +1,70 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.client;
++
++import org.apache.commons.cli.CommandLine;
++
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class ClientCertRemoveCLI extends CLI {
++
++    public ClientCLI parent;
++
++    public ClientCertRemoveCLI(String name, ClientCLI parent) {
++        super(name, "Remove certificate from client security database");
++        this.parent = parent;
++    }
++
++    public ClientCertRemoveCLI(ClientCLI parent) {
++        this("cert-del", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <nickname>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        CommandLine cmd = null;
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 1) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String nickname = cmdArgs[0];
++        parent.parent.client.removeCert(nickname);
++
++        MainCLI.printMessage("Removed certificate \"" + nickname + "\"");
++   }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientFindCertCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientFindCertCLI.java
+index 80690b7..379e95a 100644
+--- a/base/java-tools/src/com/netscape/cmstools/client/ClientFindCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientFindCertCLI.java
+@@ -18,68 +18,14 @@
+ 
+ package com.netscape.cmstools.client;
+ 
+-import org.apache.commons.cli.CommandLine;
+-import org.mozilla.jss.crypto.X509Certificate;
+-
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class ClientFindCertCLI extends CLI {
+-
+-    public ClientCLI parent;
++@Deprecated
++public class ClientFindCertCLI extends ClientCertFindCLI {
+ 
+     public ClientFindCertCLI(ClientCLI parent) {
+-        super("find-cert", "Find certificates in client security database");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " [OPTIONS]", options);
++        super("find-cert", parent);
+     }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        options.addOption(null, "ca", false, "Find CA certificates only");
+-
+-        CommandLine cmd = null;
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        X509Certificate[] certs;
+-        if (cmd.hasOption("ca")) {
+-            certs = parent.parent.client.getCACerts();
+-        } else {
+-            certs = parent.parent.client.getCerts();
+-        }
+-
+-        if (certs == null || certs.length == 0) {
+-            MainCLI.printMessage("No certificates found");
+-            System.exit(0); // valid result
+-        }
+-
+-        MainCLI.printMessage(certs.length + " certificate(s) found");
+-
+-        boolean first = true;
+-
+-        for (X509Certificate cert : certs) {
+-            if (first) {
+-                first = false;
+-            } else {
+-                System.out.println();
+-            }
+-
+-            ClientCLI.printCertInfo(cert);
+-        }
+-
+-        MainCLI.printMessage("Number of entries returned " + certs.length);
+-   }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientImportCertCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientImportCertCLI.java
+index e89f954..db0736d 100644
+--- a/base/java-tools/src/com/netscape/cmstools/client/ClientImportCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientImportCertCLI.java
+@@ -18,103 +18,14 @@
+ 
+ package com.netscape.cmstools.client;
+ 
+-import java.io.File;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-import org.apache.commons.io.FileUtils;
+-import org.mozilla.jss.crypto.X509Certificate;
+-
+-import com.netscape.certsrv.client.ClientConfig;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class ClientImportCertCLI extends CLI {
+-
+-    public ClientCLI parent;
++@Deprecated
++public class ClientImportCertCLI extends ClientCertImportCLI {
+ 
+     public ClientImportCertCLI(ClientCLI parent) {
+-        super("import-cert", "Import certificate into client security database");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " [OPTIONS]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "cert", true, "Import certificate file");
+-        option.setArgName("path");
+-        options.addOption(option);
+-
+-        option = new Option(null, "ca-cert", true, "Import CA certificate file");
+-        option.setArgName("path");
+-        options.addOption(option);
+-
+-        options.addOption(null, "ca-server", false, "Import CA certificate from CA server");
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        byte[] bytes = null;
+-        X509Certificate cert = null;
+-
+-        String certPath = cmd.getOptionValue("cert");
+-        String caCertPath = cmd.getOptionValue("ca-cert");
+-        boolean importFromCAServer = cmd.hasOption("ca-server");
+-
+-        boolean isCACert = false;
+-
+-        // load the certificate
+-        if (certPath != null) {
+-            if (verbose) System.out.println("Loading certificate from " + certPath + ".");
+-            bytes = FileUtils.readFileToByteArray(new File(certPath));
+-
+-
+-        } else if (caCertPath != null) {
+-            if (verbose) System.out.println("Loading CA certificate from " + caCertPath + ".");
+-            bytes = FileUtils.readFileToByteArray(new File(caCertPath));
+-
+-            isCACert = true;
+-
+-        } else if (importFromCAServer) {
+-            ClientConfig config = parent.parent.config;
+-            String caServerURI = "http://" + config.getServerURI().getHost() + ":8080/ca";
+-
+-            if (verbose) System.out.println("Downloading CA certificate from " + caServerURI + ".");
+-            bytes = parent.parent.client.downloadCACertChain(caServerURI);
+-
+-            isCACert = true;
+-
+-        } else {
+-            System.err.println("Error: Missing certificate to import");
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        // import the certificate
+-        if (isCACert) {
+-            if (verbose) System.out.println("Importing CA certificate.");
+-            cert = parent.parent.client.importCACertPackage(bytes);
+-
+-        } else {
+-            if (verbose) System.out.println("Importing certificate.");
+-            cert = parent.parent.client.importCertPackage(bytes, parent.parent.client.config.getCertNickname());
+-        }
+-
+-        MainCLI.printMessage("Imported certificate \"" + cert.getNickname() + "\"");
+-        ClientCLI.printCertInfo(cert);
++        super("import-cert", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/client/ClientRemoveCertCLI.java b/base/java-tools/src/com/netscape/cmstools/client/ClientRemoveCertCLI.java
+index fab4296..2b217ac 100644
+--- a/base/java-tools/src/com/netscape/cmstools/client/ClientRemoveCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/client/ClientRemoveCertCLI.java
+@@ -18,49 +18,14 @@
+ 
+ package com.netscape.cmstools.client;
+ 
+-import org.apache.commons.cli.CommandLine;
+-
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class ClientRemoveCertCLI extends CLI {
+-
+-    public ClientCLI parent;
++@Deprecated
++public class ClientRemoveCertCLI extends ClientCertRemoveCLI {
+ 
+     public ClientRemoveCertCLI(ClientCLI parent) {
+-        super("remove-cert", "Remove certificate from client security database");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <nickname>", options);
++        super("remove-cert", parent);
+     }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        CommandLine cmd = null;
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 1) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String nickname = cmdArgs[0];
+-        parent.parent.client.removeCert(nickname);
+-
+-        MainCLI.printMessage("Removed certificate \"" + nickname + "\"");
+-   }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupAddMemberCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupAddMemberCLI.java
+index 36d3c06..a761853 100644
+--- a/base/java-tools/src/com/netscape/cmstools/group/GroupAddMemberCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupAddMemberCLI.java
+@@ -18,40 +18,14 @@
+ 
+ package com.netscape.cmstools.group;
+ 
+-import com.netscape.certsrv.group.GroupMemberData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class GroupAddMemberCLI extends CLI {
+-
+-    public GroupCLI parent;
++@Deprecated
++public class GroupAddMemberCLI extends GroupMemberAddCLI {
+ 
+     public GroupAddMemberCLI(GroupCLI parent) {
+-        super("add-member", "Add group member");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String groupID = args[0];
+-        String memberID = args[1];
+-
+-        GroupMemberData groupMemberData = parent.client.addGroupMember(groupID, memberID);
+-
+-        MainCLI.printMessage("Added group member \""+memberID+"\"");
+-
+-        GroupCLI.printGroupMember(groupMemberData);
++        super("add-member", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupCLI.java
+index bd8cec7..bc4d573 100644
+--- a/base/java-tools/src/com/netscape/cmstools/group/GroupCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupCLI.java
+@@ -51,26 +51,11 @@ public class GroupCLI extends CLI {
+         addModule(new GroupShowMemberCLI(this));
+         addModule(new GroupAddMemberCLI(this));
+         addModule(new GroupRemoveMemberCLI(this));
+-    }
+-
+-    public void printHelp() {
+-
+-        System.out.println("Commands:");
+-
+-        int leftPadding = 1;
+-        int rightPadding = 25;
+ 
+-        for (CLI module : modules.values()) {
+-            String label = name+"-"+module.getName();
+-
+-            int padding = rightPadding - leftPadding - label.length();
+-            if (padding < 1) padding = 1;
+-
+-            System.out.print(StringUtils.repeat(" ", leftPadding));
+-            System.out.print(label);
+-            System.out.print(StringUtils.repeat(" ", padding));
+-            System.out.println(module.getDescription());
+-        }
++        addModule(new GroupMemberFindCLI(this));
++        addModule(new GroupMemberShowCLI(this));
++        addModule(new GroupMemberAddCLI(this));
++        addModule(new GroupMemberRemoveCLI(this));
+     }
+ 
+     public void execute(String[] args) throws Exception {
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupFindMemberCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupFindMemberCLI.java
+index f0498f0..4850910 100644
+--- a/base/java-tools/src/com/netscape/cmstools/group/GroupFindMemberCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupFindMemberCLI.java
+@@ -18,87 +18,14 @@
+ 
+ package com.netscape.cmstools.group;
+ 
+-import java.util.Collection;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-
+-import com.netscape.certsrv.group.GroupMemberCollection;
+-import com.netscape.certsrv.group.GroupMemberData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class GroupFindMemberCLI extends CLI {
+-
+-    public GroupCLI parent;
++@Deprecated
++public class GroupFindMemberCLI extends GroupMemberFindCLI {
+ 
+     public GroupFindMemberCLI(GroupCLI parent) {
+-        super("find-member", "Find group members");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <Group ID> [OPTIONS...]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "start", true, "Page start");
+-        option.setArgName("start");
+-        options.addOption(option);
+-
+-        option = new Option(null, "size", true, "Page size");
+-        option.setArgName("size");
+-        options.addOption(option);
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 1) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String groupID = cmdArgs[0];
+-
+-        String s = cmd.getOptionValue("start");
+-        Integer start = s == null ? null : Integer.valueOf(s);
+-
+-        s = cmd.getOptionValue("size");
+-        Integer size = s == null ? null : Integer.valueOf(s);
+-
+-        GroupMemberCollection response = parent.client.findGroupMembers(groupID, start, size);
+-
+-        Collection<GroupMemberData> entries = response.getMembers();
+-
+-        MainCLI.printMessage(entries.size()+" group member(s) matched");
+-
+-        boolean first = true;
+-
+-        for (GroupMemberData groupMemberData : entries) {
+-
+-            if (first) {
+-                first = false;
+-            } else {
+-                System.out.println();
+-            }
+-
+-            GroupCLI.printGroupMember(groupMemberData);
+-        }
+-
+-        MainCLI.printMessage("Number of entries returned "+entries.size());
++        super("find-member", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupMemberAddCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberAddCLI.java
+new file mode 100644
+index 0000000..5945e21
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberAddCLI.java
+@@ -0,0 +1,61 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.group;
++
++import com.netscape.certsrv.group.GroupMemberData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class GroupMemberAddCLI extends CLI {
++
++    public GroupCLI parent;
++
++    public GroupMemberAddCLI(String name, GroupCLI parent) {
++        super(name, "Add group member");
++        this.parent = parent;
++    }
++
++    public GroupMemberAddCLI(GroupCLI parent) {
++        this("member-add", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String groupID = args[0];
++        String memberID = args[1];
++
++        GroupMemberData groupMemberData = parent.client.addGroupMember(groupID, memberID);
++
++        MainCLI.printMessage("Added group member \""+memberID+"\"");
++
++        GroupCLI.printGroupMember(groupMemberData);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupMemberFindCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberFindCLI.java
+new file mode 100644
+index 0000000..c36d041
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberFindCLI.java
+@@ -0,0 +1,108 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.group;
++
++import java.util.Collection;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++
++import com.netscape.certsrv.group.GroupMemberCollection;
++import com.netscape.certsrv.group.GroupMemberData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class GroupMemberFindCLI extends CLI {
++
++    public GroupCLI parent;
++
++    public GroupMemberFindCLI(String name, GroupCLI parent) {
++        super(name, "Find group members");
++        this.parent = parent;
++    }
++
++    public GroupMemberFindCLI(GroupCLI parent) {
++        this("member-find", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <Group ID> [OPTIONS...]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "start", true, "Page start");
++        option.setArgName("start");
++        options.addOption(option);
++
++        option = new Option(null, "size", true, "Page size");
++        option.setArgName("size");
++        options.addOption(option);
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 1) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String groupID = cmdArgs[0];
++
++        String s = cmd.getOptionValue("start");
++        Integer start = s == null ? null : Integer.valueOf(s);
++
++        s = cmd.getOptionValue("size");
++        Integer size = s == null ? null : Integer.valueOf(s);
++
++        GroupMemberCollection response = parent.client.findGroupMembers(groupID, start, size);
++
++        Collection<GroupMemberData> entries = response.getMembers();
++
++        MainCLI.printMessage(entries.size()+" group member(s) matched");
++
++        boolean first = true;
++
++        for (GroupMemberData groupMemberData : entries) {
++
++            if (first) {
++                first = false;
++            } else {
++                System.out.println();
++            }
++
++            GroupCLI.printGroupMember(groupMemberData);
++        }
++
++        MainCLI.printMessage("Number of entries returned "+entries.size());
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupMemberRemoveCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberRemoveCLI.java
+new file mode 100644
+index 0000000..db85822
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberRemoveCLI.java
+@@ -0,0 +1,58 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.group;
++
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class GroupMemberRemoveCLI extends CLI {
++
++    public GroupCLI parent;
++
++    public GroupMemberRemoveCLI(String name, GroupCLI parent) {
++        super(name, "Remove group member");
++        this.parent = parent;
++    }
++
++    public GroupMemberRemoveCLI(GroupCLI parent) {
++        this("member-del", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String groupID = args[0];
++        String memberID = args[1];
++
++        parent.client.removeGroupMember(groupID, memberID);
++
++        MainCLI.printMessage("Deleted group member \""+memberID+"\"");
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupMemberShowCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberShowCLI.java
+new file mode 100644
+index 0000000..214f71d
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupMemberShowCLI.java
+@@ -0,0 +1,61 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.group;
++
++import com.netscape.certsrv.group.GroupMemberData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class GroupMemberShowCLI extends CLI {
++
++    public GroupCLI parent;
++
++    public GroupMemberShowCLI(String name, GroupCLI parent) {
++        super(name, "Show group member");
++        this.parent = parent;
++    }
++
++    public GroupMemberShowCLI(GroupCLI parent) {
++        this("member-show", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String groupID = args[0];
++        String memberID = args[1];
++
++        GroupMemberData groupMemberData = parent.client.getGroupMember(groupID, memberID);
++
++        MainCLI.printMessage("Group member \""+memberID+"\"");
++
++        GroupCLI.printGroupMember(groupMemberData);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupRemoveMemberCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupRemoveMemberCLI.java
+index c12cc89..9672488 100644
+--- a/base/java-tools/src/com/netscape/cmstools/group/GroupRemoveMemberCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupRemoveMemberCLI.java
+@@ -18,37 +18,14 @@
+ 
+ package com.netscape.cmstools.group;
+ 
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class GroupRemoveMemberCLI extends CLI {
+-
+-    public GroupCLI parent;
++@Deprecated
++public class GroupRemoveMemberCLI extends GroupMemberRemoveCLI {
+ 
+     public GroupRemoveMemberCLI(GroupCLI parent) {
+-        super("remove-member", "Remove group member");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String groupID = args[0];
+-        String memberID = args[1];
+-
+-        parent.client.removeGroupMember(groupID, memberID);
+-
+-        MainCLI.printMessage("Deleted group member \""+memberID+"\"");
++        super("remove-member", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/group/GroupShowMemberCLI.java b/base/java-tools/src/com/netscape/cmstools/group/GroupShowMemberCLI.java
+index 47ca43c..6e493d3 100644
+--- a/base/java-tools/src/com/netscape/cmstools/group/GroupShowMemberCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/group/GroupShowMemberCLI.java
+@@ -18,40 +18,14 @@
+ 
+ package com.netscape.cmstools.group;
+ 
+-import com.netscape.certsrv.group.GroupMemberData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class GroupShowMemberCLI extends CLI {
+-
+-    public GroupCLI parent;
++@Deprecated
++public class GroupShowMemberCLI extends GroupMemberShowCLI {
+ 
+     public GroupShowMemberCLI(GroupCLI parent) {
+-        super("show-member", "Show group member");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <Group ID> <Member ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String groupID = args[0];
+-        String memberID = args[1];
+-
+-        GroupMemberData groupMemberData = parent.client.getGroupMember(groupID, memberID);
+-
+-        MainCLI.printMessage("Group member \""+memberID+"\"");
+-
+-        GroupCLI.printGroupMember(groupMemberData);
++        super("show-member", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserAddCertCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserAddCertCLI.java
+index 7bec2ff..528d39c 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserAddCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserAddCertCLI.java
+@@ -18,80 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import java.io.File;
+-import java.util.Scanner;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-
+-import com.netscape.certsrv.user.UserCertData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserAddCertCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserAddCertCLI extends UserCertAddCLI {
+ 
+     public UserAddCertCLI(UserCLI parent) {
+-        super("add-cert", "Add user cert");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "input", true, "Input file");
+-        option.setArgName("file");
+-        option.setRequired(true);
+-        options.addOption(option);
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 1) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userId = cmdArgs[0];
+-        String file = cmd.getOptionValue("input");
+-
+-        // get cert from file
+-        if (verbose) {
+-            System.out.println("Reading cert from "+file+".");
+-        }
+-        String encoded = new Scanner(new File(file)).useDelimiter("\\A").next();
+-        if (verbose) {
+-            System.out.println(encoded);
+-        }
+-
+-        UserCertData userCertData = new UserCertData();
+-        userCertData.setEncoded(encoded);
+-
+-        if (verbose) {
+-            System.out.println(userCertData);
+-        }
+-
+-        userCertData = parent.client.addUserCert(userId, userCertData);
+-
+-        MainCLI.printMessage("Added certificate \"" + userCertData.getID() + "\"");
+-
+-        UserCLI.printCert(userCertData, false, false);
++        super("add-cert", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserAddMembershipCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserAddMembershipCLI.java
+index 224f226..43a55ea 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserAddMembershipCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserAddMembershipCLI.java
+@@ -18,40 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import com.netscape.certsrv.user.UserMembershipData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserAddMembershipCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserAddMembershipCLI extends UserMembershipAddCLI {
+ 
+     public UserAddMembershipCLI(UserCLI parent) {
+-        super("add-membership", "Add user membership");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> <Group ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = args[0];
+-        String groupID = args[1];
+-
+-        UserMembershipData userMembershipData = parent.client.addUserMembership(userID, groupID);
+-
+-        MainCLI.printMessage("Added membership in \""+groupID+"\"");
+-
+-        UserCLI.printUserMembership(userMembershipData);
++        super("add-membership", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserCLI.java
+index 2343d19..be404b8 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserCLI.java
+@@ -53,30 +53,18 @@ public class UserCLI extends CLI {
+         addModule(new UserAddCertCLI(this));
+         addModule(new UserRemoveCertCLI(this));
+ 
++        addModule(new UserCertFindCLI(this));
++        addModule(new UserCertShowCLI(this));
++        addModule(new UserCertAddCLI(this));
++        addModule(new UserCertRemoveCLI(this));
++
+         addModule(new UserFindMembershipCLI(this));
+         addModule(new UserAddMembershipCLI(this));
+         addModule(new UserRemoveMembershipCLI(this));
+-    }
+-
+-    public void printHelp() {
+-
+-        System.out.println("Commands:");
+ 
+-        int leftPadding = 1;
+-        int rightPadding = 25;
+-
+-        for (CLI module : modules.values()) {
+-            String label = name + "-" + module.getName();
+-
+-            int padding = rightPadding - leftPadding - label.length();
+-            if (padding < 1)
+-                padding = 1;
+-
+-            System.out.print(StringUtils.repeat(" ", leftPadding));
+-            System.out.print(label);
+-            System.out.print(StringUtils.repeat(" ", padding));
+-            System.out.println(module.getDescription());
+-        }
++        addModule(new UserMembershipFindCLI(this));
++        addModule(new UserMembershipAddCLI(this));
++        addModule(new UserMembershipRemoveCLI(this));
+     }
+ 
+     public void execute(String[] args) throws Exception {
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserCertAddCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserCertAddCLI.java
+new file mode 100644
+index 0000000..6e2e5cc
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserCertAddCLI.java
+@@ -0,0 +1,105 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import java.io.File;
++import java.util.Scanner;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++
++import com.netscape.certsrv.user.UserCertData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserCertAddCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserCertAddCLI(String name, UserCLI parent) {
++        super(name, "Add user cert");
++        this.parent = parent;
++    }
++
++    public UserCertAddCLI(UserCLI parent) {
++        this("cert-add", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "input", true, "Input file");
++        option.setArgName("file");
++        option.setRequired(true);
++        options.addOption(option);
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 1) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userId = cmdArgs[0];
++        String file = cmd.getOptionValue("input");
++
++        // get cert from file
++        if (verbose) {
++            System.out.println("Reading cert from "+file+".");
++        }
++
++        UserCertData userCertData = new UserCertData();
++
++        try (Scanner scanner = new Scanner(new File(file))) {
++            String encoded = scanner.useDelimiter("\\A").next();
++            if (verbose) {
++                System.out.println(encoded);
++            }
++
++            userCertData.setEncoded(encoded);
++        }
++
++        if (verbose) {
++            System.out.println(userCertData);
++        }
++
++        userCertData = parent.client.addUserCert(userId, userCertData);
++
++        MainCLI.printMessage("Added certificate \"" + userCertData.getID() + "\"");
++
++        UserCLI.printCert(userCertData, false, false);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserCertFindCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserCertFindCLI.java
+new file mode 100644
+index 0000000..c0c85a0
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserCertFindCLI.java
+@@ -0,0 +1,108 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import java.util.Collection;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++
++import com.netscape.certsrv.user.UserCertCollection;
++import com.netscape.certsrv.user.UserCertData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserCertFindCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserCertFindCLI(String name, UserCLI parent) {
++        super(name, "Find user certs");
++        this.parent = parent;
++    }
++
++    public UserCertFindCLI(UserCLI parent) {
++        this("cert-find", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "start", true, "Page start");
++        option.setArgName("start");
++        options.addOption(option);
++
++        option = new Option(null, "size", true, "Page size");
++        option.setArgName("size");
++        options.addOption(option);
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 1) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = cmdArgs[0];
++
++        String s = cmd.getOptionValue("start");
++        Integer start = s == null ? null : Integer.valueOf(s);
++
++        s = cmd.getOptionValue("size");
++        Integer size = s == null ? null : Integer.valueOf(s);
++
++        UserCertCollection response = parent.client.findUserCerts(userID, start, size);
++
++        Collection<UserCertData> entries = response.getCerts();
++
++        MainCLI.printMessage(entries.size() + " user cert(s) matched");
++
++        boolean first = true;
++
++        for (UserCertData userCertData : entries) {
++
++            if (first) {
++                first = false;
++            } else {
++                System.out.println();
++            }
++
++            UserCLI.printCert(userCertData, false, false);
++        }
++
++        MainCLI.printMessage("Number of entries returned " + entries.size());
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserCertRemoveCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserCertRemoveCLI.java
+new file mode 100644
+index 0000000..503e137
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserCertRemoveCLI.java
+@@ -0,0 +1,65 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import java.net.URLEncoder;
++
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserCertRemoveCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserCertRemoveCLI(String name, UserCLI parent) {
++        super(name, "Remove user cert");
++        this.parent = parent;
++    }
++
++    public UserCertRemoveCLI(UserCLI parent) {
++        this("cert-del", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> <Cert ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = args[0];
++        String certID = args[1];
++
++        if (verbose) {
++            System.out.println("Removing cert "+certID+" from user "+userID+".");
++        }
++
++        parent.client.removeUserCert(userID, URLEncoder.encode(certID, "UTF-8"));
++
++        MainCLI.printMessage("Deleted certificate \"" + certID + "\"");
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserCertShowCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserCertShowCLI.java
+new file mode 100644
+index 0000000..fcf5159
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserCertShowCLI.java
+@@ -0,0 +1,100 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2012 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import java.io.FileWriter;
++import java.io.PrintWriter;
++import java.net.URLEncoder;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++
++import com.netscape.certsrv.user.UserCertData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserCertShowCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserCertShowCLI(String name, UserCLI parent) {
++        super(name, "Show user cert");
++        this.parent = parent;
++    }
++
++    public UserCertShowCLI(UserCLI parent) {
++        this("cert-show", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> <Cert ID> [OPTIONS...]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "output", true, "Output file");
++        option.setArgName("file");
++        options.addOption(option);
++
++        options.addOption(null, "pretty", false, "Pretty print");
++        options.addOption(null, "encoded", false, "Base-64 encoded");
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        boolean showPrettyPrint = cmd.hasOption("pretty");
++        boolean showEncoded = cmd.hasOption("encoded");
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = cmdArgs[0];
++        String certID = cmdArgs[1];
++        String file = cmd.getOptionValue("output");
++
++        UserCertData userCertData = parent.client.getUserCert(userID, URLEncoder.encode(certID, "UTF-8"));
++
++        String encoded = userCertData.getEncoded();
++        if (encoded != null && file != null) {
++            // store cert to file
++            PrintWriter out = new PrintWriter(new FileWriter(file));
++            out.print(encoded);
++            out.close();
++        }
++
++        MainCLI.printMessage("Certificate \"" + userCertData.getID() + "\"");
++
++        UserCLI.printCert(userCertData, showPrettyPrint, showEncoded);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserFindCertCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserFindCertCLI.java
+index 08f6879..baf73c9 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserFindCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserFindCertCLI.java
+@@ -18,87 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import java.util.Collection;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-
+-import com.netscape.certsrv.user.UserCertCollection;
+-import com.netscape.certsrv.user.UserCertData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserFindCertCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserFindCertCLI extends UserCertFindCLI {
+ 
+     public UserFindCertCLI(UserCLI parent) {
+-        super("find-cert", "Find user certs");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "start", true, "Page start");
+-        option.setArgName("start");
+-        options.addOption(option);
+-
+-        option = new Option(null, "size", true, "Page size");
+-        option.setArgName("size");
+-        options.addOption(option);
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 1) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = cmdArgs[0];
+-
+-        String s = cmd.getOptionValue("start");
+-        Integer start = s == null ? null : Integer.valueOf(s);
+-
+-        s = cmd.getOptionValue("size");
+-        Integer size = s == null ? null : Integer.valueOf(s);
+-
+-        UserCertCollection response = parent.client.findUserCerts(userID, start, size);
+-
+-        Collection<UserCertData> entries = response.getCerts();
+-
+-        MainCLI.printMessage(entries.size() + " user cert(s) matched");
+-
+-        boolean first = true;
+-
+-        for (UserCertData userCertData : entries) {
+-
+-            if (first) {
+-                first = false;
+-            } else {
+-                System.out.println();
+-            }
+-
+-            UserCLI.printCert(userCertData, false, false);
+-        }
+-
+-        MainCLI.printMessage("Number of entries returned " + entries.size());
++        super("find-cert", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserFindMembershipCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserFindMembershipCLI.java
+index 494c3c3..24fb9ca 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserFindMembershipCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserFindMembershipCLI.java
+@@ -18,87 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import java.util.Collection;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-
+-import com.netscape.certsrv.user.UserMembershipCollection;
+-import com.netscape.certsrv.user.UserMembershipData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserFindMembershipCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserFindMembershipCLI extends UserMembershipFindCLI {
+ 
+     public UserFindMembershipCLI(UserCLI parent) {
+-        super("find-membership", "Find user memberships");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "start", true, "Page start");
+-        option.setArgName("start");
+-        options.addOption(option);
+-
+-        option = new Option(null, "size", true, "Page size");
+-        option.setArgName("size");
+-        options.addOption(option);
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 1) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = cmdArgs[0];
+-
+-        String s = cmd.getOptionValue("start");
+-        Integer start = s == null ? null : Integer.valueOf(s);
+-
+-        s = cmd.getOptionValue("size");
+-        Integer size = s == null ? null : Integer.valueOf(s);
+-
+-        UserMembershipCollection response = parent.client.findUserMemberships(userID, start, size);
+-
+-        Collection<UserMembershipData> entries = response.getMemberships();
+-
+-        MainCLI.printMessage(entries.size()+" membership(s) matched");
+-
+-        boolean first = true;
+-
+-        for (UserMembershipData userMembershipData : entries) {
+-
+-            if (first) {
+-                first = false;
+-            } else {
+-                System.out.println();
+-            }
+-
+-            UserCLI.printUserMembership(userMembershipData);
+-        }
+-
+-        MainCLI.printMessage("Number of entries returned "+entries.size());
++        super("find-membership", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserMembershipAddCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipAddCLI.java
+new file mode 100644
+index 0000000..44cb578
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipAddCLI.java
+@@ -0,0 +1,61 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import com.netscape.certsrv.user.UserMembershipData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserMembershipAddCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserMembershipAddCLI(String name, UserCLI parent) {
++        super(name, "Add user membership");
++        this.parent = parent;
++    }
++
++    public UserMembershipAddCLI(UserCLI parent) {
++        this("membership-add", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> <Group ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = args[0];
++        String groupID = args[1];
++
++        UserMembershipData userMembershipData = parent.client.addUserMembership(userID, groupID);
++
++        MainCLI.printMessage("Added membership in \""+groupID+"\"");
++
++        UserCLI.printUserMembership(userMembershipData);
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserMembershipFindCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipFindCLI.java
+new file mode 100644
+index 0000000..beca5f4
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipFindCLI.java
+@@ -0,0 +1,108 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import java.util.Collection;
++
++import org.apache.commons.cli.CommandLine;
++import org.apache.commons.cli.Option;
++
++import com.netscape.certsrv.user.UserMembershipCollection;
++import com.netscape.certsrv.user.UserMembershipData;
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserMembershipFindCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserMembershipFindCLI(String name, UserCLI parent) {
++        super(name, "Find user memberships");
++        this.parent = parent;
++    }
++
++    public UserMembershipFindCLI(UserCLI parent) {
++        this("membership-find", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> [OPTIONS...]", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        Option option = new Option(null, "start", true, "Page start");
++        option.setArgName("start");
++        options.addOption(option);
++
++        option = new Option(null, "size", true, "Page size");
++        option.setArgName("size");
++        options.addOption(option);
++
++        CommandLine cmd = null;
++
++        try {
++            cmd = parser.parse(options, args);
++
++        } catch (Exception e) {
++            System.err.println("Error: " + e.getMessage());
++            printHelp();
++            System.exit(1);
++        }
++
++        String[] cmdArgs = cmd.getArgs();
++
++        if (cmdArgs.length != 1) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = cmdArgs[0];
++
++        String s = cmd.getOptionValue("start");
++        Integer start = s == null ? null : Integer.valueOf(s);
++
++        s = cmd.getOptionValue("size");
++        Integer size = s == null ? null : Integer.valueOf(s);
++
++        UserMembershipCollection response = parent.client.findUserMemberships(userID, start, size);
++
++        Collection<UserMembershipData> entries = response.getMemberships();
++
++        MainCLI.printMessage(entries.size()+" membership(s) matched");
++
++        boolean first = true;
++
++        for (UserMembershipData userMembershipData : entries) {
++
++            if (first) {
++                first = false;
++            } else {
++                System.out.println();
++            }
++
++            UserCLI.printUserMembership(userMembershipData);
++        }
++
++        MainCLI.printMessage("Number of entries returned "+entries.size());
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserMembershipRemoveCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipRemoveCLI.java
+new file mode 100644
+index 0000000..ba43b05
+--- /dev/null
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserMembershipRemoveCLI.java
+@@ -0,0 +1,58 @@
++// --- BEGIN COPYRIGHT BLOCK ---
++// This program is free software; you can redistribute it and/or modify
++// it under the terms of the GNU General Public License as published by
++// the Free Software Foundation; version 2 of the License.
++//
++// This program is distributed in the hope that it will be useful,
++// but WITHOUT ANY WARRANTY; without even the implied warranty of
++// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
++// GNU General Public License for more details.
++//
++// You should have received a copy of the GNU General Public License along
++// with this program; if not, write to the Free Software Foundation, Inc.,
++// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
++//
++// (C) 2013 Red Hat, Inc.
++// All rights reserved.
++// --- END COPYRIGHT BLOCK ---
++
++package com.netscape.cmstools.user;
++
++import com.netscape.cmstools.cli.CLI;
++import com.netscape.cmstools.cli.MainCLI;
++
++/**
++ * @author Endi S. Dewata
++ */
++public class UserMembershipRemoveCLI extends CLI {
++
++    public UserCLI parent;
++
++    public UserMembershipRemoveCLI(String name, UserCLI parent) {
++        super(name, "Remove user membership");
++        this.parent = parent;
++    }
++
++    public UserMembershipRemoveCLI(UserCLI parent) {
++        this("membership-del", parent);
++    }
++
++    public void printHelp() {
++        formatter.printHelp(parent.name + "-" + name + " <User ID> <Group ID>", options);
++    }
++
++    public void execute(String[] args) throws Exception {
++
++        if (args.length != 2) {
++            printHelp();
++            System.exit(1);
++        }
++
++        String userID = args[0];
++        String groupID = args[1];
++
++        parent.client.removeUserMembership(userID, groupID);
++
++        MainCLI.printMessage("Deleted membership in group \""+groupID+"\"");
++    }
++}
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserRemoveCertCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserRemoveCertCLI.java
+index 264458b..58fd57e 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserRemoveCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserRemoveCertCLI.java
+@@ -18,44 +18,15 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import java.net.URLEncoder;
+-
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserRemoveCertCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserRemoveCertCLI extends UserCertRemoveCLI {
+ 
+     public UserRemoveCertCLI(UserCLI parent) {
+-        super("remove-cert", "Remove user cert");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> <Cert ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = args[0];
+-        String certID = args[1];
+-
+-        if (verbose) {
+-            System.out.println("Removing cert "+certID+" from user "+userID+".");
+-        }
+-
+-        parent.client.removeUserCert(userID, URLEncoder.encode(certID, "UTF-8"));
+-
+-        MainCLI.printMessage("Deleted certificate \"" + certID + "\"");
++        super("remove-cert", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserRemoveMembershipCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserRemoveMembershipCLI.java
+index 26a5a6e..4cafcec 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserRemoveMembershipCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserRemoveMembershipCLI.java
+@@ -18,37 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserRemoveMembershipCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserRemoveMembershipCLI extends UserMembershipRemoveCLI {
+ 
+     public UserRemoveMembershipCLI(UserCLI parent) {
+-        super("remove-membership", "Remove user membership");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> <Group ID>", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        if (args.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = args[0];
+-        String groupID = args[1];
+-
+-        parent.client.removeUserMembership(userID, groupID);
+-
+-        MainCLI.printMessage("Deleted membership in group \""+groupID+"\"");
++        super("remove-membership", parent);
+     }
+ }
+diff --git a/base/java-tools/src/com/netscape/cmstools/user/UserShowCertCLI.java b/base/java-tools/src/com/netscape/cmstools/user/UserShowCertCLI.java
+index f30c723..5177281 100644
+--- a/base/java-tools/src/com/netscape/cmstools/user/UserShowCertCLI.java
++++ b/base/java-tools/src/com/netscape/cmstools/user/UserShowCertCLI.java
+@@ -18,79 +18,14 @@
+ 
+ package com.netscape.cmstools.user;
+ 
+-import java.io.FileWriter;
+-import java.io.PrintWriter;
+-import java.net.URLEncoder;
+-
+-import org.apache.commons.cli.CommandLine;
+-import org.apache.commons.cli.Option;
+-
+-import com.netscape.certsrv.user.UserCertData;
+-import com.netscape.cmstools.cli.CLI;
+-import com.netscape.cmstools.cli.MainCLI;
+ 
+ /**
+  * @author Endi S. Dewata
+  */
+-public class UserShowCertCLI extends CLI {
+-
+-    public UserCLI parent;
++@Deprecated
++public class UserShowCertCLI extends UserCertShowCLI {
+ 
+     public UserShowCertCLI(UserCLI parent) {
+-        super("show-cert", "Show user cert");
+-        this.parent = parent;
+-    }
+-
+-    public void printHelp() {
+-        formatter.printHelp(parent.name + "-" + name + " <User ID> <Cert ID> [OPTIONS...]", options);
+-    }
+-
+-    public void execute(String[] args) throws Exception {
+-
+-        Option option = new Option(null, "output", true, "Output file");
+-        option.setArgName("file");
+-        options.addOption(option);
+-
+-        options.addOption(null, "pretty", false, "Pretty print");
+-        options.addOption(null, "encoded", false, "Base-64 encoded");
+-
+-        CommandLine cmd = null;
+-
+-        try {
+-            cmd = parser.parse(options, args);
+-
+-        } catch (Exception e) {
+-            System.err.println("Error: " + e.getMessage());
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        boolean showPrettyPrint = cmd.hasOption("pretty");
+-        boolean showEncoded = cmd.hasOption("encoded");
+-
+-        String[] cmdArgs = cmd.getArgs();
+-
+-        if (cmdArgs.length != 2) {
+-            printHelp();
+-            System.exit(1);
+-        }
+-
+-        String userID = cmdArgs[0];
+-        String certID = cmdArgs[1];
+-        String file = cmd.getOptionValue("output");
+-
+-        UserCertData userCertData = parent.client.getUserCert(userID, URLEncoder.encode(certID, "UTF-8"));
+-
+-        String encoded = userCertData.getEncoded();
+-        if (encoded != null && file != null) {
+-            // store cert to file
+-            PrintWriter out = new PrintWriter(new FileWriter(file));
+-            out.print(encoded);
+-            out.close();
+-        }
+-
+-        MainCLI.printMessage("Certificate \"" + userCertData.getID() + "\"");
+-
+-        UserCLI.printCert(userCertData, showPrettyPrint, showEncoded);
++        super("show-cert", parent);
+     }
+ }
+-- 
+1.8.3.1
+
diff --git a/SOURCES/0006-Added-new-link-for-resteasy-dependency.patch b/SOURCES/0006-Added-new-link-for-resteasy-dependency.patch
new file mode 100644
index 0000000..ac0feb9
--- /dev/null
+++ b/SOURCES/0006-Added-new-link-for-resteasy-dependency.patch
@@ -0,0 +1,92 @@
+From cbd26eee9194438627a7f0949bde9fa4f582ca8c Mon Sep 17 00:00:00 2001
+From: Ade Lee <alee@redhat.com>
+Date: Wed, 30 Oct 2013 17:03:15 -0400
+Subject: [PATCH 6/6] Added new link for resteasy dependency
+
+    Resteasy 2.3.5 uses apache-commons-io.  Not having a link to
+    this jar results in IPA replica installs failing.
+
+    Resolves: rhbz 1024679
+---
+ base/common/shared/conf/pki.policy            | 4 ++++
+ base/java-tools/pki                           | 1 +
+ base/server/etc/default.cfg                   | 2 ++
+ base/server/scripts/operations                | 1 +
+ base/server/src/scriptlets/instance_layout.py | 2 ++
+ 5 files changed, 10 insertions(+)
+
+diff --git a/base/common/shared/conf/pki.policy b/base/common/shared/conf/pki.policy
+index 52e3d7f..df9157e 100644
+--- a/base/common/shared/conf/pki.policy
++++ b/base/common/shared/conf/pki.policy
+@@ -46,6 +46,10 @@ grant codeBase "file:/usr/share/java/apache-commons-collections.jar" {
+         permission java.security.AllPermission;
+ };
+ 
++grant codeBase "file:/usr/share/java/apache-commons-io.jar" {
++        permission java.security.AllPermission;
++};
++
+ grant codeBase "file:/usr/share/java/apache-commons-lang.jar" {
+         permission java.security.AllPermission;
+ };
+diff --git a/base/java-tools/pki b/base/java-tools/pki
+index b7d9bfe..5821620 100755
+--- a/base/java-tools/pki
++++ b/base/java-tools/pki
+@@ -80,6 +80,7 @@ $ENV{CLASSPATH} = "/usr/share/java/${PRODUCT}/pki-certsrv.jar:"
+                 . "/usr/share/java/${PRODUCT}/pki-tools.jar:"
+                 . "/usr/share/java/apache-commons-cli.jar:"
+                 . "/usr/share/java/apache-commons-codec.jar:"
++                . "/usr/share/java/apache-commons-io.jar:"
+                 . "/usr/share/java/apache-commons-lang.jar:"
+                 . "/usr/share/java/apache-commons-logging.jar:"
+                 . "/usr/share/java/commons-httpclient.jar:"
+diff --git a/base/server/etc/default.cfg b/base/server/etc/default.cfg
+index f4ad2be..8559b42 100644
+--- a/base/server/etc/default.cfg
++++ b/base/server/etc/default.cfg
+@@ -275,6 +275,7 @@ pki_nsutil_jar_link=%(pki_tomcat_webapps_subsystem_webinf_lib_path)s/pki-nsutil.
+ pki_jss_jar=%(jni_jar_dir)s/jss4.jar
+ pki_symkey_jar=%(jni_jar_dir)s/symkey.jar
+ pki_apache_commons_collections_jar=/usr/share/java/apache-commons-collections.jar
++pki_apache_commons_io_jar=/usr/share/java/apache-commons-io.jar
+ pki_apache_commons_lang_jar=/usr/share/java/apache-commons-lang.jar
+ pki_apache_commons_logging_jar=/usr/share/java/apache-commons-logging.jar
+ pki_commons_codec_jar=/usr/share/java/commons-codec.jar
+@@ -304,6 +305,7 @@ pki_xml_commons_resolver_jar=/usr/share/java/xml-commons-resolver.jar
+ pki_jss_jar_link=%(pki_tomcat_common_lib_path)s/jss4.jar
+ pki_symkey_jar_link=%(pki_tomcat_common_lib_path)s/symkey.jar
+ pki_apache_commons_collections_jar_link=%(pki_tomcat_common_lib_path)s/apache-commons-collections.jar
++pki_apache_commons_io_jar_link=%(pki_tomcat_common_lib_path)s/apache-commons-io.jar
+ pki_apache_commons_lang_jar_link=%(pki_tomcat_common_lib_path)s/apache-commons-lang.jar
+ pki_apache_commons_logging_jar_link=%(pki_tomcat_common_lib_path)s/apache-commons-logging.jar
+ pki_commons_codec_jar_link=%(pki_tomcat_common_lib_path)s/apache-commons-codec.jar
+diff --git a/base/server/scripts/operations b/base/server/scripts/operations
+index 8a703d6..df89ea6 100644
+--- a/base/server/scripts/operations
++++ b/base/server/scripts/operations
+@@ -1197,6 +1197,7 @@ verify_symlinks()
+     common_jar_symlinks=(
+         [apache-commons-codec.jar]=${java_dir}/commons-codec.jar
+         [apache-commons-collections.jar]=${java_dir}/apache-commons-collections.jar
++        [apache-commons-io.jar]=${java_dir}/apache-commons-io.jar
+         [apache-commons-lang.jar]=${java_dir}/apache-commons-lang.jar
+         [apache-commons-logging.jar]=${java_dir}/apache-commons-logging.jar
+         [httpclient.jar]=${java_dir}/httpcomponents/httpclient.jar
+diff --git a/base/server/src/scriptlets/instance_layout.py b/base/server/src/scriptlets/instance_layout.py
+index 07ae03e..1f75de7 100644
+--- a/base/server/src/scriptlets/instance_layout.py
++++ b/base/server/src/scriptlets/instance_layout.py
+@@ -88,6 +88,8 @@ class PkiScriptlet(pkiscriptlet.AbstractBasePkiScriptlet):
+             # establish Tomcat instance common lib jar symbolic links
+             util.symlink.create(master['pki_apache_commons_collections_jar'],
+                 master['pki_apache_commons_collections_jar_link'])
++            util.symlink.create(master['pki_apache_commons_io_jar'],
++                master['pki_apache_commons_io_jar_link'])
+             util.symlink.create(master['pki_apache_commons_lang_jar'],
+                 master['pki_apache_commons_lang_jar_link'])
+             util.symlink.create(master['pki_apache_commons_logging_jar'],
+-- 
+1.8.3.1
+
diff --git a/SPECS/pki-core.spec b/SPECS/pki-core.spec
new file mode 100644
index 0000000..ff0947a
--- /dev/null
+++ b/SPECS/pki-core.spec
@@ -0,0 +1,2331 @@
+%{!?python_sitelib: %global python_sitelib %(%{__python} -c "from
+distutils.sysconfig import get_python_lib; print(get_python_lib())")}
+%{!?python_sitearch: %global python_sitearch %(%{__python} -c "from
+distutils.sysconfig import get_python_lib; print(get_python_lib(1))")}
+
+Name:             pki-core
+Version:          10.0.5
+Release:          2%{?dist}
+Summary:          Certificate System - PKI Core Components
+URL:              http://pki.fedoraproject.org/
+License:          GPLv2
+Group:            System Environment/Daemons
+
+BuildRoot:        %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
+
+BuildRequires:    cmake >= 2.8.9-1
+BuildRequires:    zip
+BuildRequires:    java-devel >= 1:1.6.0
+BuildRequires:    redhat-rpm-config
+BuildRequires:    ldapjdk
+BuildRequires:    apache-commons-cli
+BuildRequires:    apache-commons-codec
+BuildRequires:    apache-commons-io
+BuildRequires:    nspr-devel
+BuildRequires:    nss-devel
+BuildRequires:    openldap-devel
+BuildRequires:    pkgconfig
+BuildRequires:    policycoreutils
+BuildRequires:    velocity
+BuildRequires:    xalan-j2
+BuildRequires:    xerces-j2
+
+%if  0%{?rhel}
+BuildRequires:    resteasy-base-atom-provider
+BuildRequires:    resteasy-base-jaxb-provider
+BuildRequires:    resteasy-base-jaxrs
+BuildRequires:    resteasy-base-jaxrs-api
+BuildRequires:    resteasy-base-jettison-provider
+%else
+BuildRequires:    resteasy >= 2.3.2-1
+%endif
+
+BuildRequires:    junit
+BuildRequires:    jpackage-utils >= 0:1.7.5-10
+%if 0%{?rhel} || 0%{?fedora} >= 19
+BuildRequires:    jss >= 4.2.6-28
+%else
+BuildRequires:    jss >= 4.2.6-24
+%endif
+BuildRequires:    systemd-units
+%if 0%{?rhel} || 0%{?fedora} >= 19
+BuildRequires:    tomcatjss >= 7.1.0
+%endif
+%if 0%{?fedora} == 18
+BuildRequires:    tomcatjss >= 7.0.0-4
+%endif
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+BuildRequires:    tomcatjss >= 6.0.2
+BuildRequires:    selinux-policy-devel >= 3.10.0-151
+%endif
+
+Source0:          http://pki.fedoraproject.org/pki/sources/%{name}/%{name}-%{version}%{?prerel}.tar.gz
+
+Patch0: 0000-Storing-authentication-info-in-session.patch
+Patch1: 0001-Fixed-error-handling-in-DoUnrevoke-servlet.patch
+Patch2: 0002-Fixed-errors-during-Tomcat-shutdown.patch
+Patch3: 0003-Fixed-logic-for-setting-admin-cert-signing-algorithm.patch
+Patch4: 0004-Backup-upgrade-tracker.patch
+Patch5: 0005-Added-CLI-command-aliases.patch
+Patch6: 0006-Added-new-link-for-resteasy-dependency.patch
+
+%if 0%{?rhel}
+ExcludeArch:      ppc ppc64 s390 s390x
+%endif
+
+%global saveFileContext() \
+if [ -s /etc/selinux/config ]; then \
+     . %{_sysconfdir}/selinux/config; \
+     FILE_CONTEXT=%{_sysconfdir}/selinux/%1/contexts/files/file_contexts; \
+     if [ "${SELINUXTYPE}" == %1 -a -f ${FILE_CONTEXT} ]; then \
+          cp -f ${FILE_CONTEXT} ${FILE_CONTEXT}.%{name}; \
+     fi \
+fi;
+
+%global relabel() \
+. %{_sysconfdir}/selinux/config; \
+FILE_CONTEXT=%{_sysconfdir}/selinux/%1/contexts/files/file_contexts; \
+selinuxenabled; \
+if [ $? == 0  -a "${SELINUXTYPE}" == %1 -a -f ${FILE_CONTEXT}.%{name} ]; then \
+     fixfiles -C ${FILE_CONTEXT}.%{name} restore; \
+     rm -f ${FILE_CONTEXT}.%name; \
+fi;
+
+%global overview                                                       \
+==================================                                     \
+||  ABOUT "CERTIFICATE SYSTEM"  ||                                     \
+==================================                                     \
+                                                                       \
+Certificate System (CS) is an enterprise software system designed      \
+to manage enterprise Public Key Infrastructure (PKI) deployments.      \
+                                                                       \
+PKI Core contains ALL top-level java-based Tomcat PKI components:      \
+                                                                       \
+  * pki-symkey                                                         \
+  * pki-base                                                           \
+  * pki-tools                                                          \
+  * pki-selinux (f17 only)                                             \
+  * pki-server                                                         \
+  * pki-ca                                                             \
+  * pki-kra  (fedora only)                                             \
+  * pki-ocsp (fedora only)                                             \
+  * pki-tks  (fedora only)                                             \
+  * pki-javadoc                                                        \
+                                                                       \
+which comprise the following corresponding PKI subsystems:             \
+                                                                       \
+  * Certificate Authority (CA)                                         \
+  * Data Recovery Manager (DRM) (fedora only)                          \
+  * Online Certificate Status Protocol (OCSP) Manager (fedora only)    \
+  * Token Key Service (TKS) (fedora only)                              \
+                                                                       \
+For deployment purposes, PKI Core contains fundamental packages        \
+required by BOTH native-based Apache AND java-based Tomcat             \
+Certificate System instances consisting of the following components:   \
+                                                                       \
+  * pki-tools                                                          \
+  * pki-selinux (f17 only)                                             \
+                                                                       \
+Additionally, PKI Core contains the following fundamental packages     \
+required ONLY by ALL java-based Tomcat Certificate System instances:   \
+                                                                       \
+  * pki-symkey                                                         \
+  * pki-base                                                           \
+  * pki-tools                                                          \
+  * pki-server                                                         \
+                                                                       \
+PKI Core also includes the following components:                       \
+                                                                       \
+  * pki-javadoc                                                        \
+                                                                       \
+Finally, if Certificate System is being deployed as an individual or   \
+set of standalone rather than embedded server(s)/service(s), it is     \
+strongly recommended (though not explicitly required) to include at    \
+least one PKI Theme package:                                           \
+                                                                       \
+  * dogtag-pki-theme (Dogtag Certificate System deployments)           \
+    * dogtag-pki-server-theme                                          \
+  * redhat-pki-server-theme (Red Hat Certificate System deployments)   \
+    * redhat-pki-server-theme                                          \
+  * customized pki theme (Customized Certificate System deployments)   \
+    * <customized>-pki-server-theme                                    \
+                                                                       \
+  NOTE:  As a convenience for standalone deployments, top-level meta   \
+         packages may be provided which bind a particular theme to     \
+         these certificate server packages.                            \
+                                                                       \
+%{nil}
+
+%description %{overview}
+
+
+%package -n       pki-symkey
+Summary:          Symmetric Key JNI Package
+Group:            System Environment/Libraries
+
+Requires:         java >= 1:1.6.0
+Requires:         nss
+Requires:         jpackage-utils >= 0:1.7.5-10
+%if 0%{?rhel} || 0%{?fedora} >= 19
+Requires:         jss >= 4.2.6-28
+%else
+Requires:         jss >= 4.2.6-24
+%endif
+
+Provides:         symkey = %{version}-%{release}
+
+Obsoletes:        symkey < %{version}-%{release}
+
+%description -n   pki-symkey
+The Symmetric Key Java Native Interface (JNI) package supplies various native
+symmetric key operations to Java programs.
+
+This package is a part of the PKI Core used by the Certificate System.
+
+%{overview}
+
+
+%package -n       pki-base
+Summary:          Certificate System - PKI Framework
+Group:            System Environment/Base
+
+BuildArch:        noarch
+
+Provides:         pki-common = %{version}-%{release}
+Provides:         pki-util = %{version}-%{release}
+
+Obsoletes:        pki-common < %{version}-%{release}
+Obsoletes:        pki-util < %{version}-%{release}
+
+Conflicts:        freeipa-server < 3.0.0
+Requires:         apache-commons-cli
+Requires:         apache-commons-codec
+Requires:         apache-commons-io
+Requires:         apache-commons-lang
+Requires:         apache-commons-logging
+Requires:         java >= 1:1.6.0
+Requires:         javassist
+Requires:         jettison
+Requires:         jpackage-utils >= 0:1.7.5-10
+%if 0%{?rhel} || 0%{?fedora} >= 19
+Requires:         jss >= 4.2.6-28
+%else
+Requires:         jss >= 4.2.6-24
+%endif
+Requires:         ldapjdk
+Requires:         python-ldap
+Requires:         python-lxml
+Requires:         python-requests >= 1.1.0-3
+%if  0%{?rhel}
+Requires:    resteasy-base-atom-provider
+Requires:    resteasy-base-jaxb-provider
+Requires:    resteasy-base-jaxrs
+Requires:    resteasy-base-jaxrs-api
+Requires:    resteasy-base-jettison-provider
+%else
+Requires:         resteasy >= 2.3.2-1
+%endif
+Requires:         xalan-j2
+Requires:         xerces-j2
+Requires:         xml-commons-apis
+Requires:         xml-commons-resolver
+
+%description -n   pki-base
+The PKI Framework contains the common and client libraries and utilities.
+This package is a part of the PKI Core used by the Certificate System.
+
+%{overview}
+
+
+%package -n       pki-tools
+Summary:          Certificate System - PKI Tools
+Group:            System Environment/Base
+
+Provides:         pki-native-tools = %{version}-%{release}
+Provides:         pki-java-tools = %{version}-%{release}
+
+Obsoletes:        pki-native-tools < %{version}-%{release}
+Obsoletes:        pki-java-tools < %{version}-%{release}
+
+Requires:         openldap-clients
+Requires:         nss
+Requires:         nss-tools
+Requires:         java >= 1:1.6.0
+Requires:         pki-base = %{version}-%{release}
+Requires:         jpackage-utils >= 0:1.7.5-10
+
+%description -n   pki-tools
+This package contains PKI executables that can be used to help make
+Certificate System into a more complete and robust PKI solution.
+
+This package is a part of the PKI Core used by the Certificate System.
+
+%{overview}
+
+
+%package -n       pki-server
+Summary:          Certificate System - PKI Server Framework
+Group:            System Environment/Base
+
+BuildArch:        noarch
+
+Provides:         pki-deploy = %{version}-%{release}
+Provides:         pki-setup = %{version}-%{release}
+Provides:         pki-silent = %{version}-%{release}
+
+Obsoletes:        pki-deploy < %{version}-%{release}
+Obsoletes:        pki-setup < %{version}-%{release}
+Obsoletes:        pki-silent < %{version}-%{release}
+
+Requires:         java >= 1:1.6.0
+Requires:         java-atk-wrapper
+Requires:         net-tools
+Requires:         perl(File::Slurp)
+Requires:         perl(XML::LibXML)
+Requires:         perl-Crypt-SSLeay
+Requires:         policycoreutils
+Requires:         openldap-clients
+Requires:         pki-base = %{version}-%{release}
+Requires:         pki-symkey = %{version}-%{release}
+Requires:         pki-tools = %{version}-%{release}
+
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+Requires:         pki-selinux = %{version}-%{release}
+%else
+Requires:         selinux-policy-base >= 3.11.1-43
+Obsoletes:        pki-selinux
+Requires:         tomcat >= 7.0.27
+%endif
+
+Requires:         velocity
+Requires(post):   systemd-units
+Requires(preun):  systemd-units
+Requires(postun): systemd-units
+Requires:         tomcat >= 7.0.27
+%if 0%{?rhel} || 0%{?fedora} >= 19
+Requires:         tomcatjss >= 7.1.0
+%endif
+%if 0%{?fedora} == 18
+Requires:         tomcatjss >= 7.0.0-4
+%endif
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+Requires:         tomcatjss >= 6.0.2
+%endif
+
+%description -n   pki-server
+The PKI Server Framework is required by the following four PKI subsystems:
+
+    the Certificate Authority (CA),
+    the Data Recovery Manager (DRM),
+    the Online Certificate Status Protocol (OCSP) Manager, and
+    the Token Key Service (TKS).
+
+This package is a part of the PKI Core used by the Certificate System.
+The package contains scripts to create and remove PKI subsystems.
+
+%{overview}
+
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+%package -n       pki-selinux
+Summary:          Certificate System - PKI Selinux Policies
+Group:            System Environment/Base
+
+BuildArch:        noarch
+
+Requires:         policycoreutils
+Requires:         selinux-policy-targeted
+Conflicts:        selinux-policy-base >= 3.11.1-43
+Requires:         selinux-policy >= 3.10.0-151
+
+%description -n   pki-selinux
+Selinux policies for the PKI components.
+
+This package is a part of the PKI Core used by the Certificate System.
+
+%{overview}
+%endif
+
+%package -n       pki-ca
+Summary:          Certificate System - Certificate Authority
+Group:            System Environment/Daemons
+
+BuildArch:        noarch
+
+Requires:         java >= 1:1.6.0
+Requires:         pki-server = %{version}-%{release}
+Requires(post):   systemd-units
+Requires(preun):  systemd-units
+Requires(postun): systemd-units
+
+%description -n   pki-ca
+The Certificate Authority (CA) is a required PKI subsystem which issues,
+renews, revokes, and publishes certificates as well as compiling and
+publishing Certificate Revocation Lists (CRLs).
+
+The Certificate Authority can be configured as a self-signing Certificate
+Authority, where it is the root CA, or it can act as a subordinate CA,
+where it obtains its own signing certificate from a public CA.
+
+This package is one of the top-level java-based Tomcat PKI subsystems
+provided by the PKI Core used by the Certificate System.
+
+%{overview}
+
+
+%if ! 0%{?rhel}
+%package -n       pki-kra
+Summary:          Certificate System - Data Recovery Manager
+Group:            System Environment/Daemons
+
+BuildArch:        noarch
+
+Requires:         java >= 1:1.6.0
+Requires:         pki-server = %{version}-%{release}
+Requires(post):   systemd-units
+Requires(preun):  systemd-units
+Requires(postun): systemd-units
+
+%description -n   pki-kra
+The Data Recovery Manager (DRM) is an optional PKI subsystem that can act
+as a Key Recovery Authority (KRA).  When configured in conjunction with the
+Certificate Authority (CA), the DRM stores private encryption keys as part of
+the certificate enrollment process.  The key archival mechanism is triggered
+when a user enrolls in the PKI and creates the certificate request.  Using the
+Certificate Request Message Format (CRMF) request format, a request is
+generated for the user's private encryption key.  This key is then stored in
+the DRM which is configured to store keys in an encrypted format that can only
+be decrypted by several agents requesting the key at one time, providing for
+protection of the public encryption keys for the users in the PKI deployment.
+
+Note that the DRM archives encryption keys; it does NOT archive signing keys,
+since such archival would undermine non-repudiation properties of signing keys.
+
+This package is one of the top-level java-based Tomcat PKI subsystems
+provided by the PKI Core used by the Certificate System.
+
+%{overview}
+%endif
+
+
+%if ! 0%{?rhel}
+%package -n       pki-ocsp
+Summary:          Certificate System - Online Certificate Status Protocol Manager
+Group:            System Environment/Daemons
+
+BuildArch:        noarch
+
+Requires:         java >= 1:1.6.0
+Requires:         pki-server = %{version}-%{release}
+Requires(post):   systemd-units
+Requires(preun):  systemd-units
+Requires(postun): systemd-units
+
+%description -n   pki-ocsp
+The Online Certificate Status Protocol (OCSP) Manager is an optional PKI
+subsystem that can act as a stand-alone OCSP service.  The OCSP Manager
+performs the task of an online certificate validation authority by enabling
+OCSP-compliant clients to do real-time verification of certificates.  Note
+that an online certificate-validation authority is often referred to as an
+OCSP Responder.
+
+Although the Certificate Authority (CA) is already configured with an
+internal OCSP service.  An external OCSP Responder is offered as a separate
+subsystem in case the user wants the OCSP service provided outside of a
+firewall while the CA resides inside of a firewall, or to take the load of
+requests off of the CA.
+
+The OCSP Manager can receive Certificate Revocation Lists (CRLs) from
+multiple CA servers, and clients can query the OCSP Manager for the
+revocation status of certificates issued by all of these CA servers.
+
+When an instance of OCSP Manager is set up with an instance of CA, and
+publishing is set up to this OCSP Manager, CRLs are published to it
+whenever they are issued or updated.
+
+This package is one of the top-level java-based Tomcat PKI subsystems
+provided by the PKI Core used by the Certificate System.
+
+%{overview}
+%endif
+
+
+%if ! 0%{?rhel}
+%package -n       pki-tks
+Summary:          Certificate System - Token Key Service
+Group:            System Environment/Daemons
+
+BuildArch:        noarch
+
+Requires:         java >= 1:1.6.0
+Requires:         pki-server = %{version}-%{release}
+Requires(post):   systemd-units
+Requires(preun):  systemd-units
+Requires(postun): systemd-units
+
+%description -n   pki-tks
+The Token Key Service (TKS) is an optional PKI subsystem that manages the
+master key(s) and the transport key(s) required to generate and distribute
+keys for hardware tokens.  TKS provides the security between tokens and an
+instance of Token Processing System (TPS), where the security relies upon the
+relationship between the master key and the token keys.  A TPS communicates
+with a TKS over SSL using client authentication.
+
+TKS helps establish a secure channel (signed and encrypted) between the token
+and the TPS, provides proof of presence of the security token during
+enrollment, and supports key changeover when the master key changes on the
+TKS.  Tokens with older keys will get new token keys.
+
+Because of the sensitivity of the data that TKS manages, TKS should be set up
+behind the firewall with restricted access.
+
+This package is one of the top-level java-based Tomcat PKI subsystems
+provided by the PKI Core used by the Certificate System.
+
+%{overview}
+%endif
+
+
+%package -n       pki-javadoc
+Summary:          Certificate System - PKI Framework Javadocs
+Group:            Documentation
+
+BuildArch:        noarch
+
+Provides:         pki-util-javadoc = %{version}-%{release}
+Provides:         pki-java-tools-javadoc = %{version}-%{release}
+Provides:         pki-common-javadoc = %{version}-%{release}
+
+Obsoletes:        pki-util-javadoc < %{version}-%{release}
+Obsoletes:        pki-java-tools-javadoc < %{version}-%{release}
+Obsoletes:        pki-common-javadoc < %{version}-%{release}
+
+%description -n   pki-javadoc
+This documentation pertains exclusively to version %{version} of
+the PKI Framework and Tools.
+
+This package is a part of the PKI Core used by the Certificate System.
+
+%{overview}
+
+
+%prep
+%setup -q -n %{name}-%{version}%{?prerel}
+
+%patch0 -p1
+%patch1 -p1
+%patch2 -p1
+%patch3 -p1
+%patch4 -p1
+%patch5 -p1
+%patch6 -p1
+
+%clean
+%{__rm} -rf %{buildroot}
+
+%build
+%{__mkdir_p} build
+cd build
+%cmake -DVERSION=%{version}-%{release} \
+	-DVAR_INSTALL_DIR:PATH=/var \
+	-DBUILD_PKI_CORE:BOOL=ON \
+	-DJAVA_LIB_INSTALL_DIR=%{_jnidir} \
+	-DSYSTEMD_LIB_INSTALL_DIR=%{_unitdir} \
+%if 0%{?rhel}
+	-DRESTEASY_LIB=/usr/share/java/resteasy-base \
+%else
+	-DRESTEASY_LIB=/usr/share/java/resteasy \
+%endif
+	%{?_without_javadoc:-DWITH_JAVADOC:BOOL=OFF} \
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+        -DBUILD_PKI_SELINUX:BOOL=ON \
+%endif
+%if 0%{?rhel}
+        -DBUILD_PKI_KRA:BOOL=OFF \
+        -DBUILD_PKI_OCSP:BOOL=OFF \
+        -DBUILD_PKI_TKS:BOOL=OFF \
+%endif
+	..
+%{__make} VERBOSE=1 %{?_smp_mflags} all
+# %{__make} VERBOSE=1 %{?_smp_mflags} test
+
+
+%install
+%{__rm} -rf %{buildroot}
+cd build
+%{__make} install DESTDIR=%{buildroot} INSTALL="install -p"
+
+# Fedora 18 and 17:  Substitute 'tomcat7jss.jar' for 'tomcatjss.jar'
+%if ! 0%{?rhel} && 0%{?fedora} <= 18
+	sed -i -e 's/grant codeBase "file:\/usr\/share\/java\/tomcatjss.jar" {/grant codeBase "file:\/usr\/share\/java\/tomcat7jss.jar" {/' %{buildroot}%{_datadir}/pki/server/conf/pki.policy
+	sed -i -e 's/pki_tomcatjss_jar=\/usr\/share\/java\/tomcatjss.jar/pki_tomcatjss_jar=\/usr\/share\/java\/tomcat7jss.jar/' %{buildroot}%{_sysconfdir}/pki/default.cfg
+	sed -i -e 's/        \[tomcatjss.jar\]=\${java_dir}\/tomcatjss.jar/        \[tomcatjss.jar\]=\${java_dir}\/tomcat7jss.jar/' %{buildroot}%{_datadir}/pki/scripts/operations
+%endif
+
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%{__mkdir_p} %{buildroot}%{_sysconfdir}/tmpfiles.d
+# generate 'pki-ca.conf' under the 'tmpfiles.d' directory
+echo "D /run/lock/pki 0755 root root -"    >  %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ca.conf
+echo "D /run/lock/pki/ca 0755 root root -" >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ca.conf
+echo "D /run/pki 0755 root root -"     >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ca.conf
+echo "D /run/pki/ca 0755 root root -"  >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ca.conf
+%if ! 0%{?rhel}
+# generate 'pki-kra.conf' under the 'tmpfiles.d' directory
+echo "D /run/lock/pki 0755 root root -"     >  %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-kra.conf
+echo "D /run/lock/pki/kra 0755 root root -" >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-kra.conf
+echo "D /run/pki 0755 root root -"      >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-kra.conf
+echo "D /run/pki/kra 0755 root root -"  >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-kra.conf
+%endif
+%if ! 0%{?rhel}
+# generate 'pki-ocsp.conf' under the 'tmpfiles.d' directory
+echo "D /run/lock/pki 0755 root root -"      >  %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ocsp.conf
+echo "D /run/lock/pki/ocsp 0755 root root -" >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ocsp.conf
+echo "D /run/pki 0755 root root -"       >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ocsp.conf
+echo "D /run/pki/ocsp 0755 root root -"  >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-ocsp.conf
+%endif
+# generate 'pki-tomcat.conf' under the 'tmpfiles.d' directory
+echo "D /run/lock/pki 0755 root root -"    >  %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tomcat.conf
+echo "D /run/lock/pki/tomcat 0755 root root -" >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tomcat.conf
+echo "D /run/pki 0755 root root -"     >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tomcat.conf
+echo "D /run/pki/tomcat 0755 root root -"  >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tomcat.conf
+%if ! 0%{?rhel}
+# generate 'pki-tks.conf' under the 'tmpfiles.d' directory
+echo "D /run/lock/pki 0755 root root -"     >  %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tks.conf
+echo "D /run/lock/pki/tks 0755 root root -" >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tks.conf
+echo "D /run/pki 0755 root root -"      >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tks.conf
+echo "D /run/pki/tks 0755 root root -"  >> %{buildroot}%{_sysconfdir}/tmpfiles.d/pki-tks.conf
+%endif
+
+%{__rm} %{buildroot}%{_initrddir}/pki-cad
+%if ! 0%{?rhel}
+%{__rm} %{buildroot}%{_initrddir}/pki-krad
+%endif
+%if ! 0%{?rhel}
+%{__rm} %{buildroot}%{_initrddir}/pki-ocspd
+%endif
+%if ! 0%{?rhel}
+%{__rm} %{buildroot}%{_initrddir}/pki-tksd
+%endif
+
+%{__rm} -rf %{buildroot}%{_datadir}/pki/server/lib
+
+# tomcat6 has changed how TOMCAT_LOG is used.
+# Need to adjust accordingly
+# This macro will be executed in the postinstall scripts
+%define fix_tomcat_log() (                                                   \
+if [ -d /etc/sysconfig/pki/%i ]; then                                        \
+  for F in `find /etc/sysconfig/pki/%1 -type f`; do                          \
+    instance=`basename $F`                                                   \
+    if [ -f /etc/sysconfig/$instance ]; then                                 \
+        sed -i -e 's/catalina.out/tomcat-initd.log/' /etc/sysconfig/$instance \
+    fi                                                                       \
+  done                                                                       \
+fi                                                                           \
+)
+%{__mkdir_p} %{buildroot}%{_localstatedir}/log/pki
+%{__mkdir_p} %{buildroot}%{_sharedstatedir}/pki
+
+%if ! 0%{?rhel} && 0%{?fedora} >= 19
+%pretrans -n pki-base -p <lua>
+function test(a)
+    if posix.stat(a) then
+        for f in posix.files(a) do
+            if f~=".." and f~="." then
+                return true
+            end
+        end
+    end
+    return false
+end
+
+if (test("/etc/sysconfig/pki/ca") or
+    test("/etc/sysconfig/pki/kra") or
+    test("/etc/sysconfig/pki/ocsp") or
+    test("/etc/sysconfig/pki/tks")) then
+   msg = "Unable to upgrade to Fedora 19.  There are Dogtag 9 instances\n" ..
+         "that will no longer work since they require Tomcat 6, and \n" ..
+         "Tomcat 6 is no longer available in Fedora 19.\n\n" ..
+         "Please follow these instructions to migrate the instances to \n" ..
+         "Dogtag 10:\n\n" ..
+         "http://pki.fedoraproject.org/wiki/Migrating_Dogtag_9_Instances_to_Dogtag_10"
+   error(msg)
+end
+%endif
+
+%post -n pki-base
+
+%if ! 0%{?rhel} && 0%{?fedora} <= 18
+if [ "`uname -i`" == "x86_64" ]
+then
+	sed -i -e 's/^JNI_JAR_DIR=.*$/JNI_JAR_DIR=\/usr\/lib64\/java/' %{_datadir}/pki/etc/pki.conf
+else
+	sed -i -e 's/^JNI_JAR_DIR=.*$/JNI_JAR_DIR=\/usr\/lib\/java/' %{_datadir}/pki/etc/pki.conf
+fi
+%else
+	sed -i -e 's/^JNI_JAR_DIR=.*$/JNI_JAR_DIR=\/usr\/lib\/java/' %{_datadir}/pki/etc/pki.conf
+%endif
+
+if [ $1 -eq 1 ]
+then
+    # On RPM installation create system upgrade tracker
+    echo "Configuration-Version: %{version}" > %{_sysconfdir}/pki/pki.version
+
+else
+    # On RPM upgrade run system upgrade
+    echo "Upgrading system at `/bin/date`." >> /var/log/pki/pki-upgrade-%{version}.log 2>&1
+    /sbin/pki-upgrade --silent >> /var/log/pki/pki-upgrade-%{version}.log 2>&1
+    echo >> /var/log/pki/pki-upgrade-%{version}.log 2>&1
+fi
+
+%postun -n pki-base
+
+if [ $1 -eq 0 ]
+then
+    # On RPM uninstallation remove system upgrade tracker
+    rm -f %{_sysconfdir}/pki/pki.version
+fi
+
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+%pre -n pki-selinux
+%saveFileContext targeted
+
+%post -n pki-selinux
+semodule -s targeted -i %{_datadir}/selinux/modules/pki.pp
+%relabel targeted
+
+%preun -n pki-selinux
+if [ $1 = 0 ]; then
+     %saveFileContext targeted
+fi
+
+%postun -n pki-selinux
+if [ $1 = 0 ]; then
+     semodule -s targeted -r pki
+     %relabel targeted
+fi
+%endif
+
+%post -n pki-ca
+# Attempt to update ALL old "CA" instances to "systemd"
+if [ -d /etc/sysconfig/pki/ca ]; then
+    for inst in `ls /etc/sysconfig/pki/ca`; do
+        if [ ! -e "/etc/systemd/system/pki-cad.target.wants/pki-cad@${inst}.service" ]; then
+            ln -s "/lib/systemd/system/pki-cad@.service" \
+                  "/etc/systemd/system/pki-cad.target.wants/pki-cad@${inst}.service"
+            [ -L /var/lib/${inst}/${inst} ] && unlink /var/lib/${inst}/${inst}
+            ln -s /usr/sbin/tomcat6-sysd /var/lib/${inst}/${inst}
+
+            if [ -e /var/run/${inst}.pid ]; then
+                kill -9 `cat /var/run/${inst}.pid` || :
+                rm -f /var/run/${inst}.pid
+                echo "pkicreate.systemd.servicename=pki-cad@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+                /bin/systemctl daemon-reload >/dev/null 2>&1 || :
+                /bin/systemctl restart pki-cad@${inst}.service || :
+            else 
+                echo "pkicreate.systemd.servicename=pki-cad@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+            fi
+        else
+            # Conditionally restart this Dogtag 9 instance
+            /bin/systemctl condrestart pki-cad@${inst}.service
+        fi
+    done
+fi
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+%fix_tomcat_log ca
+
+
+%if ! 0%{?rhel}
+%post -n pki-kra
+# Attempt to update ALL old "KRA" instances to "systemd"
+if [ -d /etc/sysconfig/pki/kra ]; then
+    for inst in `ls /etc/sysconfig/pki/kra`; do
+        if [ ! -e "/etc/systemd/system/pki-krad.target.wants/pki-krad@${inst}.service" ]; then
+            ln -s "/lib/systemd/system/pki-krad@.service" \
+                  "/etc/systemd/system/pki-krad.target.wants/pki-krad@${inst}.service"
+            [ -L /var/lib/${inst}/${inst} ] && unlink /var/lib/${inst}/${inst}
+            ln -s /usr/sbin/tomcat6-sysd /var/lib/${inst}/${inst}
+
+            if [ -e /var/run/${inst}.pid ]; then
+                kill -9 `cat /var/run/${inst}.pid` || :
+                rm -f /var/run/${inst}.pid
+                echo "pkicreate.systemd.servicename=pki-krad@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+                /bin/systemctl daemon-reload >/dev/null 2>&1 || :
+                /bin/systemctl restart pki-krad@${inst}.service || :
+            else 
+                echo "pkicreate.systemd.servicename=pki-krad@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+            fi
+        else
+            # Conditionally restart this Dogtag 9 instance
+            /bin/systemctl condrestart pki-krad@${inst}.service
+        fi
+    done
+fi
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+%fix_tomcat_log kra
+%endif
+
+
+%if ! 0%{?rhel}
+%post -n pki-ocsp
+# Attempt to update ALL old "OCSP" instances to "systemd"
+if [ -d /etc/sysconfig/pki/ocsp ]; then
+    for inst in `ls /etc/sysconfig/pki/ocsp`; do
+        if [ ! -e "/etc/systemd/system/pki-ocspd.target.wants/pki-ocspd@${inst}.service" ]; then
+            ln -s "/lib/systemd/system/pki-ocspd@.service" \
+                  "/etc/systemd/system/pki-ocspd.target.wants/pki-ocspd@${inst}.service"
+            [ -L /var/lib/${inst}/${inst} ] && unlink /var/lib/${inst}/${inst}
+            ln -s /usr/sbin/tomcat6-sysd /var/lib/${inst}/${inst}
+
+            if [ -e /var/run/${inst}.pid ]; then
+                kill -9 `cat /var/run/${inst}.pid` || :
+                rm -f /var/run/${inst}.pid
+                echo "pkicreate.systemd.servicename=pki-ocspd@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+                /bin/systemctl daemon-reload >/dev/null 2>&1 || :
+                /bin/systemctl restart pki-ocspd@${inst}.service || :
+            else 
+                echo "pkicreate.systemd.servicename=pki-ocspd@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+            fi
+        else
+            # Conditionally restart this Dogtag 9 instance
+            /bin/systemctl condrestart pki-ocspd@${inst}.service
+        fi
+    done
+fi
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+%fix_tomcat_log ocsp
+%endif
+
+
+%if ! 0%{?rhel}
+%post -n pki-tks
+# Attempt to update ALL old "TKS" instances to "systemd"
+if [ -d /etc/sysconfig/pki/tks ]; then
+    for inst in `ls /etc/sysconfig/pki/tks`; do
+        if [ ! -e "/etc/systemd/system/pki-tksd.target.wants/pki-tksd@${inst}.service" ]; then
+            ln -s "/lib/systemd/system/pki-tksd@.service" \
+                  "/etc/systemd/system/pki-tksd.target.wants/pki-tksd@${inst}.service"
+            [ -L /var/lib/${inst}/${inst} ] && unlink /var/lib/${inst}/${inst}
+            ln -s /usr/sbin/tomcat6-sysd /var/lib/${inst}/${inst}
+
+            if [ -e /var/run/${inst}.pid ]; then
+                kill -9 `cat /var/run/${inst}.pid` || :
+                rm -f /var/run/${inst}.pid
+                echo "pkicreate.systemd.servicename=pki-tksd@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+                /bin/systemctl daemon-reload >/dev/null 2>&1 || :
+                /bin/systemctl restart pki-tksd@${inst}.service || :
+            else 
+                echo "pkicreate.systemd.servicename=pki-tksd@${inst}.service" >> \
+                     /var/lib/${inst}/conf/CS.cfg || :
+            fi
+        else
+            # Conditionally restart this Dogtag 9 instance
+            /bin/systemctl condrestart pki-tksd@${inst}.service
+        fi
+    done
+fi
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+%fix_tomcat_log tks
+%endif
+
+
+%post -n pki-server
+## NOTE:  At this time, NO attempt has been made to update ANY PKI subsystem
+##        from EITHER 'sysVinit' OR previous 'systemd' processes to the new
+##        PKI deployment process
+
+echo "Upgrading server at `/bin/date`." >> /var/log/pki/pki-server-upgrade-%{version}.log 2>&1
+/sbin/pki-server-upgrade --silent >> /var/log/pki/pki-server-upgrade-%{version}.log 2>&1
+echo >> /var/log/pki/pki-server-upgrade-%{version}.log 2>&1
+
+
+%preun -n pki-ca
+if [ $1 = 0 ] ; then
+    /bin/systemctl --no-reload disable pki-cad.target > /dev/null 2>&1 || :
+    /bin/systemctl stop pki-cad.target > /dev/null 2>&1 || :
+fi
+
+
+%if ! 0%{?rhel}
+%preun -n pki-kra
+if [ $1 = 0 ] ; then
+    /bin/systemctl --no-reload disable pki-krad.target > /dev/null 2>&1 || :
+    /bin/systemctl stop pki-krad.target > /dev/null 2>&1 || :
+fi
+%endif
+
+
+%if ! 0%{?rhel}
+%preun -n pki-ocsp
+if [ $1 = 0 ] ; then
+    /bin/systemctl --no-reload disable pki-ocspd.target > /dev/null 2>&1 || :
+    /bin/systemctl stop pki-ocspd.target > /dev/null 2>&1 || :
+fi
+%endif
+
+
+%if ! 0%{?rhel}
+%preun -n pki-tks
+if [ $1 = 0 ] ; then
+    /bin/systemctl --no-reload disable pki-tksd.target > /dev/null 2>&1 || :
+    /bin/systemctl stop pki-tksd.target > /dev/null 2>&1 || :
+fi
+%endif
+
+
+## %preun -n pki-server
+## NOTE:  At this time, NO attempt has been made to update ANY PKI subsystem
+##        from EITHER 'sysVinit' OR previous 'systemd' processes to the new
+##        PKI deployment process
+
+
+%postun -n pki-ca
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+if [ "$1" -ge "1" ] ; then
+    /bin/systemctl try-restart pki-cad.target >/dev/null 2>&1 || :
+fi
+
+
+%if ! 0%{?rhel}
+%postun -n pki-kra
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+if [ "$1" -ge "1" ] ; then
+    /bin/systemctl try-restart pki-krad.target >/dev/null 2>&1 || :
+fi
+%endif
+
+
+%if ! 0%{?rhel}
+%postun -n pki-ocsp
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+if [ "$1" -ge "1" ] ; then
+    /bin/systemctl try-restart pki-ocspd.target >/dev/null 2>&1 || :
+fi
+%endif
+
+
+%if ! 0%{?rhel}
+%postun -n pki-tks
+/bin/systemctl daemon-reload >/dev/null 2>&1 || :
+if [ "$1" -ge "1" ] ; then
+    /bin/systemctl try-restart pki-tksd.target >/dev/null 2>&1 || :
+fi
+%endif
+
+
+## %postun -n pki-server
+## NOTE:  At this time, NO attempt has been made to update ANY PKI subsystem
+##        from EITHER 'sysVinit' OR previous 'systemd' processes to the new
+##        PKI deployment process
+
+%files -n pki-symkey
+%defattr(-,root,root,-)
+%doc base/symkey/LICENSE
+%{_jnidir}/symkey.jar
+%{_libdir}/symkey/
+
+
+%files -n pki-base
+%defattr(-,root,root,-)
+%doc base/common/LICENSE
+%dir %{_datadir}/pki
+%{_datadir}/pki/VERSION
+%{_datadir}/pki/etc/
+%{_datadir}/pki/upgrade/
+%dir %{_sysconfdir}/pki
+%config(noreplace) %{_sysconfdir}/pki/pki.conf
+%dir %{_javadir}/pki
+%{_javadir}/pki/pki-cmsutil.jar
+%{_javadir}/pki/pki-nsutil.jar
+%{_javadir}/pki/pki-certsrv.jar
+%dir %{python_sitelib}/pki
+%{python_sitelib}/pki/*.py
+%{python_sitelib}/pki/*.pyc
+%{python_sitelib}/pki/*.pyo
+%dir %{_localstatedir}/log/pki
+%{_sbindir}/pki-upgrade
+%{_mandir}/man8/pki-upgrade.8.gz
+
+%files -n pki-tools
+%defattr(-,root,root,-)
+%doc base/native-tools/LICENSE base/native-tools/doc/README
+%{_bindir}/pki
+%{_bindir}/p7tool
+%{_bindir}/revoker
+%{_bindir}/setpin
+%{_bindir}/sslget
+%{_bindir}/tkstool
+%{_datadir}/pki/native-tools/
+%{_bindir}/AtoB
+%{_bindir}/AuditVerify
+%{_bindir}/BtoA
+%{_bindir}/CMCEnroll
+%{_bindir}/CMCRequest
+%{_bindir}/CMCResponse
+%{_bindir}/CMCRevoke
+%{_bindir}/CRMFPopClient
+%{_bindir}/DRMTool
+%{_bindir}/ExtJoiner
+%{_bindir}/GenExtKeyUsage
+%{_bindir}/GenIssuerAltNameExt
+%{_bindir}/GenSubjectAltNameExt
+%{_bindir}/HttpClient
+%{_bindir}/OCSPClient
+%{_bindir}/PKCS10Client
+%{_bindir}/PKCS12Export
+%{_bindir}/PrettyPrintCert
+%{_bindir}/PrettyPrintCrl
+%{_bindir}/TokenInfo
+%{_javadir}/pki/pki-tools.jar
+%{_datadir}/pki/java-tools/
+%{_mandir}/man1/pki.1.gz
+
+
+%files -n pki-server
+%defattr(-,root,root,-)
+%doc base/common/THIRD_PARTY_LICENSES
+%doc base/server/LICENSE
+%{_sysconfdir}/pki/default.cfg
+%{_sbindir}/pkispawn
+%{_sbindir}/pkidestroy
+%{_sbindir}/pki-server-upgrade
+#%{_bindir}/pki-setup-proxy
+%{python_sitelib}/pki/deployment/
+%{python_sitelib}/pki/server/
+%dir %{_datadir}/pki/deployment
+%{_datadir}/pki/deployment/config/
+%dir %{_datadir}/pki/scripts
+%{_datadir}/pki/scripts/operations
+%{_datadir}/pki/scripts/pkicommon.pm
+%{_datadir}/pki/scripts/functions
+%{_datadir}/pki/scripts/pki_apache_initscript
+%dir %{_localstatedir}/lock/pki
+%dir %{_localstatedir}/run/pki
+%{_bindir}/pkidaemon
+%dir %{_sysconfdir}/systemd/system/pki-tomcatd.target.wants
+%{_unitdir}/pki-tomcatd@.service
+%{_unitdir}/pki-tomcatd.target
+%{_javadir}/pki/pki-cms.jar
+%{_javadir}/pki/pki-cmsbundle.jar
+%{_javadir}/pki/pki-cmscore.jar
+%{_javadir}/pki/pki-silent.jar
+%{_javadir}/pki/pki-tomcat.jar
+%dir %{_localstatedir}/lock/pki/tomcat
+%dir %{_localstatedir}/run/pki/tomcat
+%dir %{_sharedstatedir}/pki
+%{_bindir}/pkicreate
+%{_bindir}/pkiremove
+%{_bindir}/pki-setup-proxy
+%{_bindir}/pkisilent
+%{_datadir}/pki/silent/
+%{_bindir}/pkicontrol
+%{_mandir}/man5/pki_default.cfg.5.gz
+%{_mandir}/man8/pki-server-upgrade.8.gz
+%{_mandir}/man8/pkidestroy.8.gz
+%{_mandir}/man8/pkispawn.8.gz
+
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%config(noreplace) %{_sysconfdir}/tmpfiles.d/pki-tomcat.conf
+
+%{_datadir}/pki/setup/
+%{_datadir}/pki/server/
+
+%if ! 0%{?rhel} && 0%{?fedora} <= 17
+%files -n pki-selinux
+%defattr(-,root,root,-)
+%doc base/selinux/LICENSE
+%{_datadir}/selinux/modules/pki.pp
+%endif
+
+%files -n pki-ca
+%defattr(-,root,root,-)
+%doc base/ca/LICENSE
+%dir %{_sysconfdir}/systemd/system/pki-cad.target.wants
+%{_unitdir}/pki-cad@.service
+%{_unitdir}/pki-cad.target
+%{_javadir}/pki/pki-ca.jar
+%dir %{_datadir}/pki/ca
+%{_datadir}/pki/ca/conf/
+%{_datadir}/pki/ca/emails/
+%dir %{_datadir}/pki/ca/profiles
+%{_datadir}/pki/ca/profiles/ca/
+%{_datadir}/pki/ca/setup/
+%{_datadir}/pki/ca/webapps/
+%dir %{_localstatedir}/lock/pki/ca
+%dir %{_localstatedir}/run/pki/ca
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%config(noreplace) %{_sysconfdir}/tmpfiles.d/pki-ca.conf
+
+
+%if ! 0%{?rhel}
+%files -n pki-kra
+%defattr(-,root,root,-)
+%doc base/kra/LICENSE
+%dir %{_sysconfdir}/systemd/system/pki-krad.target.wants
+%{_unitdir}/pki-krad@.service
+%{_unitdir}/pki-krad.target
+%{_javadir}/pki/pki-kra.jar
+%dir %{_datadir}/pki/kra
+%{_datadir}/pki/kra/conf/
+%{_datadir}/pki/kra/setup/
+%{_datadir}/pki/kra/webapps/
+%dir %{_localstatedir}/lock/pki/kra
+%dir %{_localstatedir}/run/pki/kra
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%config(noreplace) %{_sysconfdir}/tmpfiles.d/pki-kra.conf
+%endif
+
+
+%if ! 0%{?rhel}
+%files -n pki-ocsp
+%defattr(-,root,root,-)
+%doc base/ocsp/LICENSE
+%dir %{_sysconfdir}/systemd/system/pki-ocspd.target.wants
+%{_unitdir}/pki-ocspd@.service
+%{_unitdir}/pki-ocspd.target
+%{_javadir}/pki/pki-ocsp.jar
+%dir %{_datadir}/pki/ocsp
+%{_datadir}/pki/ocsp/conf/
+%{_datadir}/pki/ocsp/setup/
+%{_datadir}/pki/ocsp/webapps/
+%dir %{_localstatedir}/lock/pki/ocsp
+%dir %{_localstatedir}/run/pki/ocsp
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%config(noreplace) %{_sysconfdir}/tmpfiles.d/pki-ocsp.conf
+%endif
+
+
+%if ! 0%{?rhel}
+%files -n pki-tks
+%defattr(-,root,root,-)
+%doc base/tks/LICENSE
+%dir %{_sysconfdir}/systemd/system/pki-tksd.target.wants
+%{_unitdir}/pki-tksd@.service
+%{_unitdir}/pki-tksd.target
+%{_javadir}/pki/pki-tks.jar
+%dir %{_datadir}/pki/tks
+%{_datadir}/pki/tks/conf/
+%{_datadir}/pki/tks/setup/
+%{_datadir}/pki/tks/webapps/
+%dir %{_localstatedir}/lock/pki/tks
+%dir %{_localstatedir}/run/pki/tks
+# Details:
+#
+#     * https://fedoraproject.org/wiki/Features/var-run-tmpfs
+#     * https://fedoraproject.org/wiki/Tmpfiles.d_packaging_draft
+#
+%config(noreplace) %{_sysconfdir}/tmpfiles.d/pki-tks.conf
+%endif
+
+
+%if %{?_without_javadoc:0}%{!?_without_javadoc:1}
+%files -n pki-javadoc
+%defattr(-,root,root,-)
+%{_javadocdir}/pki-%{version}/
+%endif
+
+
+%changelog
+* Sat Nov 2 2013 Ade Lee <alee@redhat.com> 10.0.5-2
+- Trac #739, BZ#999722 - Fixed error handling in DoUnrevoke servlet.
+- Trac #775, BZ#1018628 - Fixed errors during Tomcat shutdown.
+- Trac #776, BZ#1024679 - Added missing link for apache-commons-io
+- Trac #781, BZ#1024445 - Admin cert signed with SHA1, should be SHA256
+- Trac #780 - Store authentication info in session.
+- Trac #763 - Backup upgrade tracker.
+- Trac #779 - Renamed some CLI commands.
+- Trac #743 - Fixed references to /var/run and /var/lock in tmpfiles.
+
+* Fri Sep 6 2013 Ade Lee <alee@redhat.com> 10.0.5-1
+- Roll release to next version
+
+* Fri Aug 2 2013 Ade Lee <alee@redhat.com> 10.0.4-2
+- Trac Ticket 699 - on upgrade to F19, CA fails to start.
+
+* Thu Jul 25 2013 Ade Lee <alee@redhat.com> 10.0.4-1
+- Change release number for official release
+
+* Wed Jul 24 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.4-0.4
+- Bugzilla Bug #986506 - Need to determine RPM packages to be excluded
+  from compose . . . (exclude pki-kra, pki-ocsp, and pki-tks from rhel 7)
+
+* Wed Jul 17 2013 Endi S. Dewata <edewata@redhat.com> 10.0.4-0.3
+- Added man pages for upgrade tools.
+- Cleaned up the code to install man pages.
+
+* Tue Jul 9 2013 Ade Lee <alee@redhat.com> 10.0.4-0.2
+- Bugzilla Bug 973224 -  resteasy-base must be split into subpackages
+  to simplify dependencies
+
+* Wed Jun 26 2013 Ade Lee <alee@redhat.com> 10.0.4-0.1
+- Roll release to next version
+
+* Mon Jun 10 2013 Ade Lee <alee@redhat.com> 10.0.3-2
+- TRAC Ticket 646 - PKCS12Export fails on F19 
+- Bugzilla Bug 961522 - allows key to be exported
+
+* Thu Jun 6 2013 Ade Lee <alee@redhat.com> 10.0.3-1
+- Change release number for official release.
+
+* Wed Jun 5 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.3-0.2
+- TRAC Ticket 606 - add restart / start at boot info to pkispawn man page
+- TRAC Ticket 610 - Document limitation in using GUI install
+- TRAC Ticket 629 - Package ownership of '/usr/share/pki/etc/' directory
+
+* Tue May 7 2013 Ade Lee <alee@redhat.com> 10.0.3-0.1
+- Roll release to next version.
+
+* Mon May 6 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-5
+- Fixed incorrect JNI_JAR_DIR.
+
+* Sat May 4 2013 Ade Lee <alee@redhat.com> 10.0.2-4
+- TRAC Ticket 605 Junit internal function used in TestRunner,
+  breaks F19 build
+
+* Sat May 4 2013 Ade Lee <alee@redhat.com> 10.0.2-3
+- TRAC Ticket 604 Added fallback methods for pkispawn tests
+
+* Mon Apr 29 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-2
+- Added default pki.conf in /usr/share/pki/etc
+- Create upgrade tracker on install and remove it on uninstall
+
+* Fri Apr 26 2013 Ade Lee <alee@redhat.com> 10.0.2-1
+- Change release number for official release.
+
+* Thu Apr 25 2013 Ade Lee <alee@redhat.com> 10.0.2-0.8
+- Added %pretrans script for f19
+- Added java-atk-wrapper dependency
+
+* Wed Apr 24 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.7
+- Added pki-server-upgrade script and pki.server module.
+- Call upgrade scripts in %post for pki-base and pki-server.
+
+* Tue Apr 23 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.6
+- Added dependency on commons-io.
+
+* Mon Apr 22 2013 Ade Lee <alee@redhat.com> 10.0.2-0.5
+- Add /var/log/pki and /var/lib/pki directories
+
+* Tue Apr 16 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.4
+- Run pki-upgrade on post server installation.
+
+* Mon Apr 15 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.3
+- Added dependency on python-lxml.
+
+* Fri Apr 5 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.2
+- Added pki-upgrade script.
+
+* Fri Apr 5 2013 Endi S. Dewata <edewata@redhat.com> 10.0.2-0.1
+- Updated version number to 10.0.2-0.1.
+
+* Fri Apr 5 2013 Endi S. Dewata <edewata@redhat.com> 10.0.1-9
+- Renamed base/deploy to base/server.
+- Moved pki.conf into pki-base.
+- Removed redundant pki/server folder declaration.
+
+* Tue Mar 19 2013 Ade Lee <alee@redhat.com> 10.0.1-8
+- Removed jython dependency
+
+* Mon Mar 11 2013 Endi S. Dewata <edewata@redhat.com> 10.0.1-7
+- Added minimum python-requests version.
+
+* Fri Mar 8 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.1-6
+- Bugzilla Bug #919476 - pkispawn crashes due to dangling symlink to jss4.jar
+
+* Thu Mar 7 2013 Endi S. Dewata <edewata@redhat.com> 10.0.1-5
+- Added dependency on python-requests.
+- Reorganized Python module packaging.
+
+* Thu Mar 7 2013 Endi S. Dewata <edewata@redhat.com> 10.0.1-4
+- Added dependency on python-ldap.
+
+* Mon Mar  4 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.1-3
+- TRAC Ticket #517 - Clean up theme dependencies
+- TRAC Ticket #518 - Remove UI dependencies from pkispawn . . .
+
+* Fri Mar  1 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.1-2
+- Removed runtime dependency on 'pki-server-theme' to resolve
+  Bugzilla Bug #916134 - unresolved dependency in pki-server: pki-server-theme
+
+* Tue Jan 15 2013 Ade Lee <alee@redhat.com> 10.0.1-1
+- TRAC Ticket 214 - Missing error description for duplicate user
+- TRAC Ticket 213 - Add nonces for cert revocation
+- TRAC Ticket 367 - pkidestroy does not remove connector
+- TRAC Ticket #430 - License for 3rd party code
+- Bugzilla Bug 839426 - [RFE] ECC CRL support for OCSP
+- Fix spec file to allow f17 to work with latest tomcatjss
+- TRAC Ticket 466 - Increase root CA validity to 20 years
+- TRAC Ticket 469 - Fix tomcatjss issue in spec files
+- TRAC Ticket 468 - pkispawn throws exception
+- TRAC Ticket 191 - Mapping HTTP Exceptions to HTTP error codes
+- TRAC Ticket 271 - Dogtag 10: Fix 'status' command in 'pkidaemon' . . .
+- TRAC Ticket 437 - Make admin cert p12 file location configurable
+- TRAC Ticket 393 - pkispawn fails when selinux is disabled
+- Punctuation and formatting changes in man pages
+- Revert to using default config file for pkidestroy
+- Hardcode setting of resteasy-lib for instance
+- TRAC Ticket 436 - Interpolation for pki_subsystem
+- TRAC Ticket 433 - Interpolation for paths
+- TRAC Ticket 435 - Identical instance id and instance name
+- TRAC Ticket 406 - Replace file dependencies with package dependencies
+
+* Wed Jan  9 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-5
+- TRAC Ticket #430 - License for 3rd party code
+
+* Fri Jan  4 2013 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-4
+- TRAC Ticket #469 - Dogtag 10: Fix tomcatjss issue in pki-core.spec and
+  dogtag-pki.spec . . .
+- TRAC Ticket #468 - pkispawn throws exception
+
+* Wed Dec 12 2012 Ade Lee <alee@redhat.com> 10.0.0-3
+- Replaced file dependencies with package dependencies
+
+* Mon Dec 10 2012 Ade Lee <alee@redhat.com> 10.0.0-2
+- Updated man pages
+
+* Fri Dec 7 2012 Ade Lee <alee@redhat.com> 10.0.0-1
+- Update to official release for rc1
+
+* Thu Dec  6 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.56.b3
+- TRAC Ticket #315 - Man pages for pkispawn/pkidestroy.
+- Added place-holders for 'pki.1' and 'pki_default.cfg.5' man pages.
+
+* Thu Dec 6 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.55.b3
+- Added system-wide configuration /etc/pki/pki.conf.
+- Removed redundant lines in %files.
+
+* Tue Dec 4 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.54.b3
+- Moved default deployment configuration to /etc/pki.
+
+* Mon Nov 19 2012 Ade Lee <alee@redhat.com> 10.0.0-0.53.b3
+- Cleaned up spec file to provide only support rhel 7+, f17+
+- Added resteasy-base dependency for rhel 7
+- Update cmake version
+
+* Mon Nov 12 2012 Ade Lee <alee@redhat.com> 10.0.0-0.52.b3
+- Update release to b3
+
+* Fri Nov 9 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.51.b2
+- Removed dependency on CA, KRA, OCSP, TKS theme packages.
+
+* Thu Nov 8 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.50.b2
+- Renamed pki-common-theme to pki-server-theme.
+
+* Thu Nov  8 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.49.b2
+- TRAC Ticket #395 - Dogtag 10: Add a Tomcat 7 runtime requirement to
+  'pki-server'
+
+* Mon Oct 29 2012 Ade Lee <alee@redhat.com> 10.0.0-0.48.b2
+- Update release to b2
+
+* Wed Oct 24 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.47.b1
+- TRAC Ticket #350 - Dogtag 10: Remove version numbers from PKI jar files . . .
+
+* Tue Oct 23 2012 Ade Lee <alee@redhat.com> 10.0.0-0.46.b1
+- Added Obsoletes for pki-selinux
+
+* Tue Oct 23 2012 Ade Lee <alee@redhat.com> 10.0.0-0.45.b1
+- Remove build of pki-selinux for f18, use system policy instead
+
+* Fri Oct 12 2012 Ade Lee <alee@redhat.com> 10.0.0-0.44.b1
+- Update required tomcatjss version
+- Added net-tools dependency
+
+* Mon Oct 8 2012 Ade Lee <alee@redhat.com> 10.0.0-0.43.b1
+- Update selinux-policy version to fix error from latest policy changes
+
+* Mon Oct 8 2012 Ade Lee <alee@redhat.com> 10.0.0-0.42.b1
+- Fix typo in selinux policy versions
+
+* Mon Oct 8 2012 Ade Lee <alee@redhat.com> 10.0.0-0.41.b1
+- Added build requires for correct version of selinux-policy-devel
+
+* Mon Oct 8 2012 Ade Lee <alee@redhat.com> 10.0.0-0.40.b1
+- Update release to b1
+
+* Fri Oct 5 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.40.a2
+- Merged pki-silent into pki-server.
+
+* Fri Oct 5 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.39.a2
+- Renamed "shared" folder to "server".
+
+* Fri Oct 5 2012 Ade Lee <alee@redhat.com> 10.0.0-0.38.a2
+- Added required selinux versions for new policy.
+
+* Tue Oct 2 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.37.a2
+- Added Provides to packages replacing obsolete packages.
+
+* Mon Oct 1 2012 Ade Lee <alee@redhat.com> 10.0.0-0.36.a2
+- Update release to a2
+
+* Sun Sep 30 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.36.a1
+- Modified CMake to use RPM version number
+
+* Tue Sep 25 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.35.a1
+- Added VERSION file
+
+* Mon Sep 24 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.34.a1
+- Merged pki-setup into pki-server
+
+* Thu Sep 13 2012 Ade Lee <alee@redhat.com> 10.0.0-0.33.a1
+- Added Conflicts for IPA 2.X
+- Added build requires for zip to work around mock problem
+
+* Wed Sep 12 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.32.a1
+- TRAC Ticket #312 - Dogtag 10: Automatically restart any running instances
+  upon RPM "update" . . .
+- TRAC Ticket #317 - Dogtag 10: Move "pkispawn"/"pkidestroy"
+  from /usr/bin to /usr/sbin . . .
+
+* Wed Sep 12 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.31.a1
+- Fixed pki-server to include everything in shared dir.
+
+* Tue Sep 11 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.30.a1
+- Added build dependency on redhat-rpm-config.
+
+* Thu Aug 30 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.29.a1
+- Merged Javadoc packages.
+
+* Thu Aug 30 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.28.a1
+- Added pki-tomcat.jar.
+
+* Thu Aug 30 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.27.a1
+- Moved webapp creation code into pkispawn.
+
+* Mon Aug 20 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.26.a1
+- Split pki-client.jar into pki-certsrv.jar and pki-tools.jar.
+
+* Mon Aug 20 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.25.a1
+- Merged pki-native-tools and pki-java-tools into pki-tools.
+- Modified pki-server to depend on pki-tools.
+
+* Mon Aug 20 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.24.a1
+- Split pki-common into pki-base and pki-server.
+- Merged pki-util into pki-base.
+- Merged pki-deploy into pki-server.
+
+* Thu Aug 16 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.23.a1
+- Updated release of 'tomcatjss' to rely on Tomcat 7 for Fedora 17
+- Changed Dogtag 10 build-time and runtime requirements for 'pki-deploy'
+- Altered PKI Package Dependency Chain (top-to-bottom):
+  pki-ca, pki-kra, pki-ocsp, pki-tks --> pki-deploy --> pki-common
+
+* Mon Aug 13 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.22.a1
+- Added pki-client.jar.
+
+* Fri Jul 27 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.21.a1
+- Merged pki-jndi-realm.jar into pki-cmscore.jar.
+
+* Tue Jul 24 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.20.a1
+- PKI TRAC Task #254 - Dogtag 10: Fix spec file to build successfully
+  via mock on Fedora 17 . . .
+
+* Wed Jul 11 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.19.a1
+- Moved 'pki-jndi-real.jar' link from 'tomcat6' to 'tomcat' (Tomcat 7)
+
+* Thu Jun 14 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.18.a1
+- Updated release of 'tomcatjss' to rely on Tomcat 7 for Fedora 18
+
+* Tue May 29 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.17.a1
+- Added CLI for REST services
+
+* Fri May 18 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.16.a1
+- Integration of Tomcat 7
+- Addition of centralized 'pki-tomcatd' systemd functionality to the
+  PKI Deployment strategy
+- Removal of 'pki_flavor' attribute
+
+* Mon Apr 16 2012 Ade Lee <alee@redhat.com> 10.0.0-0.15.a1
+- BZ 813075 - selinux denial for file size access
+
+* Thu Apr  5 2012 Christina Fu <cfu@redhat.com> 10.0.0-0.14.a1
+- Bug 745278 - [RFE] ECC encryption keys cannot be archived
+
+* Tue Mar 27 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.13.a1
+- Replaced candlepin-deps with resteasy
+
+* Fri Mar 23 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.12.a1
+- Added option to build without Javadoc
+
+* Fri Mar 16 2012 Ade Lee <alee@redhat.com> 10.0.0-0.11.a1
+- BZ 802396 - Change location of TOMCAT_LOG to match tomcat6 changes
+- Corrected patch selected for selinux f17 rules
+
+* Wed Mar 14 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.10.a1
+- Corrected 'junit' dependency check
+
+* Mon Mar 12 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.9.a1
+- Initial attempt at PKI deployment framework described in
+  'http://pki.fedoraproject.org/wiki/PKI_Instance_Deployment'.
+
+* Fri Mar 09 2012 Jack Magne <jmagne@redhat.com> 10.0.0-0.8.a1
+- Added support for pki-jndi-realm in tomcat6 in pki-common
+  and pki-kra.
+- Ticket #69.
+
+* Fri Mar  2 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.7.a1
+- For 'mock' purposes, removed platform-specific logic from around
+  the 'patch' files so that ALL 'patch' files will be included in
+  the SRPM.
+
+* Wed Feb 29 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.6.a1
+- Removed dependency on OSUtil.
+
+* Tue Feb 28 2012 Ade Lee <alee@redhat.com> 10.0.0-0.5.a1
+- 'pki-selinux'
+-      Added platform-dependent patches for SELinux component
+-      Bugzilla Bug #739708 - Selinux fix for ephemeral ports (F16)
+-      Bugzilla Bug #795966 - pki-selinux policy is kind of a mess (F17)
+
+* Thu Feb 23 2012 Endi S. Dewata <edewata@redhat.com> 10.0.0-0.4.a1
+- Added dependency on Apache Commons Codec.
+
+* Wed Feb 22 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.3.a1
+- Add '-DSYSTEMD_LIB_INSTALL_DIR' override flag to 'cmake' to address changes
+  in fundamental path structure in Fedora 17
+- 'pki-setup'
+-      Hard-code Perl dependencies to protect against bugs such as
+       Bugzilla Bug #772699 - Adapt perl and python fileattrs to
+       changed file 5.10 magics
+- 'pki-selinux'
+-      Bugzilla Bug #795966 - pki-selinux policy is kind of a mess
+
+* Mon Feb 20 2012 Matthew Harmsen <mharmsen@redhat.com> 10.0.0-0.2.a1
+- Integrated 'pki-kra' into 'pki-core'
+- Integrated 'pki-ocsp' into 'pki-core'
+- Integrated 'pki-tks' into 'pki-core'
+- Bugzilla Bug #788787 - added 'junit'/'junit4' build-time requirements
+
+* Wed Feb  1 2012 Nathan Kinder <nkinder@redhat.com> 10.0.0-0.1.a1
+- Updated package version number
+
+* Mon Jan 16 2012 Ade Lee <alee@redhat.com> 9.0.16-3
+- Added resteasy-jettison-provider-2.3-RC1.jar to pki-setup
+
+* Mon Nov 28 2011 Endi S. Dewata <edewata@redhat.com> 9.0.16-2
+- Added JUnit tests
+ 
+* Fri Oct 28 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.16-1
+- 'pki-setup'
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+-      Bugzilla Bug #737122 - DRM: during archiving and recovering,
+       wrapping unwrapping keys should be done in the token (cfu)
+- 'pki-java-tools'
+- 'pki-common'
+-      Bugzilla Bug #744797 - KRA key recovery (retrieve pkcs#12) fails after
+       the in-place upgrade( CS 8.0->8.1) (cfu)
+- 'pki-selinux'
+- 'pki-ca'
+-      Bugzilla Bug #746367 - Typo in the profile name. (jmagne)
+-      Bugzilla Bug #737122 - DRM: during archiving and recovering,
+       wrapping unwrapping keys should be done in the token (cfu)
+-      Bugzilla Bug #749927 - Java class conflicts using Java 7 in Fedora 17
+       (rawhide) . . . (mharmsen)
+-      Bugzilla Bug #749945 - Installation error reported during CA, DRM,
+       OCSP, and TKS package installation . . . (mharmsen)
+- 'pki-silent'
+
+* Thu Sep 22 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.15-1
+- Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . . (mharmsen)
+- Bugzilla Bug #699809 - Convert CS to use systemd (alee)
+- 'pki-setup'
+-      Bugzilla Bug #730146 - SSL handshake picks non-FIPS ciphers in FIPS
+       mode (cfu)
+-      Bugzilla Bug #737192 - Need script to upgrade proxy configuration (alee)
+- 'pki-symkey'
+-      Bugzilla Bug #730162 - TPS/TKS token enrollment failure in FIPS mode
+       (hsm+NSS). (jmagne)
+- 'pki-native-tools'
+-      Bugzilla Bug #730801 - Coverity issues in native-tools area (awnuk)
+-      Bugzilla Bug #730146 - SSL handshake picks non-FIPS ciphers in FIPS
+       mode (cfu)
+- 'pki-util'
+-      Bugzilla Bug #730146 - SSL handshake picks non-FIPS ciphers in FIPS
+       mode (cfu)
+- 'pki-java-tools'
+- 'pki-common'
+-      Bugzilla Bug #730146 - SSL handshake picks non-FIPS ciphers in FIPS
+       mode (cfu)
+-      Bugzilla Bug #737218 - Incorrect request attribute name matching
+       ignores request attributes during request parsing. (awnuk)
+-      Bugzilla Bug #730162 - TPS/TKS token enrollment failure in FIPS mode
+       (hsm+NSS). (jmagne)
+- 'pki-selinux'
+-      Bugzilla Bug #739708 - pki-selinux lacks rules in F16 (alee)
+- 'pki-ca'
+-      Bugzilla Bug #712931 - CS requires too many ports
+       to be open in the FW (alee)
+-      Bugzilla Bug #730146 - SSL handshake picks non-FIPS ciphers in FIPS
+       mode (cfu)
+- 'pki-silent'
+-      Bugzilla Bug #739201 - pkisilent does not take arch into account
+       as Java packages migrated to arch-dependent directories (mharmsen)
+
+* Fri Sep 9 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.14-1
+- 'pki-setup'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+- 'pki-symkey'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+- 'pki-native-tools'
+- 'pki-util'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+- 'pki-java-tools'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+- 'pki-common'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+- 'pki-selinux'
+- 'pki-ca'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+-      Bugzilla Bug #699809 - Convert CS to use systemd (alee)
+- 'pki-silent'
+-      Bugzilla Bug #734590 - Refactor JNI libraries for Fedora 16+ . . .
+
+* Tue Sep 6 2011 Ade Lee <alee@redhat.com> 9.0.13-1
+- 'pki-setup'
+-      Bugzilla Bug #699809 - Convert CS to use systemd (alee)
+- 'pki-ca'
+-      Bugzilla Bug #699809 - Convert CS to use systemd (alee)
+- 'pki-common'
+-      Bugzilla Bug #699809 - Convert CS to use systemd (alee)
+
+* Tue Aug 23 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.12-1
+- 'pki-setup'
+-      Bugzilla Bug #712931 - CS requires too many ports
+       to be open in the FW (alee)
+- 'pki-symkey'
+- 'pki-native-tools'
+-      Bugzilla Bug #717643 - Fopen without NULL check and other Coverity
+       issues (awnuk)
+-      Bugzilla Bug #730801 - Coverity issues in native-tools area (awnuk)
+- 'pki-util'
+- 'pki-java-tools'
+- 'pki-common'
+-      Bugzilla Bug #700522 - pki tomcat6 instances currently running
+       unconfined, allow server to come up when selinux disabled (alee)
+-      Bugzilla Bug #731741 - some CS.cfg nickname parameters not updated
+       correctly when subsystem cloned (using hsm) (alee)
+-      Bugzilla Bug #712931 - CS requires too many ports
+       to be open in the FW (alee)
+- 'pki-selinux'
+-      Bugzilla Bug #712931 - CS requires too many ports
+       to be open in the FW (alee)
+- 'pki-ca'
+-      Bugzilla Bug #712931 - CS requires too many ports
+       to be open in the FW (alee)
+- 'pki-silent'
+
+* Wed Aug 10 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.11-1
+- 'pki-setup'
+-      Bugzilla Bug #689909 - Dogtag installation under IPA takes too much
+       time - remove the inefficient sleeps (alee)
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-      Bugzilla Bug #724861 - DRMTool: fix duplicate "dn:" records by
+       renumbering "cn=<value>" (mharmsen)
+- 'pki-common'
+-      Bugzilla Bug #717041 - Improve escaping of some enrollment inputs like
+       (jmagne, awnuk)
+-      Bugzilla Bug #689909 - Dogtag installation under IPA takes too much
+       time - remove the inefficient sleeps (alee)
+-      Bugzilla Bug #708075 - Clone installation does not work over NAT
+       (alee)
+-      Bugzilla Bug #726785 - If replication fails while setting up a clone
+       it will wait forever (alee)
+-      Bugzilla Bug #728332 - xml output has changed on cert requests (awnuk)
+-      Bugzilla Bug #700505 - pki tomcat6 instances currently running
+       unconfined (alee)
+- 'pki-selinux'
+-      Bugzilla Bug #700505 - pki tomcat6 instances currently running
+       unconfined (alee)
+- 'pki-ca'
+-      Bugzilla Bug #728605 - RFE: increase default validity from 6mo to 2yrs
+       in IPA profile (awnuk)
+- 'pki-silent'
+-      Bugzilla Bug #689909 - Dogtag installation under IPA takes too much
+       time - remove the inefficient sleeps (alee)
+
+* Fri Jul 22 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.10-1
+- 'pki-setup'
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+-      Bugzilla Bug #719007 - Key Constraint keyParameter being ignored
+       using an ECC CA to generate ECC certs from CRMF. (jmagne)
+-      Bugzilla Bug #716307 - rhcs80 - DER shall not include an encoding
+       for any component value which is equal to its default value (alee)
+- 'pki-java-tools'
+- 'pki-common'
+-      Bugzilla Bug #720510 - Console: Adding a certificate into nethsm
+       throws Token not found error. (jmagne)
+-      Bugzilla Bug #719007 - Key Constraint keyParameter being ignored
+       using an ECC CA to generate ECC certs from CRMF. (jmagne)
+-      Bugzilla Bug #716307 - rhcs80 - DER shall not include an encoding
+       for any component value which is equal to its default value (alee)
+-      Bugzilla Bug #722989 - Registering an agent when a subsystem is
+       created - does not log AUTHZ_SUCCESS event. (alee)
+- 'pki-selinux'
+- 'pki-ca'
+-      Bugzilla Bug #719113 - Add client usage flag to caIPAserviceCert
+       (awnuk)
+- 'pki-silent'
+
+* Thu Jul 14 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.9-1
+- Updated release of 'jss'
+- Updated release of 'tomcatjss' for Fedora 15
+- 'pki-setup'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #693815 - /var/log/tomcat6/catalina.out owned by pkiuser
+       (jdennis)
+-      Bugzilla Bug #694569 - parameter used by pkiremove not updated (alee)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-symkey'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-native-tools'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #717765 - TPS configuration: logging into security domain
+       from tps does not work with clientauth=want. (alee)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-util'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-java-tools'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #532548 - Tool to do DRM re-key (mharmsen)
+-      Bugzilla Bug #532548 - Tool to do DRM re-key (config file and record
+       processing) (mharmsen)
+-      Bugzilla Bug #532548 - Tool to do DRM re-key (tweaks) (mharmsen)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-common'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #695403 - Editing signedaudit or transaction, system
+       logs throws 'Invalid protocol' for OCSP subsystems (alee)
+-      Bugzilla Bug #694569 - parameter used by pkiremove not updated (alee)
+-      Bugzilla Bug #695015 - Serial No. of a revoked certificate is not
+       populated in the CA signedAudit messages (alee)
+-      Bugzilla Bug #694143 - CA Agent not returning specified request (awnuk)
+-      Bugzilla Bug #695015 - Serial No. of a revoked certificate is not
+       populated in the CA signedAudit messages (jmagne)
+-      Bugzilla Bug #698885 - Race conditions during IPA installation (alee)
+-      Bugzilla Bug #704792 - CC_LAB_EVAL: CA agent interface:
+       SubjectID=$Unidentified$ fails audit evaluation (jmagne)
+-      Bugzilla Bug #705914 - SCEP mishandles nicknames when processing
+       subsequent SCEP requests. (awnuk)
+-      Bugzilla Bug #661142 - Verification should fail when a revoked
+       certificate is added. (jmagne)
+-      Bugzilla Bug #707416 - CC_LAB_EVAL: Security Domain: missing audit msgs
+       for modify/add (alee)
+-      Bugzilla Bug #707416 - additional audit messages for GetCookie (alee)
+-      Bugzilla Bug #707607 - Published certificate summary has list of
+       non-published certificates with succeeded status (jmagne)
+-      Bugzilla Bug #717813 - EV_AUDIT_LOG_SHUTDOWN audit log not generated
+       for tps and ca on server shutdown (jmagne)
+-      Bugzilla Bug #697939 - DRM signed audit log message - operation should
+       be read instead of modify (jmagne)
+-      Bugzilla Bug #718427 - When audit log is full, server continue to
+       function. (alee)
+-      Bugzilla Bug #718607 - CC_LAB_EVAL: No AUTH message is generated in
+       CA's signedaudit log when a directory based user enrollment is
+       performed (jmagne)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-selinux'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #720503 - RA and TPS require additional SELinux
+       permissions to run in "Enforcing" mode (alee)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-ca'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #693815 - /var/log/tomcat6/catalina.out owned by pkiuser
+       (jdennis)
+-      Bugzilla Bug #699837 - service command is not fully backwards
+       compatible with Dogtag pki subsystems (mharmsen)
+-      Bugzilla Bug #649910 - Console: an auditor or agent can be added to an
+       administrator group. (jmagne)
+-      Bugzilla Bug #707416 - CC_LAB_EVAL: Security Domain: missing audit msgs
+       for modify/add (alee)
+-      Bugzilla Bug #716269 - make ra authenticated profiles non-visible on ee
+       pages (alee)
+-      Bugzilla Bug #718621 - CC_LAB_EVAL: PRIVATE_KEY_ARCHIVE_REQUEST occurs
+       for a revocation invoked by EE user (awnuk)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+- 'pki-silent'
+-      Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+       (mharmsen)
+-      Bugzilla Bug #669226 - Remove Legacy Build System (mharmsen)
+
+* Wed May 25 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.8-2
+- 'pki-setup'
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-     Added 'DRMTool.cfg' configuration file to inventory
+- 'pki-common'
+- 'pki-selinux'
+- 'pki-ca'
+- 'pki-silent'
+
+* Wed May 25 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.8-1
+- 'pki-setup'
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-     Bugzilla Bug #532548 - Tool to do DRM re-key
+- 'pki-common'
+- 'pki-selinux'
+- 'pki-ca'
+- 'pki-silent'
+
+* Tue Apr 26 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.7-1
+- 'pki-setup'
+-     Bugzilla Bug #693815 - /var/log/tomcat6/catalina.out owned by pkiuser
+-     Bugzilla Bug #694569 - parameter used by pkiremove not updated
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+- 'pki-common'
+-     Bugzilla Bug #695403 - Editing signedaudit or transaction, system logs
+      throws 'Invalid protocol' for OCSP subsystems
+-     Bugzilla Bug #694569 - parameter used by pkiremove not updated
+-     Bugzilla Bug #695015 - Serial No. of a revoked certificate is not
+      populated in the CA signedAudit messages
+-     Bugzilla Bug #694143 - CA Agent not returning specified request
+-     Bugzilla Bug #695015 - Serial No. of a revoked certificate is not
+      populated in the CA signedAudit messages
+-     Bugzilla Bug #698885 - Race conditions during IPA installation
+- 'pki-selinux'
+- 'pki-ca'
+-     Bugzilla Bug #693815 - /var/log/tomcat6/catalina.out owned by pkiuser
+-     Bugzilla Bug #699837 - service command is not fully backwards compatible
+      with Dogtag pki subsystems
+- 'pki-silent'
+
+* Mon Apr 11 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.6-2
+- Bugzilla Bug #695157 - Auditverify on TPS audit log throws error.
+
+* Tue Apr 5 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.6-1
+- Bugzilla Bug #690950 - Update Dogtag Packages for Fedora 15 (beta)
+- Bugzilla Bug #693327 - Missing requires: tomcatjss
+- 'pki-setup'
+-     Bugzilla Bug #690626 - pkiremove removes the registry entry for
+      all instances on a machine
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-     Bugzilla Bug #689453 - CRMFPopClient request to CA's unsecure port
+      throws file not found exception.
+- 'pki-common'
+-     Bugzilla Bug #692990 - Audit log messages needed to match CC doc:
+      DRM Recovery audit log messages
+- 'pki-selinux'
+- 'pki-ca'
+- 'pki-silent'
+
+* Tue Apr 5 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.5-2
+- Bugzilla Bug #693327 - Missing requires: tomcatjss
+
+* Fri Mar 25 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.5-1
+- Bugzilla Bug #690950 - Update Dogtag Packages for Fedora 15 (beta)
+- Require "jss >= 4.2.6-15" as a build and runtime requirement
+- Require "tomcatjss >= 2.1.1" as a build and runtime requirement
+  for Fedora 15 and later platforms
+- 'pki-setup'
+-     Bugzilla Bug #688287 - Add "deprecation" notice regarding using
+      "shared ports" in pkicreate -help . . .
+-     Bugzilla Bug #688251 - Dogtag installation under IPA takes
+      too much time - SELinux policy compilation
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-     Bugzilla Bug #689501 - ExtJoiner tool fails to join the multiple
+      extensions
+- 'pki-common'
+-     Bugzilla Bug #683581 - CA configuration with ECC(Default
+      EC curve-nistp521) CA fails with 'signing operation failed'
+-     Bugzilla Bug #689662 - ocsp publishing needs to be re-enabled
+      on the EE port
+- 'pki-selinux'
+-     Bugzilla Bug #684871 - ldaps selinux link change
+- 'pki-ca'
+-     Bugzilla Bug #683581 - CA configuration with ECC(Default
+      EC curve-nistp521) CA fails with 'signing operation failed'
+-     Bugzilla Bug #684381 - CS.cfg specifies incorrect type of comments
+-     Bugzilla Bug #689453 - CRMFPopClient request to CA's unsecure port
+      throws file not found exception.(profile and CS.cfg only)
+- 'pki-silent'
+
+* Thu Mar 17 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.4-1
+- Bugzilla Bug #688763 - Rebase updated Dogtag Packages for Fedora 15 (alpha)
+- Bugzilla Bug #676182 - IPA installation failing - Fails to create CA
+  instance
+- Bugzilla Bug #675742 - Profile caIPAserviceCert Not Found
+- 'pki-setup'
+-     Bugzilla Bug #678157 - uninitialized variable warnings from Perl
+-     Bugzilla Bug #679574 - Velocity fails to load all dependent classes
+-     Bugzilla Bug #680420 - xml-commons-apis.jar dependency
+-     Bugzilla Bug #682013 - pkisilent needs xml-commons-apis.jar in it's
+      classpath
+-     Bugzilla Bug #673508 - CS8 64 bit pkicreate script uses wrong library
+      name for SafeNet LunaSA
+- 'pki-common'
+-     Bugzilla Bug #673638 - Installation within IPA hangs
+-     Bugzilla Bug #678715 - netstat loop fixes needed
+-     Bugzilla Bug #673609 - CC: authorize() call needs to be added to
+      getStats servlet
+- 'pki-selinux'
+-     Bugzilla Bug #674195: SELinux error message thrown during token
+      enrollment
+- 'pki-ca'
+-     Bugzilla Bug #673638 - Installation within IPA hangs
+-     Bugzilla Bug #673609 - CC: authorize() call needs to be added to
+      getStats servlet
+-     Bugzilla Bug #676330 - init script cannot start service
+- 'pki-silent'
+-     Bugzilla Bug #682013 - pkisilent needs xml-commons-apis.jar in it's
+      classpath
+
+* Wed Feb 9 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.3-2
+- 'pki-common'
+-     Bugzilla Bug #676051 - IPA installation failing - Fails to create CA
+      instance
+-     Bugzilla Bug #676182 - IPA installation failing - Fails to create CA
+      instance
+
+* Fri Feb 4 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.3-1
+- 'pki-common'
+-     Bugzilla Bug #674894 - ipactl restart : an annoy output line
+-     Bugzilla Bug #675179 - ipactl restart : an annoy output line
+
+* Thu Feb 3 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.2-1
+- Bugzilla Bug #673233 - Rebase pki-core to pick the latest features and fixes
+- 'pki-setup'
+-     Bugzilla Bug #673638 - Installation within IPA hangs
+- 'pki-symkey'
+- 'pki-native-tools'
+- 'pki-util'
+- 'pki-java-tools'
+-     Bugzilla Bug #673614 - CC: Review of cryptographic algorithms provided
+      by 'netscape.security.provider' package
+- 'pki-common'
+-     Bugzilla Bug #672291 - CA is not publishing certificates issued using
+      "Manual User Dual-Use Certificate Enrollment"
+-     Bugzilla Bug #670337 - CA Clone configuration throws TCP connection
+      error.
+-     Bugzilla Bug #504056 - Completed SCEP requests are assigned to the
+      "begin" state instead of "complete".
+-     Bugzilla Bug #504055 - SCEP requests are not properly populated
+-     Bugzilla Bug #564207 - Searches for completed requests in the agent
+      interface returns zero entries
+-     Bugzilla Bug #672291 - CA is not publishing certificates issued using
+      "Manual User Dual-Use Certificate Enrollment" -
+-     Bugzilla Bug #673614 - CC: Review of cryptographic algorithms provided
+      by 'netscape.security.provider' package
+-     Bugzilla Bug #672920 - CA console: adding policy to a profile throws
+      'Duplicate policy' error in some cases.
+-     Bugzilla Bug #673199 - init script returns control before web apps have
+      started
+-     Bugzilla Bug #674917 - Restore identification of Tomcat-based PKI
+      subsystem instances
+- 'pki-selinux'
+- 'pki-ca'
+-     Bugzilla Bug #504013 - sscep request is rejected due to authentication
+      error if submitted through one time pin router certificate enrollment.
+-     Bugzilla Bug #672111 - CC doc: certServer.usrgrp.administration missing
+      information
+-     Bugzilla Bug #583825 - CC: Obsolete servlets to be removed from web.xml
+      as part of CC interface review
+-     Bugzilla Bug #672333 - Creation of RA agent fails in IPA installation
+-     Bugzilla Bug #674917 - Restore identification of Tomcat-based PKI
+      subsystem instances
+- 'pki-silent'
+-     Bugzilla Bug #673614 - CC: Review of cryptographic algorithms provided
+      by 'netscape.security.provider' package
+
+* Wed Feb 2 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.1-3
+- Bugzilla Bug #656661 - Please Update Spec File to use 'ghost' on files
+  in /var/run and /var/lock
+
+* Thu Jan 20 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.1-2
+- 'pki-symkey'
+-     Bugzilla Bug #671265 - pki-symkey jar version incorrect
+- 'pki-common'
+-     Bugzilla Bug #564207 - Searches for completed requests in the agent
+      interface returns zero entries
+
+* Tue Jan 18 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.1-1
+- Allow 'pki-native-tools' to be installed independently of 'pki-setup'
+- Removed explicit 'pki-setup' requirement from 'pki-ca'
+  (since it already requires 'pki-common')
+- 'pki-setup'
+-     Bugzilla Bug #223343 - pkicreate: should add 'pkiuser' to nfast group
+-     Bugzilla Bug #629377 - Selinux errors during pkicreate CA, KRA, OCSP
+      and TKS.
+-     Bugzilla Bug #555927 - rhcs80 - AgentRequestFilter servlet and port
+      fowarding for agent services
+-     Bugzilla Bug #632425 - Port to tomcat6
+-     Bugzilla Bug #606946 - Convert Native Tools to use ldapAPI from
+      OpenLDAP instead of the Mozldap
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #658926 - org.apache.commons.lang class not found on F13
+-     Bugzilla Bug #661514 - CMAKE build system requires rules to make
+      javadocs
+-     Bugzilla Bug #665388 - jakarta-* jars have been renamed to apache-*,
+      pkicreate fails Fedora 14 and above
+-     Bugzilla Bug #23346 - Two conflicting ACL list definitions in source
+      repository
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+- 'pki-symkey'
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #644056 - CS build contains warnings
+- 'pki-native-tools'
+-     template change
+-     Bugzilla Bug #606946 - Convert Native Tools to use ldapAPI from
+      OpenLDAP instead of the Mozldap
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #644056 - CS build contains warnings
+- 'pki-util'
+-     Bugzilla Bug #615814 - rhcs80 - profile policyConstraintsCritical
+      cannot be set to true
+-     Bugzilla Bug #224945 - javadocs has missing descriptions, contains
+      empty packages
+-     Bugzilla Bug #621337 - Limit the received senderNonce value to 16 bytes.
+-     Bugzilla Bug #621338 - Include a server randomly-generated 16 byte
+      senderNonce in all signed SCEP responses.
+-     Bugzilla Bug #621327 - Provide switch disabling algorithm downgrade
+      attack in SCEP
+-     Bugzilla Bug #621334 - Provide an option to set default hash algorithm
+      for signing SCEP response messages.
+-     Bugzilla Bug #635033 - At installation wizard selecting key types other
+      than CA's signing cert will fail
+-     Bugzilla Bug #645874 - rfe ecc - add ecc curve name support in JSS and
+      CS interface
+-     Bugzilla Bug #488253 - com.netscape.cmsutil.ocsp.BasicOCSPResponse
+      ASN.1 encoding/decoding is broken
+-     Bugzilla Bug #551410 - com.netscape.cmsutil.ocsp.TBSRequest ASN.1
+      encoding/decoding is incomplete
+-     Bugzilla Bug #550331 - com.netscape.cmsutil.ocsp.ResponseData ASN.1
+      encoding/decoding is incomplete
+-     Bugzilla Bug #623452 - rhcs80 pkiconsole profile policy editor limit
+      policy extension to 5 only
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #651977 - turn off ssl2 for java servers (server.xml)
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #661514 - CMAKE build system requires rules to make
+      javadocs
+-     Bugzilla Bug #658188 - remove remaining references to tomcat5
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+-     Bugzilla Bug #223319 - Certificate Status inconsistency between token
+      db and CA
+-     Bugzilla Bug #531137 - RHCS 7.1 - Running out of Java Heap Memory
+      During CRL Generation
+- 'pki-java-tools'
+-     Bugzilla Bug #224945 - javadocs has missing descriptions, contains
+      empty packages
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #659004 - CC: AuditVerify hardcoded with SHA-1
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #661514 - CMAKE build system requires rules to make
+      javadocs
+-     Bugzilla Bug #662156 - HttpClient is hard-coded to handle only up to
+      5000 bytes
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+- 'pki-common'
+-     Bugzilla Bug #583822 - CC: ACL issues from CA interface CC doc review
+-     Bugzilla Bug #623745 - SessionTimer with LDAPSecurityDomainSessionTable
+      started before configuration completed
+-     Bugzilla Bug #620925 - CC: auditor needs to be able to download audit
+      logs in the java subsystems
+-     Bugzilla Bug #615827 - rhcs80 - profile policies need more than 5
+      policy mappings (seem hardcoded)
+-     Bugzilla Bug #224945 - javadocs has missing descriptions, contains
+      empty packages
+-     Bugzilla Bug #548699 - subCA's admin certificate should be generated by
+      itself
+-     Bugzilla Bug #621322 - Provide switch disabling SCEP support in CA
+-     Bugzilla Bug #563386 - rhcs80 ca crash on invalid inputs to profile
+      caAgentServerCert (null cert_request)
+-     Bugzilla Bug #621339 - SCEP one-time PIN can be used an unlimited
+      number of times
+-     Bugzilla Bug #583825 - CC: Obsolete servlets to be removed from web.xml
+      as part of CC interface review
+-     Bugzilla Bug #629677 - TPS: token enrollment fails.
+-     Bugzilla Bug #621350 - Unauthenticated user can decrypt a one-time PIN
+      in a SCEP request
+-     Bugzilla Bug #503838 - rhcs71-80 external publishing ldap connection
+      pools not reliable - improve connections or discovery
+-     Bugzilla Bug #629769 - password decryption logs plain text password
+-     Bugzilla Bug #583823 - CC: Auditing issues found as result of
+      CC - interface review
+-     Bugzilla Bug #632425 - Port to tomcat6
+-     Bugzilla Bug #586700 - OCSP Server throws fatal error while using
+      OCSP console for renewing SSL Server certificate.
+-     Bugzilla Bug #621337 - Limit the received senderNonce value to 16 bytes.
+-     Bugzilla Bug #621338 - Include a server randomly-generated 16 byte
+      senderNonce in all signed SCEP responses.
+-     Bugzilla Bug #607380 - CC: Make sure Java Console can configure all
+      security relevant config items
+-     Bugzilla Bug #558100 - host challenge of the Secure Channel needs to be
+      generated on TKS instead of TPS.
+-     Bugzilla Bug #489342 -
+      com.netscape.cms.servlet.common.CMCOutputTemplate.java
+      doesn't support EC
+-     Bugzilla Bug #630121 - OCSP responder lacking option to delete or
+      disable a CA that it serves
+-     Bugzilla Bug #634663 - CA CMC response default hard-coded to SHA1
+-     Bugzilla Bug #621327 - Provide switch disabling algorithm downgrade
+      attack in SCEP
+-     Bugzilla Bug #621334 - Provide an option to set default hash algorithm
+      for signing SCEP response messages.
+-     Bugzilla Bug #635033 - At installation wizard selecting key types other
+      than CA's signing cert will fail
+-     Bugzilla Bug #621341 - Add CA support for new SCEP key pair dedicated
+      for SCEP signing and encryption.
+-     Bugzilla Bug #223336 - ECC: unable to clone a ECC CA
+-     Bugzilla Bug #539781 - rhcs 71 - CRLs Partitioned
+      by Reason Code - onlySomeReasons ?
+-     Bugzilla Bug #637330 - CC feature: Key Management - provide signature
+      verification functions (JAVA subsystems)
+-     Bugzilla Bug #223313 - should do random generated IV param
+      for symmetric keys
+-     Bugzilla Bug #555927 - rhcs80 - AgentRequestFilter servlet and port
+      fowarding for agent services
+-     Bugzilla Bug #630176 - Improve reliability of the LdapAnonConnFactory
+-     Bugzilla Bug #524916 - ECC key constraints plug-ins should be based on
+      ECC curve names (not on key sizes).
+-     Bugzilla Bug #516632 - RHCS 7.1 - CS Incorrectly Issuing Multiple
+      Certificates from the Same Request
+-     Bugzilla Bug #648757 - expose and use updated cert verification
+      function in JSS
+-     Bugzilla Bug #638242 - Installation Wizard: at SizePanel, fix selection
+      of signature algorithm; and for ECC curves
+-     Bugzilla Bug #451874 - RFE - Java console - Certificate Wizard missing
+      e.c. support
+-     Bugzilla Bug #651040 - cloning shoud not include sslserver
+-     Bugzilla Bug #542863 - RHCS8: Default cert audit nickname written to
+      CS.cfg files imcomplete when the cert is stored on a hsm
+-     Bugzilla Bug #360721 - New Feature: Profile Integrity Check . . .
+-     Bugzilla Bug #651916 - kra and ocsp are using incorrect ports
+      to talk to CA and complete configuration in DonePanel
+-     Bugzilla Bug #642359 - CC Feature - need to verify certificate when it
+      is added
+-     Bugzilla Bug #653713 - CC: setting trust on a CIMC cert requires
+      auditing
+-     Bugzilla Bug #489385 - references to rhpki
+-     Bugzilla Bug #499494 - change CA defaults to SHA2
+-     Bugzilla Bug #623452 - rhcs80 pkiconsole profile policy editor limit
+      policy extension to 5 only
+-     Bugzilla Bug #649910 - Console: an auditor or agent can be added to
+      an administrator group.
+-     Bugzilla Bug #632425 - Port to tomcat6
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #651977 - turn off ssl2 for java servers (server.xml)
+-     Bugzilla Bug #653576 - tomcat5 does not always run filters on servlets
+      as expected
+-     Bugzilla Bug #642357 - CC Feature- Self-Test plugins only check for
+      validity
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #659004 - CC: AuditVerify hardcoded with SHA-1
+-     Bugzilla Bug #661196 - ECC(with nethsm) subca configuration fails with
+      Key Type RSA Not Matched despite using ECC key pairs for rootCA & subCA.
+-     Bugzilla Bug #661889 - The Servlet TPSRevokeCert of the CA returns an
+      error to TPS even if certificate in question is already revoked.
+-     Bugzilla Bug #663546 - Disable the functionalities that are not exposed
+      in the console
+-     Bugzilla Bug #661514 - CMAKE build system requires rules to make
+      javadocs
+-     Bugzilla Bug #658188 - remove remaining references to tomcat5
+-     Bugzilla Bug #649343 - Publishing queue should recover from CA crash.
+-     Bugzilla Bug #491183 - rhcs rfe - add rfc 4523 support for pkiUser and
+      pkiCA, obsolete 2252 and 2256
+-     Bugzilla Bug #640710 - Current SCEP implementation does not support HSMs
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+-     Bugzilla Bug #661142 - Verification should fail when
+      a revoked certificate is added
+-     Bugzilla Bug #642741 - CS build uses deprecated functions
+-     Bugzilla Bug #670337 - CA Clone configuration throws TCP connection error
+-     Bugzilla Bug #662127 - CC doc Error: SignedAuditLog expiration time
+      interface is no longer available through console
+- 'pki-selinux'
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #667153 - store nuxwdog passwords in kernel ring buffer -
+      selinux changes
+- 'pki-ca'
+-     Bugzilla Bug #583822 - CC: ACL issues from CA interface CC doc review
+-     Bugzilla Bug #620925 - CC: auditor needs to be able to download audit
+      logs in the java subsystems
+-     Bugzilla Bug #621322 - Provide switch disabling SCEP support in CA
+-     Bugzilla Bug #583824 - CC: Duplicate servlet mappings found as part of
+      CC interface doc review
+-     Bugzilla Bug #621602 - pkiconsole: Click on 'Publishing' option with
+      admin privilege throws error "You are not authorized to perform this
+      operation".
+-     Bugzilla Bug #583825 - CC: Obsolete servlets to be removed from web.xml
+      as part of CC interface review
+-     Bugzilla Bug #583823 - CC: Auditing issues found as result of
+      CC - interface review
+-     Bugzilla Bug #519291 - Deleting a CRL Issuing Point after edits throws
+      'Internal Server Error'.
+-     Bugzilla Bug #586700 - OCSP Server throws fatal error while using
+      OCSP console for renewing SSL Server certificate.
+-     Bugzilla Bug #621337 - Limit the received senderNonce value to 16 bytes.
+-     Bugzilla Bug #621338 - Include a server randomly-generated 16 byte
+      senderNonce in all signed SCEP responses.
+-     Bugzilla Bug #558100 - host challenge of the Secure Channel needs to be
+      generated on TKS instead of TPS.
+-     Bugzilla Bug #630121 - OCSP responder lacking option to delete or
+      disable a CA that it serves
+-     Bugzilla Bug #634663 - CA CMC response default hard-coded to SHA1
+-     Bugzilla Bug #621327 - Provide switch disabling algorithm downgrade
+      attack in SCEP
+-     Bugzilla Bug #621334 - Provide an option to set default hash algorithm
+      for signing SCEP response messages.
+-     Bugzilla Bug #539781 - rhcs 71 - CRLs Partitioned
+      by Reason Code - onlySomeReasons ?
+-     Bugzilla Bug #637330 - CC feature: Key Management - provide signature
+      verification functions (JAVA subsystems)
+-     Bugzilla Bug #555927 - rhcs80 - AgentRequestFilter servlet and port
+      fowarding for agent services
+-     Bugzilla Bug #524916 - ECC key constraints plug-ins should be based on
+      ECC curve names (not on key sizes).
+-     Bugzilla Bug #516632 - RHCS 7.1 - CS Incorrectly Issuing Multiple
+      Certificates from the Same Request
+-     Bugzilla Bug #638242 - Installation Wizard: at SizePanel, fix selection
+      of signature algorithm; and for ECC curves
+-     Bugzilla Bug #529945 - (Instructions and sample only) CS 8.0 GA
+      release -- DRM and TKS do not seem to have CRL checking enabled
+-     Bugzilla Bug #609641 - CC: need procedure (and possibly tools) to help
+      correctly set up CC environment
+-     Bugzilla Bug #509481 - RFE: support sMIMECapabilities extensions in
+      certificates (RFC 4262)
+-     Bugzilla Bug #651916 - kra and ocsp are using incorrect ports
+      to talk to CA and complete configuration in DonePanel
+-     Bugzilla Bug #511990 - rhcs 7.3, 8.0 - re-activate missing object
+      signing support in RHCS
+-     Bugzilla Bug #651977 - turn off ssl2 for java servers (server.xml)
+-     Bugzilla Bug #489385 - references to rhpki
+-     Bugzilla Bug #499494 - change CA defaults to SHA2
+-     Bugzilla Bug #623452 - rhcs80 pkiconsole profile policy editor limit
+      policy extension to 5 only
+-     Bugzilla Bug #649910 - Console: an auditor or agent can be added to
+      an administrator group.
+-     Bugzilla Bug #632425 - Port to tomcat6
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #653576 - tomcat5 does not always run filters on servlets
+      as expected
+-     Bugzilla Bug #642357 - CC Feature- Self-Test plugins only check for
+      validity
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #661128 - incorrect CA ports used for revoke, unrevoke
+      certs in TPS
+-     Bugzilla Bug #512496 - RFE rhcs80 - crl updates and scheduling feature 
+-     Bugzilla Bug #661196 - ECC(with nethsm) subca configuration fails with
+      Key Type RSA Not Matched despite using ECC key pairs for rootCA & subCA.
+-     Bugzilla Bug #649343 - Publishing queue should recover from CA crash.
+-     Bugzilla Bug #491183 - rhcs rfe - add rfc 4523 support for pkiUser and
+      pkiCA, obsolete 2252 and 2256
+-     Bugzilla Bug #223346 - Two conflicting ACL list definitions in source
+      repository
+-     Bugzilla Bug #640710 - Current SCEP implementation does not support HSMs
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+-     Bugzilla Bug #661142 - Verification should fail when
+      a revoked certificate is added
+-     Bugzilla Bug #668100 - DRM storage cert has OCSP signing extended key
+      usage
+-     Bugzilla Bug #662127 - CC doc Error: SignedAuditLog expiration time
+      interface is no longer available through console
+-     Bugzilla Bug #531137 - RHCS 7.1 - Running out of Java Heap Memory
+      During CRL Generation
+- 'pki-silent'
+-     Bugzilla Bug #627309 - pkisilent subca configuration fails.
+-     Bugzilla Bug #640091 - pkisilent panels need to match with changed java
+      subsystems
+-     Bugzilla Bug #527322 - pkisilent ConfigureDRM should configure DRM
+      Clone.
+-     Bugzilla Bug #643053 - pkisilent DRM configuration fails
+-     Bugzilla Bug #583754 - pki-silent needs an option to configure signing
+      algorithm for CA certificates
+-     Bugzilla Bug #489385 - references to rhpki
+-     Bugzilla Bug #638377 - Generate PKI UI components which exclude a GUI
+      interface
+-     Bugzilla Bug #651977 - turn off ssl2 for java servers (server.xml)
+-     Bugzilla Bug #640042 - TPS Installlation Wizard: need to move Module
+      Panel up to before Security Domain Panel
+-     Bugzilla Bug #643206 - New CMake based build system for Dogtag
+-     Bugzilla Bug #588323 - Failed to enable cipher 0xc001
+-     Bugzilla Bug #656733 - Standardize jar install location and jar names
+-     Bugzilla Bug #645895 - pkisilent: add ability to select ECC curves,
+      signing algorithm
+-     Bugzilla Bug #658641 - pkisilent doesn't not properly handle passwords
+      with special characters
+-     Bugzilla Bug #642741 - CS build uses deprecated functions
+
+* Thu Jan 13 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.0-3
+- Bugzilla Bug #668839 - Review Request: pki-core
+-   Removed empty "pre" from "pki-ca"
+-   Consolidated directory ownership
+-   Corrected file ownership within subpackages
+-   Removed all versioning from NSS and NSPR packages
+
+* Thu Jan 13 2011 Matthew Harmsen <mharmsen@redhat.com> 9.0.0-2
+- Bugzilla Bug #668839 - Review Request: pki-core
+-   Added component versioning comments
+-   Updated JSS from "4.2.6-10" to "4.2.6-12"
+-   Modified installation section to preserve timestamps
+-   Removed sectional comments
+
+* Wed Dec 1 2010 Matthew Harmsen <mharmsen@redhat.com> 9.0.0-1
+- Initial revision. (kwright@redhat.com & mharmsen@redhat.com)
+