Check insertion takes place before upsize check
This commit is contained in:
29
RootSet.cpp
29
RootSet.cpp
@@ -70,8 +70,14 @@ struct RootSet::Impl {
|
||||
void add(uint32_t node, int64_t version) {
|
||||
ThreadSafeHandle::Impl *h = handle.load(std::memory_order_relaxed);
|
||||
|
||||
auto end = h->end.load(std::memory_order_relaxed);
|
||||
|
||||
if (h->roots()[end - 1] == node) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Upsize if necessary
|
||||
if (h->end.load(std::memory_order_relaxed) == h->capacity) {
|
||||
if (end == h->capacity) {
|
||||
h->next = nullptr;
|
||||
auto begin = h->lastLeq(oldestVersion);
|
||||
if (lastToFree != nullptr) {
|
||||
@@ -81,23 +87,20 @@ struct RootSet::Impl {
|
||||
firstToFree = h;
|
||||
lastToFree = h;
|
||||
}
|
||||
auto *newH = ThreadSafeHandle::Impl::create((h->capacity - begin) * 2);
|
||||
memcpy(newH->roots(), h->roots() + begin,
|
||||
sizeof(h->roots()[0]) * (h->capacity - begin));
|
||||
auto newEnd = h->capacity - begin;
|
||||
auto *newH = ThreadSafeHandle::Impl::create(newEnd * 2);
|
||||
memcpy(newH->roots(), h->roots() + begin, sizeof(h->roots()[0]) * newEnd);
|
||||
memcpy(newH->versions(), h->versions() + begin,
|
||||
sizeof(h->versions()[0]) * (h->capacity - begin));
|
||||
newH->end.store(h->capacity - begin, std::memory_order_relaxed);
|
||||
sizeof(h->versions()[0]) * newEnd);
|
||||
newH->end.store(newEnd, std::memory_order_relaxed);
|
||||
handle.store(newH, std::memory_order_release);
|
||||
h = newH;
|
||||
end = newEnd;
|
||||
}
|
||||
|
||||
auto end = h->end.load(std::memory_order_relaxed);
|
||||
|
||||
if (h->roots()[end - 1] != node) {
|
||||
h->roots()[end] = node;
|
||||
h->versions()[end] = version;
|
||||
h->end.store(end + 1, std::memory_order_release);
|
||||
}
|
||||
h->roots()[end] = node;
|
||||
h->versions()[end] = version;
|
||||
h->end.store(end + 1, std::memory_order_release);
|
||||
}
|
||||
|
||||
void setOldestVersion(int64_t oldestVersion) {
|
||||
|
Reference in New Issue
Block a user