Hacker News new | ask | show | jobs
by teacup50 3587 days ago
> This turned out to be caused by HTTP/2.0 which only allows 1 billion streams over a single connection.

Hilarious. People called this issue out as an obvious flaw when HTTP/2.0 was first proposed, got ignored, and here the issue is.

For those unfamiliar:

HTTP/2.0 uses an unsigned 31-bit integer to identity individual streams over a connection.

Server-initiated streams must use even identifiers.

Client-initiated streams must use odd identifiers.

Identifiers are not reclaimed once a stream is closed. Once you've initiated (2^31)/2 streams, you've exhausted the identifier pool and there's nothing you can do other than close the connection.

For comparison, SSH channels use a 32-bit arbitrary channel identifier, specified by the initiating party, creating an identifier tuple of (peer, channel). Channel identifiers can be re-used after an existing channel with that identifier is closed.

As a result, SSH doesn't have this problem, or the need to divide the identifier space into even/odd (server/client) channel space.

4 comments

It was not ignored, it was very much made on purpose because of a certain popular programming language not having unsigned 32 bit variables...
Well, that's half of the downside presented, the other half is that it's split be server/client connections. I assume this was done because it simplifies the tracking of the next stream identifier, because you can just keep a counter and increment, rather than a table of used streams to check a new random identifier against?
Correct, something that was used already in SPDY and proved to be very handy and convenient so it was kept in HTTP/2.
BTW, recent data shows that Firefox does (on median) about 8 requests per HTTP/2 connection, up from slightly more than 1 on HTTP/1.1

So, if we ever close a connection from having reached a billion streams we are in a very very good position.

Doubling the number of them doesn't make it more right.
Are you talking about Java?
So, that's the other side of the argument? I assume there was at least a reason they specced it this way originally, even if under comparison those reasons wouldn't have held up. Was there any justification, or was it literally ignored?
It was considered a non-issue, since it's easy to work around. See https://github.com/http2/http2-spec/issues/61

Since HTTP2 is a client->server protocol, the server can close whenever and the client can just open another one.

May be I'm stupid, but how hard it is it to reimplement it as 64 bit unsigned ?
It would likely require a new version on the protocol level.
Support for Javascript? (53-bit mantissa limit)
Is the lack of reuse something to do with its evolution from QUIC as a loosely ordered UDP-based protocol?