This is an automated email from the ASF dual-hosted git repository.

markt-asf pushed a commit to branch 10.1.x
in repository https://gitbox.apache.org/repos/asf/tomcat.git


The following commit(s) were added to refs/heads/10.1.x by this push:
     new a455626243 Follow-up to parsing improvements
a455626243 is described below

commit a455626243088c9348f9831d056a5b7a3a9e5fe4
Author: Mark Thomas <[email protected]>
AuthorDate: Mon Jul 20 18:07:38 2026 +0100

    Follow-up to parsing improvements
---
 .../catalina/valves/rewrite/ResolverImpl.java      |  5 +-
 .../valves/rewrite/TestResolverSSLComponents.java  | 58 ++++++++++++++++++++++
 webapps/docs/changelog.xml                         |  4 ++
 3 files changed, 65 insertions(+), 2 deletions(-)

diff --git a/java/org/apache/catalina/valves/rewrite/ResolverImpl.java 
b/java/org/apache/catalina/valves/rewrite/ResolverImpl.java
index 4b70d39e72..cda10c6849 100644
--- a/java/org/apache/catalina/valves/rewrite/ResolverImpl.java
+++ b/java/org/apache/catalina/valves/rewrite/ResolverImpl.java
@@ -284,7 +284,7 @@ public class ResolverImpl extends Resolver {
         } else if (key.equals("M_SERIAL")) {
             return certificates[0].getSerialNumber().toString();
         } else if (key.equals("S_DN")) {
-            return certificates[0].getSubjectX500Principal().toString();
+            return certificates[0].getSubjectX500Principal().getName();
         } else if (key.startsWith("S_DN_")) {
             key = key.substring("S_DN_".length());
             return 
resolveComponent(certificates[0].getSubjectX500Principal().getName(), key);
@@ -300,7 +300,7 @@ public class ResolverImpl extends Resolver {
             return certificates[0].getIssuerX500Principal().getName();
         } else if (key.startsWith("I_DN_")) {
             key = key.substring("I_DN_".length());
-            return 
resolveComponent(certificates[0].getIssuerX500Principal().toString(), key);
+            return 
resolveComponent(certificates[0].getIssuerX500Principal().getName(), key);
         } else if (key.equals("V_START")) {
             return String.valueOf(certificates[0].getNotBefore().getTime());
         } else if (key.equals("V_END")) {
@@ -390,6 +390,7 @@ public class ResolverImpl extends Resolver {
         StringBuilder sb = new StringBuilder(s.length());
         for (int i = 0; i < s.length(); i++) {
             char c = s.charAt(i);
+            // Note: Does not handle hex escapes
             if (c == '\\' && i + 1 < s.length()) {
                 char next = s.charAt(i + 1);
                 sb.append(next);
diff --git 
a/test/org/apache/catalina/valves/rewrite/TestResolverSSLComponents.java 
b/test/org/apache/catalina/valves/rewrite/TestResolverSSLComponents.java
new file mode 100644
index 0000000000..0aa3f60f52
--- /dev/null
+++ b/test/org/apache/catalina/valves/rewrite/TestResolverSSLComponents.java
@@ -0,0 +1,58 @@
+/*
+ * 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.
+ */
+package org.apache.catalina.valves.rewrite;
+
+import java.io.IOException;
+import java.security.cert.X509Certificate;
+
+import javax.security.auth.x500.X500Principal;
+
+import org.junit.Assert;
+import org.junit.Test;
+
+import org.apache.catalina.connector.Request;
+import org.apache.juli.logging.Log;
+import org.apache.tomcat.util.net.SSLSupport;
+import org.easymock.EasyMock;
+
+public class TestResolverSSLComponents {
+
+    @Test
+    public void testEscapedComma() throws Exception {
+        Resolver resolver = createResolver("CN=abc\\,def,OU=xyz");
+
+        Assert.assertEquals("abc,def", 
resolver.resolveSsl("SSL_CLIENT_S_DN_CN"));
+        Assert.assertEquals("xyz", resolver.resolveSsl("SSL_CLIENT_S_DN_OU"));
+    }
+
+
+    private Resolver createResolver(String subjectDn) throws IOException {
+        X509Certificate certificate = 
EasyMock.createMock(X509Certificate.class);
+        
EasyMock.expect(certificate.getSubjectX500Principal()).andStubReturn(new 
X500Principal(subjectDn));
+
+        SSLSupport sslSupport = EasyMock.createMock(SSLSupport.class);
+        
EasyMock.expect(sslSupport.getPeerCertificateChain()).andStubReturn(new 
X509Certificate[] { certificate });
+
+        Request request = EasyMock.createMock(Request.class);
+        
EasyMock.expect(request.getAttribute(SSLSupport.SESSION_MGR)).andStubReturn(sslSupport);
+
+        Log log = EasyMock.createNiceMock(Log.class);
+        EasyMock.replay(certificate, sslSupport, request, log);
+
+        return new ResolverImpl(request, log);
+    }
+}
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index f269a3b563..83723aa648 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -148,6 +148,10 @@
         parent directory name for directory listings produced by the default
         servlet. Ensure XML escaping is used with XML output. (markt)
       </fix>
+      <fix>
+        When processing certificate subject names and issuer names within
+        RewriteValve rules, always use the RFC 2253 format name. (markt)
+      </fix>
     </changelog>
   </subsection>
   <subsection name="Coyote">


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to