Author: markt
Date: Mon May 14 10:50:22 2018
New Revision: 1831556

URL: http://svn.apache.org/viewvc?rev=1831556&view=rev
Log:
Relax Host validation by removing the requirement that the final component of a 
FQDN must be alphabetic.

Modified:
    tomcat/trunk/java/org/apache/tomcat/util/http/parser/HttpParser.java
    tomcat/trunk/java/org/apache/tomcat/util/http/parser/LocalStrings.properties
    tomcat/trunk/test/org/apache/tomcat/util/http/parser/TestHttpParserHost.java
    tomcat/trunk/webapps/docs/changelog.xml

Modified: tomcat/trunk/java/org/apache/tomcat/util/http/parser/HttpParser.java
URL: 
http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/tomcat/util/http/parser/HttpParser.java?rev=1831556&r1=1831555&r2=1831556&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/tomcat/util/http/parser/HttpParser.java 
(original)
+++ tomcat/trunk/java/org/apache/tomcat/util/http/parser/HttpParser.java Mon 
May 14 10:50:22 2018
@@ -667,17 +667,13 @@ public class HttpParser {
             pos++;
         } while (true);
 
-        if (octetCount != 4) {
+        if (octetCount != 4 || octet < 0 || octet > 255) {
             // Might not be an IPv4 address. Could be a host name or a FQDN 
with
             // fully numeric components. Go back to the start and parse as a
             // host / FQDN.
             reader.reset();
             return readHostDomainName(reader);
         }
-        if (octet < 0 || octet > 255) {
-            throw new IllegalArgumentException(
-                    sm.getString("http.invalidOctet", 
Integer.toString(octet)));
-        }
 
         return pos;
     }
