Harden against aba problem

This commit is contained in:
Justine Tunney 2024-08-26 19:59:25 -07:00
parent 610c951f71
commit 884d89235f
No known key found for this signature in database
GPG key ID: BE714B4575D6E328
8 changed files with 212 additions and 85 deletions

View file

@ -50,6 +50,13 @@
#define PGUP(x) (((x) + pagesz - 1) & -pagesz)
#define MASQUE 0x00fffffffffffff8
#define PTR(x) ((uintptr_t)(x) & MASQUE)
#define TAG(x) ROL((uintptr_t)(x) & ~MASQUE, 8)
#define ABA(p, t) ((uintptr_t)(p) | (ROR((uintptr_t)(t), 8) & ~MASQUE))
#define ROL(x, n) (((x) << (n)) | ((x) >> (64 - (n))))
#define ROR(x, n) (((x) >> (n)) | ((x) << (64 - (n))))
#if !MMDEBUG
#define ASSERT(x) (void)0
#else
@ -227,14 +234,17 @@ StartOver:
}
void __maps_free(struct Map *map) {
uintptr_t tip;
ASSERT(!TAG(map));
map->size = 0;
map->addr = MAP_FAILED;
map->freed = atomic_load_explicit(&__maps.freed, memory_order_relaxed);
for (;;) {
if (atomic_compare_exchange_weak_explicit(&__maps.freed, &map->freed, map,
memory_order_release,
memory_order_relaxed))
for (tip = atomic_load_explicit(&__maps.freed, memory_order_relaxed);;) {
map->freed = (struct Map *)PTR(tip);
if (atomic_compare_exchange_weak_explicit(
&__maps.freed, &tip, ABA(map, TAG(tip) + 1), memory_order_release,
memory_order_relaxed))
break;
pthread_pause_np();
}
}
@ -297,12 +307,13 @@ void __maps_insert(struct Map *map) {
struct Map *__maps_alloc(void) {
struct Map *map;
map = atomic_load_explicit(&__maps.freed, memory_order_relaxed);
while (map) {
if (atomic_compare_exchange_weak_explicit(&__maps.freed, &map, map->freed,
memory_order_acquire,
memory_order_relaxed))
uintptr_t tip = atomic_load_explicit(&__maps.freed, memory_order_relaxed);
while ((map = (struct Map *)PTR(tip))) {
if (atomic_compare_exchange_weak_explicit(
&__maps.freed, &tip, ABA(map->freed, TAG(tip) + 1),
memory_order_acquire, memory_order_relaxed))
return map;
pthread_pause_np();
}
int gransz = __gransize;
struct DirectMap sys = sys_mmap(0, gransz, PROT_READ | PROT_WRITE,