This is an automated email from the ASF dual-hosted git repository. remm pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/tomcat.git
The following commit(s) were added to refs/heads/master by this push: new a19e8fe Tolerate concurrency a19e8fe is described below commit a19e8fed4ab2935a0b3d7c37cc9330da8f9fa759 Author: remm <r...@apache.org> AuthorDate: Mon Apr 29 17:14:54 2019 +0200 Tolerate concurrency The read call may return not_done by checking a semaphore, which allows safe concurrent use of the API. However, if the buffers of a pending read are concurrently cleared, then this may cause an underflow error and this is discarding one of the API benefits. This seems to be a very rare scenario. Adding some checks and sync would be expensive so this might not be a win. Will have to verify performance however ... --- java/org/apache/coyote/http2/Http2AsyncParser.java | 8 ++------ webapps/docs/changelog.xml | 4 ++++ 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/java/org/apache/coyote/http2/Http2AsyncParser.java b/java/org/apache/coyote/http2/Http2AsyncParser.java index 2c764f8..5438b40 100644 --- a/java/org/apache/coyote/http2/Http2AsyncParser.java +++ b/java/org/apache/coyote/http2/Http2AsyncParser.java @@ -33,16 +33,12 @@ class Http2AsyncParser extends Http2Parser { private final SocketWrapperBase<?> socketWrapper; private final Http2AsyncUpgradeHandler upgradeHandler; private Throwable error = null; - private final ByteBuffer header; - private final ByteBuffer framePaylod; Http2AsyncParser(String connectionId, Input input, Output output, SocketWrapperBase<?> socketWrapper, Http2AsyncUpgradeHandler upgradeHandler) { super(connectionId, input, output); this.socketWrapper = socketWrapper; socketWrapper.getSocketBufferHandler().expand(input.getMaxFrameSize()); this.upgradeHandler = upgradeHandler; - header = ByteBuffer.allocate(9); - framePaylod = ByteBuffer.allocate(input.getMaxFrameSize()); } @@ -54,8 +50,8 @@ class Http2AsyncParser extends Http2Parser { return super.readFrame(block, expected); } handleAsyncException(); - header.clear(); - framePaylod.clear(); + ByteBuffer header = ByteBuffer.allocate(9); + ByteBuffer framePaylod = ByteBuffer.allocate(input.getMaxFrameSize()); FrameCompletionHandler handler = new FrameCompletionHandler(expected, header, framePaylod); CompletionState state = socketWrapper.read(BlockingMode.NON_BLOCK, socketWrapper.getReadTimeout(), TimeUnit.MILLISECONDS, null, handler, handler, header, framePaylod); diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml index 0ddcac8..9522873 100644 --- a/webapps/docs/changelog.xml +++ b/webapps/docs/changelog.xml @@ -138,6 +138,10 @@ Associate BlockPoller thread name with its NIO connector for better readability. (remm) </fix> + <fix> + The async HTTP/2 frame parser should tolerate concurrency so clearing + shared buffers before attempting a read is not possible. (remm) + </fix> </changelog> </subsection> <subsection name="Other"> --------------------------------------------------------------------- To unsubscribe, e-mail: dev-unsubscr...@tomcat.apache.org For additional commands, e-mail: dev-h...@tomcat.apache.org