@@ -788,13 +784,9 @@ public class HttpParser {
     static int readHostDomainName(Reader reader) throws IOException {
         DomainParseState state = DomainParseState.NEW;
         int pos = 0;
-        int segmentIndex = 0;
 
         while (state.mayContinue()) {
-            state = state.next(reader.read(), segmentIndex);
-            if (DomainParseState.PERIOD == state) {
-                segmentIndex++;
-            }
+            state = state.next(reader.read());
             pos++;
         }
 
@@ -836,31 +828,23 @@ public class HttpParser {
     }
 
 
-    private enum AllowsEnd {
-        NEVER,
-        FIRST,
-        ALWAYS
-    }
-
-
     private enum DomainParseState {
-        NEW(       true, false, false,  AllowsEnd.NEVER, " at the start of"),
-        ALL_ALPHA( true,  true,  true, AllowsEnd.ALWAYS, " after a letter in"),
-        ALPHA(     true,  true,  true,  AllowsEnd.FIRST, " after a letter in"),
-        NUMERIC(   true,  true,  true,  AllowsEnd.FIRST, " after a number in"),
-        PERIOD(    true, false, false,  AllowsEnd.NEVER, " after a period in"),
-        HYPHEN(    true,  true, false,  AllowsEnd.NEVER, " after a hypen in"),
-        COLON(    false, false, false,  AllowsEnd.NEVER, " after a colon in"),
-        END(      false, false, false,  AllowsEnd.NEVER, " at the end of");
+        NEW(     true, false, false, false, " at the start of"),
+        ALPHA(   true,  true,  true,  true, " after a letter in"),
+        NUMERIC( true,  true,  true,  true, " after a number in"),
+        PERIOD(  true, false, false, false, " after a period in"),
+        HYPHEN(  true,  true, false, false, " after a hypen in"),
+        COLON(  false, false, false, false, " after a colon in"),
+        END(    false, false, false, false, " at the end of");
 
         private final boolean mayContinue;
         private final boolean allowsHyphen;
         private final boolean allowsPeriod;
-        private final AllowsEnd allowsEnd;
+        private final boolean allowsEnd;
         private final String errorLocation;
 
         private DomainParseState(boolean mayContinue, boolean allowsHyphen, 
boolean allowsPeriod,
-                AllowsEnd allowsEnd, String errorLocation) {
+                boolean allowsEnd, String errorLocation) {
             this.mayContinue = mayContinue;
             this.allowsHyphen = allowsHyphen;
             this.allowsPeriod = allowsPeriod;
@@ -872,13 +856,9 @@ public class HttpParser {
             return mayContinue;
         }
 
-        public DomainParseState next(int c, int segmentIndex) {
+        public DomainParseState next(int c) {
             if (HttpParser.isAlpha(c)) {
-                if (ALL_ALPHA == this || NEW == this || PERIOD == this) {
-                    return ALL_ALPHA;
-                } else {
-                    return ALPHA;
-                }
+                return ALPHA;
             } else if (HttpParser.isNumeric(c)) {
                 return NUMERIC;
             } else if (c == '.') {
@@ -889,26 +869,18 @@ public class HttpParser {
                             Character.toString((char) c), errorLocation));
                 }
             } else if (c == ':') {
-                if (allowsEnd == AllowsEnd.ALWAYS ||
-                        allowsEnd == AllowsEnd.FIRST && segmentIndex == 0) {
+                if (allowsEnd) {
                     return COLON;
                 } else {
                     throw new 
IllegalArgumentException(sm.getString("http.invalidCharacterDomain",
                             Character.toString((char) c), errorLocation));
                 }
             } else if (c == -1) {
-                if (allowsEnd == AllowsEnd.ALWAYS ||
-                        allowsEnd == AllowsEnd.FIRST && segmentIndex == 0) {
+                if (allowsEnd) {
                     return END;
                 } else {
-                    String msg;
-                    if (allowsEnd == AllowsEnd.NEVER) {
-                        msg = sm.getString("http.invalidSegmentEndState", 
this.name());
-                    } else {
-                        // allowsEnd == AllowsEnd.FIRST && segmentIndex > 0
-                        msg = sm.getString("http.invalidEndState", 
this.name());
-                    }
-                    throw new IllegalArgumentException(msg);
+                    throw new IllegalArgumentException(
+                            sm.getString("http.invalidSegmentEndState", 
this.name()));
                 }
             } else if (c == '-') {
                 if (allowsHyphen) {

Modified: 
tomcat/trunk/java/org/apache/tomcat/util/http/parser/LocalStrings.properties
URL: 
http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/tomcat/util/http/parser/LocalStrings.properties?rev=1831556&r1=1831555&r2=1831556&view=diff
==============================================================================
--- 
tomcat/trunk/java/org/apache/tomcat/util/http/parser/LocalStrings.properties 
(original)
+++ 
tomcat/trunk/java/org/apache/tomcat/util/http/parser/LocalStrings.properties 
Mon May 14 10:50:22 2018
@@ -26,7 +26,6 @@ http.illegalCharacterDomain=The characte
 http.illegalCharacterIpv4=The character [{0}] is never valid in an IPv4 
address.
 http.illegalCharacterIpv6=The character [{0}] is never valid in an IPv6 
address.
 http.invalidCharacterDomain=The character [{0}] is not valid{1} a domain name.
-http.invalidEndState=The state [{0}] is not valid for the end of a domain name.
 http.invalidHextet=Invalid hextet. A hextet must consist of 4 or less hex 
characters.
 http.invalidIpv4Location=The IPv6 address contains an embedded IPv4 address at 
an invalid location.
 http.invalidOctet=Invalid octet [{0}]. The valid range for IPv4 octets is 0 to 
255.

Modified: 
tomcat/trunk/test/org/apache/tomcat/util/http/parser/TestHttpParserHost.java
URL: 
http://svn.apache.org/viewvc/tomcat/trunk/test/org/apache/tomcat/util/http/parser/TestHttpParserHost.java?rev=1831556&r1=1831555&r2=1831556&view=diff
==============================================================================
--- 
tomcat/trunk/test/org/apache/tomcat/util/http/parser/TestHttpParserHost.java 
(original)
+++ 
tomcat/trunk/test/org/apache/tomcat/util/http/parser/TestHttpParserHost.java 
Mon May 14 10:50:22 2018
@@ -56,18 +56,25 @@ public class TestHttpParserHost {
         result.add(new Object[] { TestType.IPv4, "0.0.0.0:8080", 
Integer.valueOf(7), null} );
         result.add(new Object[] { TestType.IPv4, "0", Integer.valueOf(-1), 
null} );
         // IPv4 - invalid
-        result.add(new Object[] { TestType.IPv4, "0.0", Integer.valueOf(-1), 
IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.0.0", Integer.valueOf(-1), 
IAE} );
         result.add(new Object[] { TestType.IPv4, ".0.0.0", 
Integer.valueOf(-1), IAE} );
         result.add(new Object[] { TestType.IPv4, "0.0.0.", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "256.0.0.0", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.256.0.0", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.0.256.0", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.0.0.256", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.a.0.0", 
Integer.valueOf(-1), IAE} );
         result.add(new Object[] { TestType.IPv4, "0..0.0", 
Integer.valueOf(-1), IAE} );
         result.add(new Object[] { TestType.IPv4, "0]", Integer.valueOf(-1), 
IAE} );
         // Domain Name - valid
+        result.add(new Object[] { TestType.IPv4, "0.0", Integer.valueOf(-1), 
null} );
+        result.add(new Object[] { TestType.IPv4, "0.0:8080", 
Integer.valueOf(3), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0", Integer.valueOf(-1), 
null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0:8080", 
Integer.valueOf(5), null} );
+        result.add(new Object[] { TestType.IPv4, "256.0.0.0", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "256.0.0.0:8080", 
Integer.valueOf(9), null} );
+        result.add(new Object[] { TestType.IPv4, "0.256.0.0", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.256.0.0:8080", 
Integer.valueOf(9), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.256.0", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.256.0:8080", 
Integer.valueOf(9), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0.256", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0.256:8080", 
Integer.valueOf(9), null} );
+        result.add(new Object[] { TestType.IPv4, "0.a.0.0", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.a.0.0:8080", 
Integer.valueOf(7), null} );
         result.add(new Object[] { TestType.IPv4, "localhost", 
Integer.valueOf(-1), null} );
         result.add(new Object[] { TestType.IPv4, "localhost:8080", 
Integer.valueOf(9), null} );
         result.add(new Object[] { TestType.IPv4, "tomcat.apache.org", 
Integer.valueOf(-1), null} );
@@ -80,18 +87,42 @@ public class TestHttpParserHost {
         result.add(new Object[] { TestType.IPv4, "foo.0.0.com:8080", 
Integer.valueOf(11), null} );
         result.add(new Object[] { TestType.IPv4, "1foo.0.0.com", 
Integer.valueOf(-1), null} );
         result.add(new Object[] { TestType.IPv4, "1foo.0.0.com:8080", 
Integer.valueOf(12), null} );
+        result.add(new Object[] { TestType.IPv4, "foo1.0.0.com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo1.0.0.com:8080", 
Integer.valueOf(12), null} );
+        result.add(new Object[] { TestType.IPv4, "1foo1.0.0.com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "1foo1.0.0.com:8080", 
Integer.valueOf(13), null} );
         result.add(new Object[] { TestType.IPv4, "1-foo.0.0.com", 
Integer.valueOf(-1), null} );
         result.add(new Object[] { TestType.IPv4, "1-foo.0.0.com:8080", 
Integer.valueOf(13), null} );
         result.add(new Object[] { TestType.IPv4, "1--foo.0.0.com", 
Integer.valueOf(-1), null} );
         result.add(new Object[] { TestType.IPv4, "1--foo.0.0.com:8080", 
Integer.valueOf(14), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1com:8080", 
Integer.valueOf(12), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.com1", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.com1:8080", 
Integer.valueOf(12), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1com1", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1com1:8080", 
Integer.valueOf(13), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1-com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1-com:8080", 
Integer.valueOf(13), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1--com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.0.0.1--com:8080", 
Integer.valueOf(14), null} );
         result.add(new Object[] { TestType.IPv4, "com", Integer.valueOf(-1), 
null} );
         result.add(new Object[] { TestType.IPv4, "com:8080", 
Integer.valueOf(3), null} );
         result.add(new Object[] { TestType.IPv4, "0com", Integer.valueOf(-1), 
null} );
         result.add(new Object[] { TestType.IPv4, "0com:8080", 
Integer.valueOf(4), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0com:8080", 
Integer.valueOf(8), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0.0com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "0.0.0.0com:8080", 
Integer.valueOf(10), null} );
         result.add(new Object[] { TestType.IPv4, "123", Integer.valueOf(-1), 
null} );
         result.add(new Object[] { TestType.IPv4, "123:8080", 
Integer.valueOf(3), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.bar.0com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "foo.bar.0com:8080", 
Integer.valueOf(12), null} );
         result.add(new Object[] { TestType.IPv4, "myapp-t.mydomain.com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "myapp-t.mydomain.com:8080", 
Integer.valueOf(20), null} );
         result.add(new Object[] { TestType.IPv4, "myapp-t.my-domain.com", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, "myapp-t.my-domain.com:8080", 
Integer.valueOf(21), null} );
+        result.add(new Object[] { TestType.IPv4, "myapp-t.my-domain.c-om", 
Integer.valueOf(-1), null} );
+        result.add(new Object[] { TestType.IPv4, 
"myapp-t.my-domain.c-om:8080", Integer.valueOf(22), null} );
         // Domain Name - invalid
         result.add(new Object[] { TestType.IPv4, ".", Integer.valueOf(-1), 
IAE} );
         result.add(new Object[] { TestType.IPv4, ".:8080", 
Integer.valueOf(-1), IAE} );
@@ -108,11 +139,6 @@ public class TestHttpParserHost {
         result.add(new Object[] { TestType.IPv4, "foo.-bar", 
Integer.valueOf(-1), IAE} );
         result.add(new Object[] { TestType.IPv4, "foo.^bar", 
Integer.valueOf(-1), IAE} );
         result.add(new Object[] { TestType.IPv4, "foo.b*ar", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.0.0com", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "0.0.0.0com", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "foo.bar.0com", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "foo.bar.0com:8080", 
Integer.valueOf(-1), IAE} );
-        result.add(new Object[] { TestType.IPv4, "myapp-t.my-domain.c-om", 
Integer.valueOf(-1), IAE} );
         // IPv6 - valid
         result.add(new Object[] { TestType.IPv6, "[::1]", Integer.valueOf(-1), 
null} );
         result.add(new Object[] { TestType.IPv6, "[::1]:8080", 
Integer.valueOf(5), null} );

Modified: tomcat/trunk/webapps/docs/changelog.xml
URL: 
http://svn.apache.org/viewvc/tomcat/trunk/webapps/docs/changelog.xml?rev=1831556&r1=1831555&r2=1831556&view=diff
==============================================================================
--- tomcat/trunk/webapps/docs/changelog.xml (original)
+++ tomcat/trunk/webapps/docs/changelog.xml Mon May 14 10:50:22 2018
@@ -105,6 +105,10 @@
         is sending AJP messages that are too large for the configured
         <code>packetSize</code>. (markt)
       </fix>
+      <fix>
+        Relax Host validation by removing the requirement that the final
+        component of a FQDN must be alphabetic. (markt)
+      </fix>
     </changelog>
   </subsection>
   <subsection name="Jasper">



---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org
For additional commands, e-mail: dev-h...@tomcat.apache.org

Reply via email to