This is an automated email from the ASF dual-hosted git repository.
markt-asf pushed a commit to branch 11.0.x
in repository https://gitbox.apache.org/repos/asf/tomcat.git
The following commit(s) were added to refs/heads/11.0.x by this push:
new b74fa31d0b Improve frame validation - make sure more serious errors
take priority
b74fa31d0b is described below
commit b74fa31d0b8da208aec3abf37f6424df2a607ad1
Author: Mark Thomas <[email protected]>
AuthorDate: Mon Oct 26 23:13:57 2026 +0000
Improve frame validation - make sure more serious errors take priority
---
java/org/apache/coyote/http2/Http2AsyncParser.java | 8 ++++++++
java/org/apache/coyote/http2/Http2Parser.java | 15 +++++++++++----
webapps/docs/changelog.xml | 4 ++++
3 files changed, 23 insertions(+), 4 deletions(-)
diff --git a/java/org/apache/coyote/http2/Http2AsyncParser.java
b/java/org/apache/coyote/http2/Http2AsyncParser.java
index f5ec35a8ad..13113b4f2e 100644
--- a/java/org/apache/coyote/http2/Http2AsyncParser.java
+++ b/java/org/apache/coyote/http2/Http2AsyncParser.java
@@ -232,6 +232,14 @@ class Http2AsyncParser extends Http2Parser {
}
if (payload.position() < payloadSize) {
+ /*
+ * If the payload is larger than the buffer provided to read
it, the read can never complete. Once all
+ * of the buffers are full, further reads return zero bytes
which, if continued, results in an endless
+ * read loop. validateFrame() above should already have
rejected such a frame.
+ */
+ if (payloadSize > payload.capacity()) {
+ return CompletionHandlerCall.DONE;
+ }
return CompletionHandlerCall.CONTINUE;
}
diff --git a/java/org/apache/coyote/http2/Http2Parser.java
b/java/org/apache/coyote/http2/Http2Parser.java
index 2b07e2d4e3..ba4cbd7239 100644
--- a/java/org/apache/coyote/http2/Http2Parser.java
+++ b/java/org/apache/coyote/http2/Http2Parser.java
@@ -721,10 +721,11 @@ class Http2Parser {
Integer.toString(flags), Integer.toString(payloadSize)));
}
- if (expected != null && frameType != expected) {
- throw new
StreamException(sm.getString("http2Parser.processFrame.unexpectedType",
expected, frameType),
- Http2Error.PROTOCOL_ERROR, streamId);
- }
+ /*
+ * Frames with multiple errors may trigger multiple failures. Check
the things that can trigger the more serious
+ * ConnectionException first so such errors are not masked by a less
serious error that triggers a
+ * StreamException.
+ */
int maxFrameSize = input.getMaxFrameSize();
if (payloadSize > maxFrameSize) {
@@ -747,7 +748,13 @@ class Http2Parser {
}
}
+ // May throw StreamException or ConnectionException
frameType.check(streamId, payloadSize);
+
+ if (expected != null && frameType != expected) {
+ throw new
StreamException(sm.getString("http2Parser.processFrame.unexpectedType",
expected, frameType),
+ Http2Error.PROTOCOL_ERROR, streamId);
+ }
}
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml
index 3e73208a9c..eda24df27b 100644
--- a/webapps/docs/changelog.xml
+++ b/webapps/docs/changelog.xml
@@ -553,6 +553,10 @@
suffixed certificate is used instead.
(dsoumis)
</update>
+ <fix>
+ When validating HTTP/2 frames, make sure more serious errors take
+ priority over less serious errors. (markt)
+ </fix>
</changelog>
</subsection>
<subsection name="Jasper">
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]