ASF Bugzilla – Attachment 31140 Details for
Bug 55917
Cookie parsing fails hard with ISO-8859-1 values
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
Allow 0xa0-0xff in V0 values only
bug55917-v2.patch (text/plain), 5.70 KB, created by
Jeremy Boynes
on 2013-12-21 21:20:43 UTC
(
hide
)
Description:
Allow 0xa0-0xff in V0 values only
Filename:
MIME Type:
Creator:
Jeremy Boynes
Created:
2013-12-21 21:20:43 UTC
Size:
5.70 KB
patch
obsolete
>Index: java/org/apache/tomcat/util/http/Cookies.java >=================================================================== >--- java/org/apache/tomcat/util/http/Cookies.java (revision 1552814) >+++ java/org/apache/tomcat/util/http/Cookies.java (working copy) >@@ -508,14 +508,7 @@ > private static final int getTokenEndPosition(byte bytes[], int off, int end, > int version, boolean isName){ > int pos = off; >- while (pos < end && >- (!CookieSupport.isHttpSeparator((char)bytes[pos]) || >- version == 0 && >- CookieSupport.ALLOW_HTTP_SEPARATORS_IN_V0 && >- bytes[pos] != '=' && >- !CookieSupport.isV0Separator((char)bytes[pos]) || >- !isName && bytes[pos] == '=' && >- CookieSupport.ALLOW_EQUALS_IN_VALUE)) { >+ while (pos < end && allowInToken(bytes[pos], version, isName)) { > pos++; > } > >@@ -525,6 +518,34 @@ > return pos; > } > >+ private static boolean allowInToken(byte b, int version, boolean isName) { >+ // byte is signed so cast into a positive int for comparisons >+ int octet = ((int)b) & 0xff; >+ >+ // disallow all controls >+ if (octet < 0x20 && octet != 0x09 || octet >= 0x7f && octet < 0xa0) { >+ throw new IllegalArgumentException( >+ "Control character in cookie value or attribute."); >+ } >+ >+ // values 0xa0-0xff are allowed in V0 values, otherwise disallow >+ if (octet >= 0x80) { >+ if (isName || version != 0) { >+ throw new IllegalArgumentException( >+ "Control character in cookie value or attribute."); >+ } >+ return true; >+ } >+ >+ return !CookieSupport.isHttpSeparator((char) b) || >+ version == 0 && >+ CookieSupport.ALLOW_HTTP_SEPARATORS_IN_V0 && >+ b != '=' && >+ !CookieSupport.isV0Separator((char) b) || >+ !isName && b == '=' && >+ CookieSupport.ALLOW_EQUALS_IN_VALUE; >+ } >+ > /** > * Given a starting position after an initial quote character, this gets > * the position of the end quote. This escapes anything after a '\' char >Index: test/org/apache/tomcat/util/http/TestCookies.java >=================================================================== >--- test/org/apache/tomcat/util/http/TestCookies.java (revision 1552814) >+++ test/org/apache/tomcat/util/http/TestCookies.java (working copy) >@@ -17,11 +17,108 @@ > > package org.apache.tomcat.util.http; > >+import java.nio.charset.StandardCharsets; >+ >+import javax.servlet.http.Cookie; >+ >+import org.junit.Assert; >+import org.junit.Before; >+import org.junit.Ignore; > import org.junit.Test; > > public class TestCookies { >+ private Cookies cookies; > >+ @Before >+ public void init() { >+ this.cookies = new Cookies(null); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8bitInName() { >+ process("f\u00f6o=bar"); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallowControlInName() { >+ process("f\010o=bar"); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8BitControlInName() { >+ process("f\210o=bar"); >+ } >+ > @Test >+ public void allow8BitInV0Value() { >+ process("foo=b\u00e1r"); >+ expect(makeCookie("foo", "b\u00e1r", 0)); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8bitInV1UnquotedValue() { >+ process("$Version=1; foo=b\u00e1r"); >+ } >+ >+ @Test >+ public void allow8bitInV1QuotedValue() { >+ process("$Version=1; foo=\"b\u00e1r\""); >+ expect(makeCookie("foo", "b\u00e1r", 1)); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallowControlInV0Value() { >+ process("foo=b\010r"); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8BitControlInV0Value() { >+ process("foo=b\210r"); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallowControlInV1UnquotedValue() { >+ process("$Version=1; foo=b\010r"); >+ } >+ >+ @Ignore >+ @Test(expected = IllegalArgumentException.class) >+ public void disallowControlInV1QuotedValue() { >+ process("$Version=1; foo=\"b\010r\""); >+ } >+ >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8BitControlInV1UnquotedValue() { >+ process("$Version=1; foo=b\210r"); >+ } >+ >+ @Ignore >+ @Test(expected = IllegalArgumentException.class) >+ public void disallow8BitControlInV1QuotedValue() { >+ process("$Version=1; foo=\"b\210r\""); >+ } >+ >+ private void process(String header) { >+ byte[] bytes = header.getBytes(StandardCharsets.ISO_8859_1); >+ cookies.processCookieHeader(bytes, 0, bytes.length); >+ } >+ >+ private void expect(Cookie... expected) { >+ Assert.assertEquals(expected.length, cookies.getCookieCount()); >+ for (int i = 0; i < expected.length; i++) { >+ ServerCookie actual = cookies.getCookie(i); >+ Assert.assertEquals(expected[i].getName(), actual.getName().toString()); >+ Assert.assertEquals(expected[i].getValue(), actual.getValue().toString()); >+ } >+ } >+ >+ private static Cookie makeCookie(String name, String value, int version) { >+ Cookie cookie = new Cookie(name, value); >+ cookie.setVersion(version); >+ return cookie; >+ } >+ >+ @Test > public void testCookies() throws Exception { > test("foo=bar; a=b", "foo", "bar", "a", "b"); > test("foo=bar;a=b", "foo", "bar", "a", "b");
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 55917
:
31139
| 31140