[
https://issues.apache.org/jira/browse/HTTPCORE-568?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16772788#comment-16772788
]
ASF subversion and git services commented on HTTPCORE-568:
----------------------------------------------------------
Commit b75845c7ec4f8d51cda0a0de55e86c329e387846 in httpcomponents-core's branch
refs/heads/master from Richard Hernandez
[ https://gitbox.apache.org/repos/asf?p=httpcomponents-core.git;h=b75845c ]
HTTPCORE-568: Signal capacity in ReactiveDataConsumer whenever possible
This fixes a race condition in ReactiveDataConsumer that would cause the
input window to never be updated over HTTP/1.x connections. The bug
occurs when consume is the first method to call flushToSubscriber,
enough data has been received to exhaust the initial input window in the
stream duplexer, and there are still downstream requests for data that
haven't been served.
ReactiveDataConsumer attempts to flush data downstream whenever it gets
a chance, and only one thread is allowed to flush. After flushing, it
signals the number of bytes flushed to its capacity channel.
If the flush occurs because AbstractHttp1StreamDuplexer is calling
consume, it guarantees the capacity channel won't be set until consume
(and the flush) returns. When there are still outstanding requests
(meaning the subscriber is unlikely to call request again), the flush
from consume will be the last attempt to signal capacity. The channel
isn't set yet, so nothing happens. As a result,
AbstractHttp1StreamDuplexer's input window remains empty,
ReactiveDataConsumer receives no further interactions, and the response
stops being read.
We can fix this by signaling capacity from both flushToSubscriber and
updateCapacity.
> ReactiveDataConsumer receives at most 65k bytes over HTTP/1.1
> -------------------------------------------------------------
>
> Key: HTTPCORE-568
> URL: https://issues.apache.org/jira/browse/HTTPCORE-568
> Project: HttpComponents HttpCore
> Issue Type: Bug
> Components: HttpCore
> Affects Versions: 5.0-beta6
> Reporter: Richard Hernandez
> Priority: Major
> Time Spent: 0.5h
> Remaining Estimate: 0h
>
> [The addition of an input window to
> AbstractHttp1StreamDuplexer|https://github.com/apache/httpcomponents-core/commit/3252c39fd803f86c6856caa83b683d31e45b8391#diff-4ceed36abd5cb9433de24f108c90195aR292]
> causes ReactiveDataConsumer to only receive as many bytes as the input
> window's initial size. By default, this is only 65,536 bytes.
> The problem is that updateCapacity is only called after the window is
> exhausted. This happens after consume returns, which is where
> RectiveDataConsumer tries to signal available capacity to its
> capacityChannel. As a result, it's never able to signal more capacity to
> AbstractHttp1StreamDuplexer, and all future bytes on this channel get stuck
> in the system's socket receive buffer.
> As far as I can tell, the capacity channel was never set in prior releases.
> It just happened to work because my tests never exhausted the buffer space in
> ReactiveDataConsumer.
--
This message was sent by Atlassian JIRA
(v7.6.3#76005)
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]