Commit a1f46ff4 authored by jan.koester's avatar jan.koester
Browse files

media: discard pooled stream connection after error/empty-body drain



readBodyChunkNonBlocking() returning 0 means EAGAIN, not "stream
finished" -- only (size_t)-1 does. The upstream-error and empty-body
drain loops treated 0 as done and let the pooled HttpClient fall back
into _mdbStreamPool possibly mid-stream, corrupting it for the next
request that reuses it. That request then hangs waiting on frames
that never arrive, permanently parking one of blogi's fixed epoll
worker threads -- enough stuck video/media requests exhausts the pool
and wedges the entire site.

Co-Authored-By: default avatarClaude Sonnet 5 <noreply@anthropic.com>
parent 9978fa0e
Loading
Loading
Loading
Loading
+10 −0
Original line number Diff line number Diff line
@@ -1050,6 +1050,12 @@ namespace blogi {
                    size_t dn;
                    while ((dn = streamClient->readBodyChunkNonBlocking(drain, sizeof(drain))) != 0
                           && dn != static_cast<size_t>(-1)) {}
                    // A single EAGAIN (dn==0) doesn't mean the body finished
                    // draining -- only (size_t)-1 does. Never let a possibly
                    // still-mid-stream connection back into the pool for
                    // reuse; a future request handed this instance would
                    // desync against leftover frames still in flight.
                    streamClient.discard();
                    libhttppp::HttpResponse curres;
                    if (dataStatus == 404)
                        curres.setState(HTTP404);
@@ -1100,6 +1106,10 @@ namespace blogi {
                    size_t n;
                    while ((n = streamClient->readBodyChunkNonBlocking(drain, sizeof(drain))) != 0
                           && n != static_cast<size_t>(-1)) {}
                    // See the same discard() note in the upstream-error
                    // branch above -- dn==0 here doesn't prove the stream
                    // actually finished draining either.
                    streamClient.discard();
                    libhttppp::HttpResponse curres;
                    curres.setState(HTTP404);
                    curres.send(req,"",0);