Repository navigation
Conversation
There was a problem hiding this comment.
Warning
Copilot couldn't run its full agentic review because it didn't start before the timeout. Make sure your repository has a runner available, or add a copilot-code-review.yml file specifying one with the runs-on attribute. See the docs for more details.
Copilot review overview
4 open findings
This test intends to exerciseHeaderMapgrowth/rehash, but inserting 128 headers may not reliably… · New Since the regression includesClear()leaving_first_set_cookiestale, this test should assert… · New Theold_bucket_count+bucket_count()comparison + refresh pattern is duplicated (also in… · New Indentation inside the loop is inconsistent with surrounding lines in this block. Aligning… · New
What changed in this PR
Fixes a stale cached pointer for the first Set-Cookie header in HttpHeader after HeaderMap mutations (rehash/growth), Swap(), and Clear(), and adds regression tests for these cases.
Changes:
- Refresh
_first_set_cookieafterHeaderMapgrowth and afterHttpHeader::Swap() - Clear
_first_set_cookieinHttpHeader::Clear() - Add unit tests covering map growth,
Swap(), andClear()
🧠 Review effort: Lite
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
|
The CI failure is unrelated to this PR. It was fixed in #3610. |
bfe433d to
70608b9
Compare
There was a problem hiding this comment.
Warning
Copilot couldn't run its full agentic review because it didn't start before the timeout. Make sure your repository has a runner available, or add a copilot-code-review.yml file specifying one with the runs-on attribute. See the docs for more details.
Copilot review overview
4 open findings
HttpMessagecallsHttpHeader::HasSetCookieHeaders()andHttpHeader::SyncSetCookieHeaders().… · NewAddHeader()now unconditionally appends into_set_cookie_headersand syncsSET_COOKIE,… · New This test forces aHeaderMapgrowth by inserting up to 4096 headers and asserting… · New The counting variables are handled inconsistently here:set_cookie_value1_countis declared… · New
4 resolved since last review
Since the regression includesClear()leaving_first_set_cookiestale, this test should assert… This test intends to exerciseHeaderMapgrowth/rehash, but inserting 128 headers may not reliably… Indentation inside the loop is inconsistent with surrounding lines in this block. Aligning… Theold_bucket_count+bucket_count()comparison + refresh pattern is duplicated (also in…
🧠 Review effort: Lite
f9c55d5 to
b6001dc
Compare
There was a problem hiding this comment.
🟡 Changes recommended
Rebuilding all cookie entries after each append can cause quadratic work for multi-cookie responses.
1 open issue
4 resolved since last review
AddHeader()now unconditionally appends into_set_cookie_headersand syncsSET_COOKIE,…HttpMessagecallsHttpHeader::HasSetCookieHeaders()andHttpHeader::SyncSetCookieHeaders().… This test forces aHeaderMapgrowth by inserting up to 4096 headers and asserting… The counting variables are handled inconsistently here:set_cookie_value1_countis declared…
Review effort: Lite
|
LGTM |
There was a problem hiding this comment.
AppendHeader() now inserts incrementally, but SetHeader() still forces a full synchronization. With the default 16-bucket map, the following sequence reaches the unsafe deletion path:
brpc::HttpHeader h;
h.SetHeader("Set-Cookie", "sid=" + std::string(128, 'x'));
h.SetHeader("User-Agent", "client");
h.SetHeader("Set-Cookie", "sid=new");Set-Cookie and User-Agent collide. During the final update, _headers.erase(SET_COOKIE) removes the Cookie bucket head while retaining the User-Agent node.
MultiFlatMap::erase() destroys the head’s strings at flat_map_inl.h:473, then assigns the surviving node into those destroyed objects at lines 501–503 without reconstructing the element. With a heap-backed Cookie value, this can cause a double-free or heap corruption.




What problem does this PR solve?
Issue Number: resolve
Problem Summary:
HttpHeadercaches the firstSet-Cookievalue as a pointer into itsHeaderMap. The pointer becomes stale when the map grows.Refreshing it with
HeaderMap::seek()is not sufficient:HeaderMapis amulti-map and does not preserve the identity or insertion order of duplicate
Set-Cookiefields. The refreshed pointer may therefore select a differentcookie.
What is changed and the side effects?
Changed:
Store
Set-Cookiefields separately in insertion order and keepHeaderMapsynchronized for header iteration and serialization.
Make
GetHeader(SET_COOKIE)andGetAllSetCookieHeader()read the stableordered storage. This also makes
Swap()andClear()safe without retaininga stale cached pointer.
Add regression coverage for actual map growth, multiple
Set-Cookiefields,fragmented HTTP parsing,
Swap(), copy construction, and assignment.Side effects:
Performance effects:
The change only adds separate storage and synchronization for
Set-Cookiefields. Ordinary headers keep the existing path.
Breaking backward compatibility:
None.