You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by ma...@apache.org on 2019/09/17 21:04:27 UTC
[tomcat] branch master updated (4ed0a57 -> 6d6e899)
This is an automated email from the ASF dual-hosted git repository.
markt pushed a change to branch master
in repository https://gitbox.apache.org/repos/asf/tomcat.git.
from 4ed0a57 Merge branch 'master' of git@github.com:apache/tomcat.git
new 117bbda Revert "Only decode in standard mode."
new 6d6e899 Fix HTTP/2 related TCK failures
The 2 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails. The revisions
listed as "add" were already present in the repository and have only
been added to this reference.
Summary of changes:
.../apache/coyote/http2/Http2UpgradeHandler.java | 2 +-
.../apache/tomcat/util/codec/binary/Base64.java | 39 ++++++++++++++++------
test/org/apache/coyote/http2/Http2TestBase.java | 2 +-
webapps/docs/changelog.xml | 9 +++++
4 files changed, 40 insertions(+), 12 deletions(-)
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org
[tomcat] 02/02: Fix HTTP/2 related TCK failures
Posted by ma...@apache.org.
This is an automated email from the ASF dual-hosted git repository.
markt pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tomcat.git
commit 6d6e899482e889a37fa6c5fe1d7190d7b0ebbf38
Author: Mark Thomas <ma...@apache.org>
AuthorDate: Tue Sep 17 22:03:31 2019 +0100
Fix HTTP/2 related TCK failures
Use URL safe base 64 encoding rather than standard base 64 encoding when
generating or parsing the <code>HTTP2-Settings</code> header as part of
an HTTP upgrade to <code>h2c</code> as required by RFC 7540.
---
.../apache/coyote/http2/Http2UpgradeHandler.java | 2 +-
.../apache/tomcat/util/codec/binary/Base64.java | 32 +++++++++++++++++-----
test/org/apache/coyote/http2/Http2TestBase.java | 2 +-
webapps/docs/changelog.xml | 9 ++++++
4 files changed, 36 insertions(+), 9 deletions(-)
diff --git a/java/org/apache/coyote/http2/Http2UpgradeHandler.java b/java/org/apache/coyote/http2/Http2UpgradeHandler.java
index 10a1f65..e0f3dde 100644
--- a/java/org/apache/coyote/http2/Http2UpgradeHandler.java
+++ b/java/org/apache/coyote/http2/Http2UpgradeHandler.java
@@ -214,7 +214,7 @@ class Http2UpgradeHandler extends AbstractStream implements InternalHttpUpgradeH
// Process the initial settings frame
stream = getStream(1, true);
String base64Settings = stream.getCoyoteRequest().getHeader(HTTP2_SETTINGS_HEADER);
- byte[] settings = Base64.decodeBase64(base64Settings);
+ byte[] settings = Base64.decodeBase64URLSafe(base64Settings);
// Settings are only valid on stream 0
FrameType.SETTINGS.check(0, settings.length);
diff --git a/java/org/apache/tomcat/util/codec/binary/Base64.java b/java/org/apache/tomcat/util/codec/binary/Base64.java
index 99a501c..da1487f 100644
--- a/java/org/apache/tomcat/util/codec/binary/Base64.java
+++ b/java/org/apache/tomcat/util/codec/binary/Base64.java
@@ -110,18 +110,30 @@ public class Base64 extends BaseNCodec {
* Thanks to "commons" project in ws.apache.org for this code.
* https://svn.apache.org/repos/asf/webservices/commons/trunk/modules/util/
*/
- private static final byte[] DECODE_TABLE = {
+ private static final byte[] STANDARD_DECODE_TABLE = {
// 0 1 2 3 4 5 6 7 8 9 A B C D E F
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 00-0f
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 10-1f
- -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, 62, -1, 63, // 20-2f + - /
+ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, -1, -1, 63, // 20-2f + /
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, -1, -1, -1, // 30-3f 0-9
-1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, // 40-4f A-O
- 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, 63, // 50-5f P-Z _
+ 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, -1, // 50-5f P-Z
-1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, // 60-6f a-o
41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51 // 70-7a p-z
};
+ private static final byte[] URL_SAFE_DECODE_TABLE = {
+ // 0 1 2 3 4 5 6 7 8 9 A B C D E F
+ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 00-0f
+ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 10-1f
+ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, -1, // 20-2f -
+ 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, -1, -1, -1, // 30-3f 0-9
+ -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, // 40-4f A-O
+ 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, 63, // 50-5f P-Z _
+ -1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, // 60-6f a-o
+ 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51 // 70-7a p-z
+ };
+
/**
* Base64 uses 6-bit fields.
*/
@@ -140,7 +152,7 @@ public class Base64 extends BaseNCodec {
private final byte[] encodeTable;
// Only one decode table currently; keep for consistency with Base32 code
- private final byte[] decodeTable = DECODE_TABLE;
+ private final byte[] decodeTable;
/**
* Line separator for encoding. Not used when decoding. Only used if lineLength > 0.
@@ -273,6 +285,8 @@ public class Base64 extends BaseNCodec {
super(BYTES_PER_UNENCODED_BLOCK, BYTES_PER_ENCODED_BLOCK,
lineLength,
lineSeparator == null ? 0 : lineSeparator.length);
+ // Needs to be set early to avoid NPE during call to containsAlphabetOrPad() below
+ this.decodeTable = urlSafe ? URL_SAFE_DECODE_TABLE : STANDARD_DECODE_TABLE;
// TODO could be simplified if there is no requirement to reject invalid line sep when length <=0
// @see test case Base64Test.testConstructors()
if (lineSeparator != null) {
@@ -441,8 +455,8 @@ public class Base64 extends BaseNCodec {
context.eof = true;
break;
}
- if (b >= 0 && b < DECODE_TABLE.length) {
- final int result = DECODE_TABLE[b];
+ if (b >= 0 && b < decodeTable.length) {
+ final int result = decodeTable[b];
if (result >= 0) {
context.modulus = (context.modulus+1) % BYTES_PER_ENCODED_BLOCK;
context.ibitWorkArea = (context.ibitWorkArea << BITS_PER_ENCODED_BYTE) + result;
@@ -495,7 +509,7 @@ public class Base64 extends BaseNCodec {
* @since 1.4
*/
public static boolean isBase64(final byte octet) {
- return octet == PAD_DEFAULT || (octet >= 0 && octet < DECODE_TABLE.length && DECODE_TABLE[octet] != -1);
+ return octet == PAD_DEFAULT || (octet >= 0 && octet < STANDARD_DECODE_TABLE.length && STANDARD_DECODE_TABLE[octet] != -1);
}
/**
@@ -678,6 +692,10 @@ public class Base64 extends BaseNCodec {
return new Base64().decode(base64String);
}
+ public static byte[] decodeBase64URLSafe(final String base64String) {
+ return new Base64(true).decode(base64String);
+ }
+
/**
* Decodes Base64 data into octets.
* <p>
diff --git a/test/org/apache/coyote/http2/Http2TestBase.java b/test/org/apache/coyote/http2/Http2TestBase.java
index a394927..dc0eabf 100644
--- a/test/org/apache/coyote/http2/Http2TestBase.java
+++ b/test/org/apache/coyote/http2/Http2TestBase.java
@@ -81,7 +81,7 @@ public abstract class Http2TestBase extends TomcatBaseTest {
static {
byte[] empty = new byte[0];
- EMPTY_HTTP2_SETTINGS_HEADER = "HTTP2-Settings: " + Base64.encodeBase64String(empty) + "\r\n";
+ EMPTY_HTTP2_SETTINGS_HEADER = "HTTP2-Settings: " + Base64.encodeBase64URLSafeString(empty) + "\r\n";
}
protected static final String TRAILER_HEADER_NAME = "x-trailertest";
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index 6427313..48f3408 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -45,6 +45,15 @@
issues do not "pop up" wrt. others).
-->
<section name="Tomcat 9.0.27 (markt)" rtext="in development">
+ <subsection name="Coyote">
+ <changelog>
+ <fix>
+ Use URL safe base 64 encoding rather than standard base 64 encoding when
+ generating or parsing the <code>HTTP2-Settings</code> header as part of
+ an HTTP upgrade to <code>h2c</code> as required by RFC 7540. (markt)
+ </fix>
+ </changelog>
+ </subsection>
</section>
<section name="Tomcat 9.0.26 (markt)" rtext="release in progress">
<subsection name="Other">
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org
[tomcat] 01/02: Revert "Only decode in standard mode."
Posted by ma...@apache.org.
This is an automated email from the ASF dual-hosted git repository.
markt pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tomcat.git
commit 117bbdab820d9be87bff80a773e77c738fb9502c
Author: Mark Thomas <ma...@apache.org>
AuthorDate: Tue Sep 17 20:23:35 2019 +0100
Revert "Only decode in standard mode."
This reverts commit 9fd972c931cf3ce8829a69437b7340f9b0e1e731.
The original commit broke parsing of HTTP upgrade to h2c
---
java/org/apache/tomcat/util/codec/binary/Base64.java | 15 ++++++++-------
1 file changed, 8 insertions(+), 7 deletions(-)
diff --git a/java/org/apache/tomcat/util/codec/binary/Base64.java b/java/org/apache/tomcat/util/codec/binary/Base64.java
index 059ff66..99a501c 100644
--- a/java/org/apache/tomcat/util/codec/binary/Base64.java
+++ b/java/org/apache/tomcat/util/codec/binary/Base64.java
@@ -35,7 +35,7 @@ import java.math.BigInteger;
* <li>Line separator: Default is CRLF ("\r\n")</li>
* </ul>
* <p>
- * The URL-safe parameter is only applied to encode operations. Decoding only handles standard mode.
+ * The URL-safe parameter is only applied to encode operations. Decoding seamlessly handles both modes.
* </p>
* <p>
* Since this class operates directly on byte streams, and not character streams, it is hard-coded to only
@@ -104,7 +104,8 @@ public class Base64 extends BaseNCodec {
* in Table 1 of RFC 2045) into their 6-bit positive integer equivalents. Characters that are not in the Base64
* alphabet but fall within the bounds of the array are translated to -1.
*
- * Note: The seamless decoding of URL safe values has been disabled because Tomcat doesn't use it.
+ * Note: '+' and '-' both decode to 62. '/' and '_' both decode to 63. This means decoder seamlessly handles both
+ * URL_SAFE and STANDARD base64. (The encoder, on the other hand, needs to know ahead of time what to emit).
*
* Thanks to "commons" project in ws.apache.org for this code.
* https://svn.apache.org/repos/asf/webservices/commons/trunk/modules/util/
@@ -113,10 +114,10 @@ public class Base64 extends BaseNCodec {
// 0 1 2 3 4 5 6 7 8 9 A B C D E F
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 00-0f
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 10-1f
- -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, -1, -1, 63, // 20-2f + /
+ -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, 62, -1, 63, // 20-2f + - /
52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, -1, -1, -1, // 30-3f 0-9
-1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, // 40-4f A-O
- 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, -1, // 50-5f P-Z
+ 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, 63, // 50-5f P-Z _
-1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, // 60-6f a-o
41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51 // 70-7a p-z
};
@@ -262,7 +263,7 @@ public class Base64 extends BaseNCodec {
* Each line of encoded data will end with this sequence of bytes.
* @param urlSafe
* Instead of emitting '+' and '/' we emit '-' and '_' respectively. urlSafe is only applied to encode
- * operations. Decoding only handles standard mode.
+ * operations. Decoding seamlessly handles both modes.
* <b>Note: no padding is added when using the URL-safe alphabet.</b>
* @throws IllegalArgumentException
* The provided lineSeparator included some base64 characters. That's not going to work!
@@ -665,7 +666,7 @@ public class Base64 extends BaseNCodec {
/**
* Decodes a Base64 String into octets.
* <p>
- * <b>Note:</b> this method only handles data encoded in standard mode.
+ * <b>Note:</b> this method seamlessly handles data encoded in URL-safe or normal mode.
* </p>
*
* @param base64String
@@ -680,7 +681,7 @@ public class Base64 extends BaseNCodec {
/**
* Decodes Base64 data into octets.
* <p>
- * <b>Note:</b> this method only handles data encoded in standard mode.
+ * <b>Note:</b> this method seamlessly handles data encoded in URL-safe or normal mode.
* </p>
*
* @param base64Data
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org