summaryrefslogtreecommitdiffstats
path: root/base/server/tomcat7
diff options
context:
space:
mode:
authorEndi S. Dewata <edewata@redhat.com>2015-02-24 21:02:13 -0500
committerEndi S. Dewata <edewata@redhat.com>2015-04-21 16:53:17 -0400
commit42667acb21cee0ce73c58aaf55aea8fee19620ff (patch)
tree6f3671276e1f76f4535e11cafd20542ab2bbe36e /base/server/tomcat7
parentab5f54371519010c72f4947901c3a76cb5105e41 (diff)
downloadpki-42667acb21cee0ce73c58aaf55aea8fee19620ff.tar.gz
pki-42667acb21cee0ce73c58aaf55aea8fee19620ff.tar.xz
pki-42667acb21cee0ce73c58aaf55aea8fee19620ff.zip
Added support for Tomcat 8.
The Dogtag code has been modified to support both Tomcat 7 and 8. All files depending on a specific Tomcat version are now stored in separate folders. The build scripts have been modified to use the proper folder for the target platform. The tomcatjss dependency has been updated as well. The upgrade script will be added in a separate patch. https://fedorahosted.org/pki/ticket/1264
Diffstat (limited to 'base/server/tomcat7')
-rw-r--r--base/server/tomcat7/CMakeLists.txt10
-rw-r--r--base/server/tomcat7/conf/Catalina/localhost/ROOT.xml30
-rw-r--r--base/server/tomcat7/conf/Catalina/localhost/pki.xml30
-rw-r--r--base/server/tomcat7/conf/server.xml310
-rw-r--r--base/server/tomcat7/src/CMakeLists.txt158
-rw-r--r--base/server/tomcat7/src/com/netscape/cms/tomcat/ProxyRealm.java139
-rw-r--r--base/server/tomcat7/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java172
-rw-r--r--base/server/tomcat7/src/pki-tomcat.mf3
8 files changed, 852 insertions, 0 deletions
diff --git a/base/server/tomcat7/CMakeLists.txt b/base/server/tomcat7/CMakeLists.txt
new file mode 100644
index 000000000..ba02af18d
--- /dev/null
+++ b/base/server/tomcat7/CMakeLists.txt
@@ -0,0 +1,10 @@
+project(server-tomcat7)
+
+add_subdirectory(src)
+
+install(
+ DIRECTORY
+ conf/
+ DESTINATION
+ ${DATA_INSTALL_DIR}/server/conf/
+)
diff --git a/base/server/tomcat7/conf/Catalina/localhost/ROOT.xml b/base/server/tomcat7/conf/Catalina/localhost/ROOT.xml
new file mode 100644
index 000000000..ce98bfa4e
--- /dev/null
+++ b/base/server/tomcat7/conf/Catalina/localhost/ROOT.xml
@@ -0,0 +1,30 @@
+<?xml version='1.0' encoding='utf-8'?>
+<!-- BEGIN COPYRIGHT BLOCK
+ Copyright (C) 2012 Red Hat, Inc.
+ All rights reserved.
+ Modifications: configuration parameters
+ END COPYRIGHT BLOCK
+-->
+
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<Context crossContext="true" allowLinking="true">
+
+ <Manager
+ secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+
+</Context>
diff --git a/base/server/tomcat7/conf/Catalina/localhost/pki.xml b/base/server/tomcat7/conf/Catalina/localhost/pki.xml
new file mode 100644
index 000000000..ce98bfa4e
--- /dev/null
+++ b/base/server/tomcat7/conf/Catalina/localhost/pki.xml
@@ -0,0 +1,30 @@
+<?xml version='1.0' encoding='utf-8'?>
+<!-- BEGIN COPYRIGHT BLOCK
+ Copyright (C) 2012 Red Hat, Inc.
+ All rights reserved.
+ Modifications: configuration parameters
+ END COPYRIGHT BLOCK
+-->
+
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<Context crossContext="true" allowLinking="true">
+
+ <Manager
+ secureRandomProvider="Mozilla-JSS" secureRandomAlgorithm="pkcs11prng"/>
+
+</Context>
diff --git a/base/server/tomcat7/conf/server.xml b/base/server/tomcat7/conf/server.xml
new file mode 100644
index 000000000..b9e8860b2
--- /dev/null
+++ b/base/server/tomcat7/conf/server.xml
@@ -0,0 +1,310 @@
+<?xml version='1.0' encoding='utf-8'?>
+<!-- BEGIN COPYRIGHT BLOCK
+ Copyright (C) 2012 Red Hat, Inc.
+ All rights reserved.
+ Modifications: configuration parameters
+ END COPYRIGHT BLOCK -->
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<!-- Note: A "Server" is not itself a "Container", so you may not
+ define subcomponents such as "Valves" at this level.
+ Documentation at /docs/config/server.html
+-->
+
+<!-- DO NOT REMOVE - Begin PKI Status Definitions -->
+<!-- CA Status Definitions -->
+<!--
+Unsecure URL = http://[PKI_HOSTNAME]:[PKI_UNSECURE_PORT]/ca/ee/ca
+Secure Agent URL = https://[PKI_HOSTNAME]:[PKI_AGENT_SECURE_PORT]/ca/agent/ca
+Secure EE URL = https://[PKI_HOSTNAME]:[PKI_EE_SECURE_PORT]/ca/ee/ca
+Secure Admin URL = https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/ca/services
+EE Client Auth URL = https://[PKI_HOSTNAME]:[PKI_EE_SECURE_CLIENT_AUTH_PORT]/ca/eeca/ca
+PKI Console Command = pkiconsole https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/ca
+Tomcat Port = [TOMCAT_SERVER_PORT] (for shutdown)
+-->
+<!-- KRA Status Definitions -->
+<!--
+Unsecure URL = http://[PKI_HOSTNAME]:[PKI_UNSECURE_PORT]/kra/ee/kra
+Secure Agent URL = https://[PKI_HOSTNAME]:[PKI_AGENT_SECURE_PORT]/kra/agent/kra
+Secure EE URL = https://[PKI_HOSTNAME]:[PKI_EE_SECURE_PORT]/kra/ee/kra
+Secure Admin URL = https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/kra/services
+PKI Console Command = pkiconsole https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/kra
+Tomcat Port = [TOMCAT_SERVER_PORT] (for shutdown)
+-->
+<!-- OCSP Status Definitions -->
+<!--
+Unsecure URL = http://[PKI_HOSTNAME]:[PKI_UNSECURE_PORT]/ocsp/ee/ocsp
+Secure Agent URL = https://[PKI_HOSTNAME]:[PKI_AGENT_SECURE_PORT]/ocsp/agent/ocsp
+Secure EE URL = https://[PKI_HOSTNAME]:[PKI_EE_SECURE_PORT]/ocsp/ee/ocsp
+Secure Admin URL = https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/ocsp/services
+PKI Console Command = pkiconsole https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/ocsp
+Tomcat Port = [TOMCAT_SERVER_PORT] (for shutdown)
+-->
+<!-- TKS Status Definitions -->
+<!--
+Unsecure URL = http://[PKI_HOSTNAME]:[PKI_UNSECURE_PORT]/tks/ee/tks
+Secure Agent URL = https://[PKI_HOSTNAME]:[PKI_AGENT_SECURE_PORT]/tks/agent/tks
+Secure EE URL = https://[PKI_HOSTNAME]:[PKI_EE_SECURE_PORT]/tks/ee/tks
+Secure Admin URL = https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/tks/services
+PKI Console Command = pkiconsole https://[PKI_HOSTNAME]:[PKI_ADMIN_SECURE_PORT]/tks
+Tomcat Port = [TOMCAT_SERVER_PORT] (for shutdown)
+-->
+<!-- DO NOT REMOVE - End PKI Status Definitions -->
+
+<Server port="[TOMCAT_SERVER_PORT]" shutdown="SHUTDOWN">
+
+ <!--APR library loader. Documentation at /docs/apr.html -->
+ <!-- The following Listener class has been commented out because this -->
+ <!-- implementation depends upon the 'tomcatjss' JSSE module, 'JSS', -->
+ <!-- and 'NSS' rather than the 'tomcat-native' module! -->
+ <!-- Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" -->
+ <!--Initialize Jasper prior to webapps are loaded. Documentation at /docs/jasper-howto.html -->
+ <Listener className="org.apache.catalina.core.JasperListener" />
+ <!-- JMX Support for the Tomcat server. Documentation at /docs/non-existent.html -->
+ <!-- The following class has been commented out because it -->
+ <!-- has been EXCLUDED from the Tomcat 7 'tomcat-lib' RPM! -->
+ <!-- Listener className="org.apache.catalina.mbeans.ServerLifecycleListener" -->
+ <Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
+
+ <!-- Global JNDI resources
+ Documentation at /docs/jndi-resources-howto.html
+ -->
+ <GlobalNamingResources>
+ <!-- Editable user database that can also be used by
+ UserDatabaseRealm to authenticate users
+ -->
+ <Resource name="UserDatabase" auth="Container"
+ type="org.apache.catalina.UserDatabase"
+ description="User database that can be updated and saved"
+ factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
+ pathname="conf/tomcat-users.xml" />
+ </GlobalNamingResources>
+
+ <!-- A "Service" is a collection of one or more "Connectors" that share
+ a single "Container" Note: A "Service" is not itself a "Container",
+ so you may not define subcomponents such as "Valves" at this level.
+ Documentation at /docs/config/service.html
+ -->
+ <Service name="Catalina">
+
+ <!--The connectors can use a shared executor, you can define one or more named thread pools-->
+ <!--
+ <Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
+ maxThreads="150" minSpareThreads="4"/>
+ -->
+
+
+ <!-- A "Connector" represents an endpoint by which requests are received
+ and responses are returned. Documentation at :
+ Java HTTP Connector: /docs/config/http.html (blocking & non-blocking)
+ Java AJP Connector: /docs/config/ajp.html
+ APR (HTTP/AJP) Connector: /docs/apr.html
+ Define a non-SSL HTTP/1.1 Connector on port 8080
+ -->
+
+ [PKI_UNSECURE_PORT_SERVER_COMMENT]
+ <Connector name="[PKI_UNSECURE_PORT_CONNECTOR_NAME]" port="[PKI_UNSECURE_PORT]" protocol="HTTP/1.1" redirectPort="[PKI_SECURE_PORT]"
+ maxHttpHeaderSize="8192"
+ acceptCount="100" maxThreads="150" minSpareThreads="25"
+ enableLookups="false" connectionTimeout="20000" disableUploadTimeout="true"
+ />
+
+ <!-- Define a SSL HTTP/1.1 Connector on port 8443 -->
+ [PKI_SECURE_PORT_SERVER_COMMENT]
+ <!-- DO NOT REMOVE - Begin define PKI secure port
+ NOTE: The following 'keys' (and their assigned values) are exclusive to
+ the 'tomcatjss' JSSE module:
+
+ 'enableOCSP'
+ 'ocspResponderURL'
+ 'ocspResponderCertNickname'
+ 'ocspCacheSize'
+ 'ocspMinCacheEntryDuration'
+ 'ocspMaxCacheEntryDuration'
+ 'ocspTimeout'
+ 'strictCiphers'
+ 'clientauth' (ALL lowercase)
+ 'sslOptions'
+ 'ssl2Ciphers'
+ 'ssl3Ciphers'
+ 'tlsCiphers'
+ 'sslVersionRangeStream'
+ 'sslVersionRangeDatagram'
+ 'sslRangeCiphers'
+ 'serverCertNickFile'
+ 'passwordFile'
+ 'passwordClass'
+ 'certdbDir'
+
+ and are referenced via the value of the 'sslImplementationName' key.
+ NOTE: The OCSP settings take effect globally, so it should only be set once.
+
+ In setup where SSL clientauth="true", OCSP can be turned on by
+ setting enableOCSP to true like the following:
+ enableOCSP="true"
+ along with changes to related settings, especially:
+ ocspResponderURL=<see example in connector definition below>
+ ocspResponderCertNickname=<see example in connector definition below>
+ Here are the definition to all the OCSP-related settings:
+ enableOCSP - turns on/off the ocsp check
+ ocspResponderURL - sets the url where the ocsp requests are sent
+ ocspResponderCertNickname - sets the nickname of the cert that is
+ either CA's signing certificate or the OCSP server's signing
+ certificate.
+ The CA's signing certificate should already be in the db, in
+ case of the same security domain.
+ In case of an ocsp signing certificate, one must import the cert
+ into the subsystem's nss db and set trust. e.g.:
+ certutil -d . -A -n "ocspSigningCert cert-pki-ca" -t "C,," -a -i ocspCert.b64
+ ocspCacheSize - sets max cache entries
+ ocspMinCacheEntryDuration - sets minimum seconds to next fetch attempt
+ ocspMaxCacheEntryDuration - sets maximum seconds to next fetch attempt
+ ocspTimeout -sets OCSP timeout in seconds
+ -->
+ <Connector name="[PKI_SECURE_PORT_CONNECTOR_NAME]" port="[PKI_SECURE_PORT]" protocol="HTTP/1.1" SSLEnabled="true" sslProtocol="SSL" scheme="https" secure="true"
+ maxHttpHeaderSize="8192"
+ acceptCount="100" maxThreads="150" minSpareThreads="25"
+ enableLookups="false" disableUploadTimeout="true"
+ sslImplementationName="org.apache.tomcat.util.net.jss.JSSImplementation"
+ enableOCSP="false"
+ ocspResponderURL="http://[PKI_HOSTNAME]:9080/ca/ocsp"
+ ocspResponderCertNickname="ocspSigningCert cert-pki-ca"
+ ocspCacheSize="1000"
+ ocspMinCacheEntryDuration="60"
+ ocspMaxCacheEntryDuration="120"
+ ocspTimeout="10"
+ strictCiphers="true"
+ clientAuth="[PKI_AGENT_CLIENTAUTH]"
+ sslOptions="[TOMCAT_SSL_OPTIONS]"
+ ssl2Ciphers="[TOMCAT_SSL2_CIPHERS]"
+ ssl3Ciphers="[TOMCAT_SSL3_CIPHERS]"
+ tlsCiphers="[TOMCAT_TLS_CIPHERS]"
+ sslVersionRangeStream="[TOMCAT_SSL_VERSION_RANGE_STREAM]"
+ sslVersionRangeDatagram="[TOMCAT_SSL_VERSION_RANGE_DATAGRAM]"
+ sslRangeCiphers="[TOMCAT_SSL_RANGE_CIPHERS]"
+ serverCertNickFile="[PKI_INSTANCE_PATH]/conf/serverCertNick.conf"
+ passwordFile="[PKI_INSTANCE_PATH]/conf/password.conf"
+ passwordClass="org.apache.tomcat.util.net.jss.PlainPasswordFile"
+ certdbDir="[PKI_INSTANCE_PATH]/alias"
+ />
+ <!-- DO NOT REMOVE - End define PKI secure port -->
+
+ <!-- Define an AJP 1.3 Connector on port [PKI_AJP_PORT] -->
+[PKI_OPEN_AJP_PORT_COMMENT]
+ <Connector port="[PKI_AJP_PORT]" protocol="AJP/1.3" redirectPort="[PKI_AJP_REDIRECT_PORT]" address="127.0.0.1" />
+[PKI_CLOSE_AJP_PORT_COMMENT]
+
+
+ <!-- An Engine represents the entry point (within Catalina) that processes
+ every request. The Engine implementation for Tomcat stand alone
+ analyzes the HTTP headers included with the request, and passes them
+ on to the appropriate Host (virtual host).
+ Documentation at /docs/config/engine.html -->
+
+ <!-- You should set jvmRoute to support load-balancing via AJP ie :
+ <Engine name="Catalina" defaultHost="localhost" jvmRoute="jvm1">
+ -->
+ <Engine name="Catalina" defaultHost="localhost">
+
+ <!--For clustering, please take a look at documentation at:
+ /docs/cluster-howto.html (simple how to)
+ /docs/config/cluster.html (reference documentation) -->
+ <!--
+ <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/>
+ -->
+
+ <!-- The request dumper valve dumps useful debugging information about
+ the request and response data received and sent by Tomcat.
+ Documentation at: /docs/config/valve.html -->
+ <!--
+ <Valve className="org.apache.catalina.valves.RequestDumperValve"/>
+ -->
+
+ <!-- This Realm uses the UserDatabase configured in the global JNDI
+ resources under the key "UserDatabase". Any edits
+ that are performed against this UserDatabase are immediately
+ available for use by the Realm. -->
+
+ <!--
+ <Realm className="org.apache.catalina.realm.UserDatabaseRealm"
+ resourceName="UserDatabase"/>
+ -->
+
+ <!--
+ <Realm className="com.netscape.cmscore.realm.PKIRealm" />
+ -->
+
+ <!-- Define the default virtual host
+ Note: XML Schema validation will not work with Xerces 2.2.
+ -->
+ <Host name="localhost"
+ appBase="[PKI_INSTANCE_PATH]/webapps"
+ unpackWARs="true" autoDeploy="true"
+ xmlValidation="false" xmlNamespaceAware="false">
+
+ <!--
+ <Context path="/ca"
+ docBase="ca"
+ allowLinking="true">
+ <Loader className="org.apache.catalina.loader.VirtualWebappLoader"
+ virtualClasspath="[PKI_INSTANCE_PATH]/ca/webapps/ca/WEB-INF/classes;[PKI_INSTANCE_PATH]/ca/webapps/ca/WEB-INF/lib" />" />
+ <JarScanner scanAllDirectories="true" />
+ </Context>
+
+ <Context path="/kra"
+ docBase="kra"
+ allowLinking="true">
+ <Loader className="org.apache.catalina.loader.VirtualWebappLoader"
+ virtualClasspath="[PKI_INSTANCE_PATH]/kra/webapps/kra/WEB-INF/classes;[PKI_INSTANCE_PATH]/kra/webapps/kra/WEB-INF/lib" />
+ <JarScanner scanAllDirectories="true" />
+ </Context>
+
+ <Context path="/ocsp"
+ docBase="ocsp"
+ allowLinking="true">
+ <Loader className="org.apache.catalina.loader.VirtualWebappLoader"
+ virtualClasspath="[PKI_INSTANCE_PATH]/ocsp/webapps/ocsp/WEB-INF/classes;[PKI_INSTANCE_PATH]/ocsp/webapps/ocsp/WEB-INF/lib" />
+ <JarScanner scanAllDirectories="true" />
+ </Context>
+
+ <Context path="/tks"
+ docBase="tks"
+ allowLinking="true">
+ <Loader className="org.apache.catalina.loader.VirtualWebappLoader"
+ virtualClasspath="[PKI_INSTANCE_PATH]/tks/webapps/tks/WEB-INF/classes;[PKI_INSTANCE_PATH]/tks/webapps/tks/WEB-INF/lib" />
+ <JarScanner scanAllDirectories="true" />
+ </Context>
+ -->
+
+ <!-- SingleSignOn valve, share authentication between web applications
+ Documentation at: /docs/config/valve.html -->
+ <!--
+ <Valve className="org.apache.catalina.authenticator.SingleSignOn" />
+ -->
+
+ <!-- Access log processes all example.
+ Documentation at: /docs/config/valve.html -->
+ [PKI_OPEN_TOMCAT_ACCESS_LOG_COMMENT]
+ <Valve className="org.apache.catalina.valves.AccessLogValve"
+ directory="logs" prefix="localhost_access_log." suffix=".txt"
+ pattern="common" resolveHosts="false"/>
+ [PKI_CLOSE_TOMCAT_ACCESS_LOG_COMMENT]
+
+ </Host>
+ </Engine>
+ </Service>
+</Server>
diff --git a/base/server/tomcat7/src/CMakeLists.txt b/base/server/tomcat7/src/CMakeLists.txt
new file mode 100644
index 000000000..102dec782
--- /dev/null
+++ b/base/server/tomcat7/src/CMakeLists.txt
@@ -0,0 +1,158 @@
+project(pki-tomcat)
+
+find_file(JSS_JAR
+ NAMES
+ jss4.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(LDAPJDK_JAR
+ NAMES
+ ldapjdk.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(COMMONS_CODEC_JAR
+ NAMES
+ commons-codec.jar
+ PATHS
+ /usr/share/java
+)
+
+find_file(COMMONS_HTTPCLIENT_JAR
+ NAMES
+ commons-httpclient.jar
+ PATHS
+ /usr/share/java
+)
+
+find_file(APACHE_COMMONS_LANG_JAR
+ NAMES
+ apache-commons-lang.jar
+ PATHS
+ /usr/share/java
+)
+
+find_file(TOMCAT_CATALINA_JAR
+ NAMES
+ catalina.jar
+ PATHS
+ /usr/share/java/tomcat
+)
+
+find_file(TOMCAT_UTIL_SCAN_JAR
+ NAMES
+ tomcat-util-scan.jar
+ PATHS
+ /usr/share/java/tomcat
+)
+
+find_file(SERVLET_JAR
+ NAMES
+ servlet.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(VELOCITY_JAR
+ NAMES
+ velocity.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(XALAN_JAR
+ NAMES
+ xalan-j2.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(XERCES_JAR
+ NAMES
+ xerces-j2.jar
+ PATHS
+ ${JAVA_LIB_INSTALL_DIR}
+ /usr/share/java
+)
+
+find_file(JAXRS_API_JAR
+ NAMES
+ jaxrs-api.jar
+ PATHS
+ ${RESTEASY_LIB}
+)
+
+find_file(RESTEASY_JAXRS_JAR
+ NAMES
+ resteasy-jaxrs.jar
+ PATHS
+ ${RESTEASY_LIB}
+)
+
+find_file(RESTEASY_ATOM_PROVIDER_JAR
+ NAMES
+ resteasy-atom-provider.jar
+ PATHS
+ ${RESTEASY_LIB}
+)
+
+find_file(HTTPCLIENT_JAR
+ NAMES
+ httpclient.jar
+ PATHS
+ /usr/share/java/httpcomponents
+)
+
+find_file(HTTPCORE_JAR
+ NAMES
+ httpcore.jar
+ PATHS
+ /usr/share/java/httpcomponents
+)
+
+# build pki-tomcat
+javac(pki-tomcat-classes
+ SOURCES
+ com/netscape/cms/tomcat/*.java
+ CLASSPATH
+ ${SERVLET_JAR} ${TOMCAT_CATALINA_JAR} ${TOMCAT_UTIL_SCAN_JAR}
+ OUTPUT_DIR
+ ${CMAKE_BINARY_DIR}/classes
+)
+
+configure_file(
+ ${CMAKE_CURRENT_SOURCE_DIR}/pki-tomcat.mf
+ ${CMAKE_CURRENT_BINARY_DIR}/pki-tomcat.mf
+)
+
+jar(pki-tomcat-jar
+ CREATE
+ ${CMAKE_BINARY_DIR}/dist/pki-tomcat.jar
+ OPTIONS
+ m
+ PARAMS
+ ${CMAKE_CURRENT_BINARY_DIR}/pki-tomcat.mf
+ INPUT_DIR
+ ${CMAKE_BINARY_DIR}/classes
+ FILES
+ com/netscape/cms/tomcat/*.class
+ DEPENDS
+ pki-tomcat-classes
+)
+
+install(
+ FILES
+ ${CMAKE_BINARY_DIR}/dist/pki-tomcat.jar
+ DESTINATION
+ ${JAVA_JAR_INSTALL_DIR}/pki
+)
+
+set(PKI_TOMCAT_JAR ${CMAKE_BINARY_DIR}/dist/pki-tomcat.jar CACHE INTERNAL "pki-tomcat jar file")
diff --git a/base/server/tomcat7/src/com/netscape/cms/tomcat/ProxyRealm.java b/base/server/tomcat7/src/com/netscape/cms/tomcat/ProxyRealm.java
new file mode 100644
index 000000000..094c0561f
--- /dev/null
+++ b/base/server/tomcat7/src/com/netscape/cms/tomcat/ProxyRealm.java
@@ -0,0 +1,139 @@
+package com.netscape.cms.tomcat;
+
+import java.beans.PropertyChangeListener;
+import java.io.IOException;
+import java.security.Principal;
+import java.security.cert.X509Certificate;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.catalina.Container;
+import org.apache.catalina.Context;
+import org.apache.catalina.Realm;
+import org.apache.catalina.Wrapper;
+import org.apache.catalina.connector.Request;
+import org.apache.catalina.connector.Response;
+import org.apache.catalina.deploy.SecurityConstraint;
+import org.ietf.jgss.GSSContext;
+
+/**
+ * @author Endi S. Dewata
+ */
+public class ProxyRealm implements Realm {
+
+ public static Map<String, ProxyRealm> proxies = new HashMap<String, ProxyRealm>();
+
+ public Container container;
+ public Realm realm;
+
+ public ProxyRealm() {
+ }
+
+ @Override
+ public Container getContainer() {
+ return container;
+ }
+
+ @Override
+ public void setContainer(Container container) {
+ this.container = container;
+ if (container instanceof Context) {
+ Context context = (Context)container;
+ proxies.put(context.getBaseName(), this);
+ }
+ }
+
+ public Realm getRealm() {
+ return realm;
+ }
+
+ public void setRealm(Realm realm) {
+ this.realm = realm;
+ realm.setContainer(container);
+ }
+
+ public static void registerRealm(String contextName, Realm realm) {
+ ProxyRealm proxy = proxies.get(contextName);
+ if (proxy == null) return;
+
+ proxy.setRealm(realm);
+ }
+
+ @Override
+ public Principal authenticate(String username, String password) {
+ return realm.authenticate(username, password);
+ }
+
+ @Override
+ public Principal authenticate(X509Certificate certs[]) {
+ return realm.authenticate(certs);
+ }
+
+ @Override
+ public Principal authenticate(
+ String username,
+ String digest,
+ String nonce,
+ String nc,
+ String cnonce,
+ String qop,
+ String realmName,
+ String md5a2
+ ) {
+ return realm.authenticate(username, digest, nonce, nc, cnonce, qop, realmName, md5a2);
+ }
+
+ @Override
+ public Principal authenticate(GSSContext gssContext, boolean storeCreds) {
+ return realm.authenticate(gssContext, storeCreds);
+ }
+
+ @Override
+ public boolean hasResourcePermission(
+ Request request,
+ Response response,
+ SecurityConstraint[] constraints,
+ Context context
+ ) throws IOException {
+ return realm.hasResourcePermission(request, response, constraints, context);
+ }
+
+ @Override
+ public String getInfo() {
+ return realm.getInfo();
+ }
+
+ @Override
+ public void backgroundProcess() {
+ realm.backgroundProcess();
+ }
+
+ @Override
+ public SecurityConstraint[] findSecurityConstraints(Request request, Context context) {
+ return realm.findSecurityConstraints(request, context);
+ }
+
+ @Override
+ public boolean hasRole(Wrapper wrapper, Principal principal, String role) {
+ return realm.hasRole(wrapper, principal, role);
+ }
+
+ @Override
+ public boolean hasUserDataPermission(
+ Request request,
+ Response response,
+ SecurityConstraint[] constraint
+ ) throws IOException {
+ return realm.hasUserDataPermission(request, response, constraint);
+ }
+
+ @Override
+ public void addPropertyChangeListener(PropertyChangeListener listener) {
+ realm.addPropertyChangeListener(listener);
+ }
+
+ @Override
+ public void removePropertyChangeListener(PropertyChangeListener listener) {
+ realm.removePropertyChangeListener(listener);
+ }
+}
diff --git a/base/server/tomcat7/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java b/base/server/tomcat7/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java
new file mode 100644
index 000000000..20bf85d22
--- /dev/null
+++ b/base/server/tomcat7/src/com/netscape/cms/tomcat/SSLAuthenticatorWithFallback.java
@@ -0,0 +1,172 @@
+// --- 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.cms.tomcat;
+
+import java.io.IOException;
+import java.security.cert.X509Certificate;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import javax.servlet.http.HttpServletResponseWrapper;
+
+import org.apache.catalina.Container;
+import org.apache.catalina.Globals;
+import org.apache.catalina.LifecycleException;
+import org.apache.catalina.authenticator.AuthenticatorBase;
+import org.apache.catalina.authenticator.BasicAuthenticator;
+import org.apache.catalina.authenticator.FormAuthenticator;
+import org.apache.catalina.authenticator.SSLAuthenticator;
+import org.apache.catalina.connector.Request;
+import org.apache.catalina.deploy.LoginConfig;
+
+/**
+ * @author Endi S. Dewata
+ */
+public class SSLAuthenticatorWithFallback extends AuthenticatorBase {
+
+ public final static String BASIC_AUTHENTICATOR = "BASIC";
+ public final static String FORM_AUTHENTICATOR = "FORM";
+
+ String fallbackMethod = BASIC_AUTHENTICATOR;
+
+ AuthenticatorBase sslAuthenticator = new SSLAuthenticator();
+ AuthenticatorBase fallbackAuthenticator = new BasicAuthenticator();
+
+ public SSLAuthenticatorWithFallback() {
+ log("Creating SSL authenticator with fallback");
+ }
+
+ @Override
+ public String getInfo() {
+ return "SSL authenticator with "+fallbackMethod+" fallback.";
+ }
+
+ public String getFallbackMethod() {
+ return fallbackMethod;
+ }
+
+ public void setFallbackMethod(String fallbackMethod) {
+ log("Fallback method: "+fallbackMethod);
+ this.fallbackMethod = fallbackMethod;
+
+ if (BASIC_AUTHENTICATOR.equalsIgnoreCase(fallbackMethod)) {
+ fallbackAuthenticator = new BasicAuthenticator();
+
+ } else if (FORM_AUTHENTICATOR.equalsIgnoreCase(fallbackMethod)) {
+ fallbackAuthenticator = new FormAuthenticator();
+ }
+
+ }
+
+ @Override
+ public boolean authenticate(Request request, HttpServletResponse response, LoginConfig config) throws IOException {
+
+ X509Certificate certs[] = (X509Certificate[]) request.getAttribute(Globals.CERTIFICATES_ATTR);
+ boolean result;
+
+ if (certs != null && certs.length > 0) {
+ log("Authenticate with client certificate authentication");
+ HttpServletResponseWrapper wrapper = new HttpServletResponseWrapper(response) {
+ public void setHeader(String name, String value) {
+ log("SSL auth header: "+name+"="+value);
+ };
+ public void sendError(int code) {
+ log("SSL auth return code: "+code);
+ }
+ };
+ result = sslAuthenticator.authenticate(request, wrapper, config);
+
+ } else {
+ log("Authenticating with "+fallbackMethod+" authentication");
+ HttpServletResponseWrapper wrapper = new HttpServletResponseWrapper(response) {
+ public void setHeader(String name, String value) {
+ log("Fallback auth header: "+name+"="+value);
+ };
+ public void sendError(int code) {
+ log("Fallback auth return code: "+code);
+ }
+ };
+ result = fallbackAuthenticator.authenticate(request, wrapper, config);
+ }
+
+ if (result)
+ return true;
+
+ log("Result: "+result);
+
+ StringBuilder value = new StringBuilder(16);
+ value.append("Basic realm=\"");
+ if (config.getRealmName() == null) {
+ value.append(REALM_NAME);
+ } else {
+ value.append(config.getRealmName());
+ }
+ value.append('\"');
+ response.setHeader(AUTH_HEADER_NAME, value.toString());
+ response.sendError(HttpServletResponse.SC_UNAUTHORIZED);
+
+ return false;
+ }
+
+ @Override
+ protected String getAuthMethod() {
+ return HttpServletRequest.CLIENT_CERT_AUTH;
+ };
+
+ @Override
+ public void setContainer(Container container) {
+ log("Setting container");
+ super.setContainer(container);
+ sslAuthenticator.setContainer(container);
+ fallbackAuthenticator.setContainer(container);
+ }
+
+ @Override
+ protected void initInternal() throws LifecycleException {
+ log("Initializing authenticators");
+
+ super.initInternal();
+
+ sslAuthenticator.setAlwaysUseSession(alwaysUseSession);
+ sslAuthenticator.init();
+
+ fallbackAuthenticator.setAlwaysUseSession(alwaysUseSession);
+ fallbackAuthenticator.init();
+ }
+
+ @Override
+ public void startInternal() throws LifecycleException {
+ log("Starting authenticators");
+ super.startInternal();
+ sslAuthenticator.start();
+ fallbackAuthenticator.start();
+ }
+
+ @Override
+ public void stopInternal() throws LifecycleException {
+ log("Stopping authenticators");
+ super.stopInternal();
+ sslAuthenticator.stop();
+ fallbackAuthenticator.stop();
+ }
+
+ public void log(String message) {
+ System.out.println("SSLAuthenticatorWithFallback: "+message);
+ }
+}
diff --git a/base/server/tomcat7/src/pki-tomcat.mf b/base/server/tomcat7/src/pki-tomcat.mf
new file mode 100644
index 000000000..ca8d3bf1b
--- /dev/null
+++ b/base/server/tomcat7/src/pki-tomcat.mf
@@ -0,0 +1,3 @@
+Name: pki-tomcat
+Specification-Version: ${APPLICATION_VERSION}
+Implementation-Version: ${VERSION}