lib: Add epoch-based SMR

This commit is contained in:
2026-11-01 21:06:48 +01:00
parent 3ff068e944
commit 7c04530681
24 changed files with 1059 additions and 84 deletions
+25
View File
@@ -1,6 +1,7 @@
// SPDX-License-Identifier: ISC
#include <zinnia/alloc.h>
#include <zinnia/epoch.h>
#include <zinnia/errno.h>
#include <zinnia/print.h>
#include <zinnia/utils.h>
@@ -143,10 +144,34 @@ static errno_t fill(struct vmo* vmo, uint64_t index, enum vmo_access access, str
return 0;
}
static struct page* lookup_fast(struct vmo* vmo, uint64_t index) {
epoch_enter();
struct page* page = radix_lookup(&vmo->pages, index);
if (page && !page_try_hold(page))
page = nullptr;
const bool valid =
page && radix_lookup(&vmo->pages, index) == page && !(atomic_load(&page->flags, ATOMIC_ACQUIRE) & PAGE_BUSY);
epoch_exit();
if (page && !valid) {
page_unhold(page);
return nullptr;
}
return page;
}
errno_t vmo_get_page(struct vmo* vmo, uint64_t index, enum vmo_access access, struct page** out) {
if (vmo->pager->lookup)
return ENOTSUP;
if (access == VMO_READ) {
struct page* page = lookup_fast(vmo, index);
if (page) {
*out = page;
return 0;
}
}
mutex_lock(&vmo->lock);
while (true) {
struct page* page = radix_lookup(&vmo->pages, index);