Author: jfrederic.clere(a)jboss.com
Date: 2009-09-18 12:41:08 -0400 (Fri, 18 Sep 2009)
New Revision: 1171
Modified:
branches/2.1.x/java/org/apache/catalina/core/AprLifecycleListener.java
branches/2.1.x/java/org/apache/coyote/http11/Http11AprProcessor.java
branches/2.1.x/java/org/apache/tomcat/jni/SSLSocket.java
branches/2.1.x/webapps/docs/changelog.xml
Log:
Patch for ASF bugzilla 46950.
Modified: branches/2.1.x/java/org/apache/catalina/core/AprLifecycleListener.java
===================================================================
--- branches/2.1.x/java/org/apache/catalina/core/AprLifecycleListener.java 2009-09-17
09:03:16 UTC (rev 1170)
+++ branches/2.1.x/java/org/apache/catalina/core/AprLifecycleListener.java 2009-09-18
16:41:08 UTC (rev 1171)
@@ -58,8 +58,8 @@
protected static final int TCN_REQUIRED_MAJOR = 1;
protected static final int TCN_REQUIRED_MINOR = 1;
- protected static final int TCN_REQUIRED_PATCH = 8;
- protected static final int TCN_RECOMMENDED_PV = 12;
+ protected static final int TCN_REQUIRED_PATCH = 17;
+ protected static final int TCN_RECOMMENDED_PV = 17;
// ---------------------------------------------- Properties
Modified: branches/2.1.x/java/org/apache/coyote/http11/Http11AprProcessor.java
===================================================================
--- branches/2.1.x/java/org/apache/coyote/http11/Http11AprProcessor.java 2009-09-17
09:03:16 UTC (rev 1170)
+++ branches/2.1.x/java/org/apache/coyote/http11/Http11AprProcessor.java 2009-09-18
16:41:08 UTC (rev 1171)
@@ -1179,10 +1179,11 @@
request.setAttribute(AprEndpoint.CIPHER_SUITE_KEY, sslO);
}
// Get client certificate and the certificate chain if present
+ // certLength == -1 indicates an error
int certLength = SSLSocket.getInfoI(socket,
SSL.SSL_INFO_CLIENT_CERT_CHAIN);
byte[] clientCert = SSLSocket.getInfoB(socket,
SSL.SSL_INFO_CLIENT_CERT);
X509Certificate[] certs = null;
- if (clientCert != null) {
+ if (clientCert != null && certLength > -1) {
certs = new X509Certificate[certLength + 1];
CertificateFactory cf =
CertificateFactory.getInstance("X.509");
certs[0] = (X509Certificate) cf.generateCertificate(new
ByteArrayInputStream(clientCert));
@@ -1218,24 +1219,30 @@
inputBuffer.addActiveFilter(inputFilters[Constants.BUFFERED_FILTER]);
}
try {
+ // Configure connection to require a certificate
+ SSLSocket.setVerify(socket, SSL.SSL_CVERIFY_REQUIRE,
+ endpoint.getSSLVerifyDepth());
// Renegociate certificates
- SSLSocket.renegotiate(socket);
- // Get client certificate and the certificate chain if present
- int certLength = SSLSocket.getInfoI(socket,
SSL.SSL_INFO_CLIENT_CERT_CHAIN);
- byte[] clientCert = SSLSocket.getInfoB(socket,
SSL.SSL_INFO_CLIENT_CERT);
- X509Certificate[] certs = null;
- if (clientCert != null) {
- certs = new X509Certificate[certLength + 1];
- CertificateFactory cf =
CertificateFactory.getInstance("X.509");
- certs[0] = (X509Certificate) cf.generateCertificate(new
ByteArrayInputStream(clientCert));
- for (int i = 0; i < certLength; i++) {
- byte[] data = SSLSocket.getInfoB(socket,
SSL.SSL_INFO_CLIENT_CERT_CHAIN + i);
- certs[i+1] = (X509Certificate) cf.generateCertificate(new
ByteArrayInputStream(data));
+ if (SSLSocket.renegotiate(socket) == 0) {
+ // Don't look for certs unless we know renegotiation worked.
+ // Get client certificate and the certificate chain if present
+ // certLength == -1 indicates an error
+ int certLength = SSLSocket.getInfoI(socket,
SSL.SSL_INFO_CLIENT_CERT_CHAIN);
+ byte[] clientCert = SSLSocket.getInfoB(socket,
SSL.SSL_INFO_CLIENT_CERT);
+ X509Certificate[] certs = null;
+ if (clientCert != null && certLength > -1) {
+ certs = new X509Certificate[certLength + 1];
+ CertificateFactory cf =
CertificateFactory.getInstance("X.509");
+ certs[0] = (X509Certificate) cf.generateCertificate(new
ByteArrayInputStream(clientCert));
+ for (int i = 0; i < certLength; i++) {
+ byte[] data = SSLSocket.getInfoB(socket,
SSL.SSL_INFO_CLIENT_CERT_CHAIN + i);
+ certs[i+1] = (X509Certificate) cf.generateCertificate(new
ByteArrayInputStream(data));
+ }
}
- }
- if (certs != null) {
- request.setAttribute(AprEndpoint.CERTIFICATE_KEY, certs);
- }
+ if (certs != null) {
+ request.setAttribute(AprEndpoint.CERTIFICATE_KEY, certs);
+ }
+ }
} catch (Exception e) {
log.warn(sm.getString("http11processor.socket.ssl"), e);
}
Modified: branches/2.1.x/java/org/apache/tomcat/jni/SSLSocket.java
===================================================================
--- branches/2.1.x/java/org/apache/tomcat/jni/SSLSocket.java 2009-09-17 09:03:16 UTC (rev
1170)
+++ branches/2.1.x/java/org/apache/tomcat/jni/SSLSocket.java 2009-09-18 16:41:08 UTC (rev
1171)
@@ -48,7 +48,7 @@
* response is sent. In more detail: the renegotiation happens after the
* request line and MIME headers were read, but _before_ the attached
* request body is read. The reason simply is that in the HTTP protocol
- * usually there is no acknowledgment step between the headers and the
+ * usually there is no acknowledgement step between the headers and the
* body (there is the 100-continue feature and the chunking facility
* only), so Apache has no API hook for this step.
*
@@ -57,7 +57,30 @@
public static native int renegotiate(long thesocket);
/**
- * Retrun SSL Info parameter as byte array.
+ * Set Type of Client Certificate verification and Maximum depth of CA
+ * Certificates in Client Certificate verification.
+ * <br />
+ * This is used to change the verification level for a connection prior to
+ * starting a re-negotiation.
+ * <br />
+ * The following levels are available for level:
+ * <PRE>
+ * SSL_CVERIFY_NONE - No client Certificate is required at all
+ * SSL_CVERIFY_OPTIONAL - The client may present a valid Certificate
+ * SSL_CVERIFY_REQUIRE - The client has to present a valid
+ * Certificate
+ * SSL_CVERIFY_OPTIONAL_NO_CA - The client may present a valid Certificate
+ * but it need not to be (successfully)
+ * verifiable
+ * </PRE>
+ * <br />
+ * @param sock The socket to change.
+ * @param level Type of Client Certificate verification.
+ */
+ public static native void setVerify(long sock, int level, int depth);
+
+ /**
+ * Return SSL Info parameter as byte array.
*
* @param sock The socket to read the data from.
* @param id Parameter id.
@@ -67,7 +90,7 @@
throws Exception;
/**
- * Retrun SSL Info parameter as String.
+ * Return SSL Info parameter as String.
*
* @param sock The socket to read the data from.
* @param id Parameter id.
@@ -77,7 +100,7 @@
throws Exception;
/**
- * Retrun SSL Info parameter as integer.
+ * Return SSL Info parameter as integer.
*
* @param sock The socket to read the data from.
* @param id Parameter id.
Modified: branches/2.1.x/webapps/docs/changelog.xml
===================================================================
--- branches/2.1.x/webapps/docs/changelog.xml 2009-09-17 09:03:16 UTC (rev 1170)
+++ branches/2.1.x/webapps/docs/changelog.xml 2009-09-18 16:41:08 UTC (rev 1171)
@@ -16,6 +16,16 @@
<body>
+<section name="JBoss Web 2.1.5.GA (remm)">
+ <subsection name="Coyote">
+ <changelog>
+ <fix>
+ <bug>46950</bug>: Allow renegotiation to work for client
certificates. (markt)
+ </fix>
+ </changelog>
+ </subsection>
+</section>
+
<section name="JBoss Web 2.1.4.GA (remm)">
<subsection name="General">
<changelog>