Skip to content

Commit dcbc141

Browse files
committed
add atomic global counter system
1 parent 637ffa9 commit dcbc141

3 files changed

Lines changed: 37 additions & 1 deletion

File tree

multidict/_multilib/state.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
extern "C" {
66
#endif
77

8+
#include <stdatomic.h>
9+
810
/* State of the _multidict module */
911
typedef struct {
1012
PyTypeObject *IStrType;
@@ -128,7 +130,7 @@ get_mod_state_by_def(PyObject *self)
128130
static inline uint64_t
129131
NEXT_VERSION(mod_state *state)
130132
{
131-
return ++state->global_version;
133+
return atomic_fetch_add_explicit((_Atomic(uint64_t)*)&state->global_version, 1, memory_order_relaxed);
132134
}
133135

134136
#ifdef __cplusplus
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
import threading
2+
import multidict
3+
from multidict import MultiDict
4+
import sysconfig
5+
6+
FREETHREADED = bool(sysconfig.get_config_var("Py_GIL_DISABLED"))
7+
if not FREETHREADED:
8+
raise SystemExit(0)
9+
10+
md = MultiDict()
11+
N, M = 3, 100
12+
baseline = multidict.getversion(md)
13+
14+
15+
def worker(tid):
16+
for i in range(M):
17+
md[f"k{tid}_{i}"] = i
18+
19+
20+
if __name__ == "__main__":
21+
threads = [threading.Thread(target=worker, args=(tid,)) for tid in range(N)]
22+
for t in threads:
23+
t.start()
24+
for t in threads:
25+
t.join()
26+
27+
observed = multidict.getversion(md) - baseline
28+
expected = N * M
29+
assert expected == observed, (
30+
f"expected delta: {expected}"
31+
f" observed: {observed} "
32+
f"lost: {expected - observed}"
33+
)

tests/test_leaks.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
"multidict_type_leak.py",
1919
"multidict_type_leak_items_values.py",
2020
"multidict_pop.py",
21+
"multidict_global_counter.py",
2122
),
2223
)
2324
@pytest.mark.leaks

0 commit comments

Comments
 (0)