• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

aio-libs / multidict / 35971128892
87%

Build:
DEFAULT BRANCH: master
Ran 24 Sep 2026 07:44AM UTC
Jobs 1
Files 43
Run time 1min
Badge
Embed ▾
README BADGES
x

If you need to use a raster PNG badge, change the '.svg' to '.png' in the link

Markdown

Textile

RDoc

HTML

Rst

24 Sep 2026 07:43AM UTC coverage: 87.497%. Remained the same
35971128892

push

github

web-flow
Skip the retired-table drain when nothing is retired (#1546)

<!-- Thank you for your contribution! -->

## What do these changes do?

On the free-threaded build every lock-free reader that brings
`num_active_readers` back to zero calls `_md_drain_retired()`, which
without a second thread is every single lookup. The first thing that
function does is a sequentially consistent exchange on `md->retired`,
and that list is empty almost every time.

The drain now checks the list with a load first and the rest of it sits
behind a call, so a lookup with nothing to free pays one load instead of
an out-of-line call and a read-modify-write. The load stays sequentially
consistent: a writer that pushes and then reads `num_active_readers` as
nonzero leaves the table for whoever brings that count to zero, so the
reader doing so must not be able to miss the push, and only a seq_cst
load is ordered against the push in the single total order. On x86-64
that is the same plain `mov`, so it is free; the cost being skipped is
the exchange.

Instructions per operation, CPython 3.14.7 free-threaded:

| Operation | Before | After |
| --- | ---: | ---: |
| `key in md` | 283 | 253 (-10.6%) |
| `md[key]` | 317 | 292 (-7.9%) |
| `md.get(key)`, miss | 499 | 474 (-5.0%) |

`CIMultiDict` moves -8.1%, -6.2% and -3.3% on the same three. No other
benchmarked operation changes beyond the measurement's noise floor.
Wall clock improves more than the instruction counts do, because
Callgrind cannot see the removed `lock`-prefixed exchange. Measured back
to back against a build of the merge base, two passes each: `key in md`
35.5/35.3 ns before against 29.0/28.7 after, `md[key]` 37.1/36.9 against
30.9/30.6, so about -18%. `CIMultiDict` moves within the noise of this
machine on wall clock and I would not claim a figure for it.

This is free-threaded only. `atomic_helpers.h` is entirely inside
`#ifdef Py_GIL_DISABLED`, and `tools/codegen_diff.py` reports `0 of 190
functions differ` for the GIL... (continued)

767 of 1534 branches covered (50.0%)

Branch coverage included in aggregate %.

7386 of 7784 relevant lines covered (94.89%)

1.9 hits per line

Jobs
ID Job ID Ran Files Coverage
1 MyPy - 35971128892.1 24 Sep 2026 07:44AM UTC 86
87.5
GitHub Action Run
Source Files on build 35971128892
  • Tree
  • List 43
  • Changed 2
  • Source Changed 0
  • Coverage Changed 2
Coverage ∆ File Lines Relevant Covered Missed Hits/Line Branch Hits Branch Misses
  • Back to Repo
  • Github Actions Build #35971128892
  • a249b3c4 on github
  • Prev Build on master (#35966702630)
  • Next Build on master (#35971413209)
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE TRIAL · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc