Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJoakim Erdfelt2016-03-18 14:51:32 -0400
committerJoakim Erdfelt2016-03-18 14:51:32 -0400
commit4822bea0b189ae157082504521c507d86c5861d9 (patch)
tree590b9173e7b18f36a26c1503df6adc12e6d791ac
parent05691e16463e02b8376d05c8416722e437e86470 (diff)
downloadorg.eclipse.jetty.project-4822bea0b189ae157082504521c507d86c5861d9.tar.gz
org.eclipse.jetty.project-4822bea0b189ae157082504521c507d86c5861d9.tar.xz
org.eclipse.jetty.project-4822bea0b189ae157082504521c507d86c5861d9.zip
Issue #438 - File and Path Resources with control characters should be rejected
+ Removing regex + Adding StringUtil.indexOfControlChars() Signed-off-by: Joakim Erdfelt <joakim.erdfelt@gmail.com>
-rw-r--r--jetty-util/src/main/java/org/eclipse/jetty/util/StringUtil.java47
-rw-r--r--jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java10
-rw-r--r--jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java11
-rw-r--r--jetty-util/src/test/java/org/eclipse/jetty/util/StringUtilTest.java31
4 files changed, 81 insertions, 18 deletions
diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/StringUtil.java b/jetty-util/src/main/java/org/eclipse/jetty/util/StringUtil.java
index c1b1d4319a..9dbd9e49b7 100644
--- a/jetty-util/src/main/java/org/eclipse/jetty/util/StringUtil.java
+++ b/jetty-util/src/main/java/org/eclipse/jetty/util/StringUtil.java
@@ -374,6 +374,53 @@ public class StringUtil
}
}
+ /**
+ * Find the index of a control characters in String
+ * <p>
+ * This will return a result on the first occurrence of a control character, regardless if
+ * there are more than one.
+ * </p>
+ * <p>
+ * Note: uses codepoint version of {@link Character#isISOControl(int)} to support Unicode better.
+ * </p>
+ *
+ * <pre>
+ * indexOfControlChars(null) == -1
+ * indexOfControlChars("") == -1
+ * indexOfControlChars("\r\n") == 0
+ * indexOfControlChars("\t") == 0
+ * indexOfControlChars(" ") == -1
+ * indexOfControlChars("a") == -1
+ * indexOfControlChars(".") == -1
+ * indexOfControlChars(";\n") == 1
+ * indexOfControlChars("abc\f") == 3
+ * indexOfControlChars("z\010") == 1
+ * indexOfControlChars(":\u001c") == 1
+ * </pre>
+ *
+ * @param str
+ * the string to test.
+ * @return the index of first control character in string, -1 if no control characters encountered
+ */
+ public static int indexOfControlChars(String str)
+ {
+ if (str == null)
+ {
+ return -1;
+ }
+ int len = str.length();
+ for (int i = 0; i < len; i++)
+ {
+ if (Character.isISOControl(str.codePointAt(i)))
+ {
+ // found a control character, we can stop searching now
+ return i;
+ }
+ }
+ // no control characters
+ return -1;
+ }
+
/* ------------------------------------------------------------ */
/**
* Test if a string is null or only has whitespace characters in it.
diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java
index 5ecc6c5e12..dbc4670a72 100644
--- a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java
+++ b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java
@@ -32,10 +32,9 @@ import java.nio.channels.ReadableByteChannel;
import java.nio.file.InvalidPathException;
import java.nio.file.StandardOpenOption;
import java.security.Permission;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
import org.eclipse.jetty.util.IO;
+import org.eclipse.jetty.util.StringUtil;
import org.eclipse.jetty.util.URIUtil;
import org.eclipse.jetty.util.log.Log;
import org.eclipse.jetty.util.log.Logger;
@@ -53,7 +52,6 @@ import org.eclipse.jetty.util.log.Logger;
public class FileResource extends Resource
{
private static final Logger LOG = Log.getLogger(FileResource.class);
- private static final Pattern CNTRL_PATTERN = Pattern.compile("\\p{Cntrl}");
/* ------------------------------------------------------------ */
private final File _file;
@@ -220,10 +218,10 @@ public class FileResource extends Resource
private void assertValidPath(String path)
{
- Matcher mat = CNTRL_PATTERN.matcher(path);
- if(mat.find())
+ int idx = StringUtil.indexOfControlChars(path);
+ if (idx >= 0)
{
- throw new InvalidPathException(path, "Invalid Character at index " + mat.start());
+ throw new InvalidPathException(path, "Invalid Character at index " + idx);
}
}
diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
index 68ee7628e0..8e773676ea 100644
--- a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
+++ b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/PathResource.java
@@ -38,9 +38,8 @@ import java.nio.file.StandardOpenOption;
import java.nio.file.attribute.FileTime;
import java.util.ArrayList;
import java.util.List;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
+import org.eclipse.jetty.util.StringUtil;
import org.eclipse.jetty.util.log.Log;
import org.eclipse.jetty.util.log.Logger;
@@ -50,7 +49,6 @@ import org.eclipse.jetty.util.log.Logger;
public class PathResource extends Resource
{
private static final Logger LOG = Log.getLogger(PathResource.class);
- private static final Pattern CNTRL_PATTERN = Pattern.compile("\\p{Cntrl}");
private final Path path;
private final URI uri;
@@ -116,10 +114,11 @@ public class PathResource extends Resource
private void assertValidPath(Path path)
{
- Matcher mat = CNTRL_PATTERN.matcher(path.toString());
- if(mat.find())
+ String str = path.toString();
+ int idx = StringUtil.indexOfControlChars(str);
+ if(idx >= 0)
{
- throw new InvalidPathException(path.toString(), "Invalid Character at index " + mat.start());
+ throw new InvalidPathException(str, "Invalid Character at index " + idx);
}
}
diff --git a/jetty-util/src/test/java/org/eclipse/jetty/util/StringUtilTest.java b/jetty-util/src/test/java/org/eclipse/jetty/util/StringUtilTest.java
index a33170a629..09889fa891 100644
--- a/jetty-util/src/test/java/org/eclipse/jetty/util/StringUtilTest.java
+++ b/jetty-util/src/test/java/org/eclipse/jetty/util/StringUtilTest.java
@@ -18,20 +18,20 @@
package org.eclipse.jetty.util;
+import java.nio.charset.StandardCharsets;
+
+import org.junit.Assert;
+import org.junit.Test;
+
import static org.hamcrest.Matchers.arrayContaining;
import static org.hamcrest.Matchers.emptyArray;
+import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.nullValue;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
-import java.nio.charset.StandardCharsets;
-
-import org.hamcrest.Matchers;
-import org.junit.Assert;
-import org.junit.Test;
-
public class StringUtilTest
{
@Test
@@ -206,6 +206,25 @@ public class StringUtilTest
}
@Test
+ public void testHasControlCharacter()
+ {
+ assertThat(StringUtil.indexOfControlChars("\r\n"), is(0));
+ assertThat(StringUtil.indexOfControlChars("\t"), is(0));
+ assertThat(StringUtil.indexOfControlChars(";\n"), is(1));
+ assertThat(StringUtil.indexOfControlChars("abc\fz"), is(3));
+ assertThat(StringUtil.indexOfControlChars("z\010"), is(1));
+ assertThat(StringUtil.indexOfControlChars(":\u001c"), is(1));
+
+ assertThat(StringUtil.indexOfControlChars(null), is(-1));
+ assertThat(StringUtil.indexOfControlChars(""), is(-1));
+ assertThat(StringUtil.indexOfControlChars(" "), is(-1));
+ assertThat(StringUtil.indexOfControlChars("a"), is(-1));
+ assertThat(StringUtil.indexOfControlChars("."), is(-1));
+ assertThat(StringUtil.indexOfControlChars(";"), is(-1));
+ assertThat(StringUtil.indexOfControlChars("Euro is \u20ac"), is(-1));
+ }
+
+ @Test
public void testIsBlank()
{
Assert.assertTrue(StringUtil.isBlank(null));

Back to the top