diff options
author | Tor Egge <Tor.Egge@online.no> | 2022-04-28 12:17:24 +0200 |
---|---|---|
committer | Tor Egge <Tor.Egge@online.no> | 2022-04-28 12:17:24 +0200 |
commit | 60c7873fbfda349cd731098223168a67d122ea9c (patch) | |
tree | 4e6545d725fd912eae47053339060e0730d3becf /searchcore | |
parent | 5e28bd110a7dd893d9aea61f47923c64b49055a2 (diff) |
Use atomic for _lowest and _highest in proton::LidStateVector.
Diffstat (limited to 'searchcore')
-rw-r--r-- | searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.cpp | 59 | ||||
-rw-r--r-- | searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.h | 26 |
2 files changed, 40 insertions, 45 deletions
diff --git a/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.cpp b/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.cpp index 7309f7a518c..27b9cfdd197 100644 --- a/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.cpp +++ b/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.cpp @@ -23,9 +23,11 @@ LidStateVector::~LidStateVector() = default; void LidStateVector::resizeVector(uint32_t newSize, uint32_t newCapacity) { - assert(!_trackLowest || _lowest <= _bv.size()); - assert(!_trackHighest || _bv.size() == 0 || _highest < _bv.size()); - bool nolowest(_lowest == _bv.size()); + uint32_t lowest = getLowest(); + uint32_t highest = getHighest(); + assert(!_trackLowest || lowest <= _bv.size()); + assert(!_trackHighest || _bv.size() == 0 || highest < _bv.size()); + bool nolowest(lowest == _bv.size()); if (_bv.size() > newSize) { _bv.shrink(newSize); } @@ -36,55 +38,44 @@ LidStateVector::resizeVector(uint32_t newSize, uint32_t newCapacity) _bv.extend(newSize); } if (_trackLowest) { - if (nolowest) { - _lowest = _bv.size(); - } - if (_lowest > _bv.size()) { - _lowest = _bv.size(); + if (nolowest || lowest > _bv.size()) { + lowest = _bv.size(); + _lowest.store(lowest, std::memory_order_relaxed); } } if (_trackHighest) { - if (_highest >= _bv.size()) { - _highest = _bv.size() > 0 ? _bv.getPrevTrueBit(_bv.size() - 1) : 0; + if (highest >= _bv.size()) { + highest = _bv.size() > 0 ? _bv.getPrevTrueBit(_bv.size() - 1) : 0; + _highest.store(highest, std::memory_order_relaxed); } } - maybeUpdateLowest(); - maybeUpdateHighest(); } void -LidStateVector::updateLowest() +LidStateVector::updateLowest(uint32_t lowest) { - if (_lowest >= _bv.size()) - return; - if (_bv.testBit(_lowest)) - return; - uint32_t lowest = _bv.getNextTrueBit(_lowest); + lowest = _bv.getNextTrueBit(lowest); assert(lowest <= _bv.size()); - _lowest = lowest; + _lowest.store(lowest, std::memory_order_relaxed); } void -LidStateVector::updateHighest() +LidStateVector::updateHighest(uint32_t highest) { - if (_highest == 0) - return; - if (_bv.testBit(_highest)) - return; - uint32_t highest = _bv.getPrevTrueBit(_highest); + highest = _bv.getPrevTrueBit(highest); assert(_bv.size() == 0 || highest < _bv.size()); - _highest = highest; + _highest.store(highest, std::memory_order_relaxed); } void LidStateVector::setBit(unsigned int idx) { assert(idx < _bv.size()); - if (_trackLowest && idx < _lowest) { - _lowest = idx; + if (_trackLowest && idx < getLowest()) { + _lowest.store(idx, std::memory_order_relaxed); } - if (_trackHighest && idx > _highest) { - _highest = idx; + if (_trackHighest && idx > getHighest()) { + _highest.store(idx, std::memory_order_relaxed); } assert(!_bv.testBit(idx)); _bv.setBitAndMaintainCount(idx); @@ -111,11 +102,11 @@ LidStateVector::assert_is_not_set_then_set_bits_helper(const std::vector<uint32_ } } if (do_set) { - if (_trackLowest && low < _lowest) { - _lowest = low; + if (_trackLowest && low < getLowest()) { + _lowest.store(low, std::memory_order_relaxed); } - if (_trackHighest && high > _highest) { - _highest = high; + if (_trackHighest && high > getHighest()) { + _highest.store(high, std::memory_order_relaxed); } } return high; diff --git a/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.h b/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.h index c0db4e99fa5..592ca23e63c 100644 --- a/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.h +++ b/searchcore/src/vespa/searchcore/proton/documentmetastore/lidstatevector.h @@ -3,27 +3,31 @@ #pragma once #include <vespa/searchlib/common/growablebitvector.h> +#include <atomic> namespace proton { class LidStateVector { search::GrowableBitVector _bv; - uint32_t _lowest; - uint32_t _highest; + std::atomic<uint32_t> _lowest; + std::atomic<uint32_t> _highest; bool _trackLowest; bool _trackHighest; - void updateLowest(); - void updateHighest(); + void updateLowest(uint32_t lowest); + void updateHighest(uint32_t highest); void maybeUpdateLowest() { - if (_trackLowest && _lowest < _bv.size() && !_bv.testBit(_lowest)) - updateLowest(); + uint32_t lowest = getLowest(); + if (_trackLowest && lowest < _bv.size() && !_bv.testBit(lowest)) { + updateLowest(lowest); + } } - void maybeUpdateHighest() { - if (_trackHighest && _highest != 0 && !_bv.testBit(_highest)) - updateHighest(); + uint32_t highest = getHighest(); + if (_trackHighest && highest != 0 && !_bv.testBit(highest)) { + updateHighest(highest); + } } template <bool do_set> uint32_t assert_is_not_set_then_set_bits_helper(const std::vector<uint32_t>& idxs); @@ -51,8 +55,8 @@ public: return _bv.extraByteSize() + sizeof(LidStateVector); } bool empty() const { return count() == 0u; } - unsigned int getLowest() const { return _lowest; } - unsigned int getHighest() const { return _highest; } + unsigned int getLowest() const { return _lowest.load(std::memory_order_relaxed); } + unsigned int getHighest() const { return _highest.load(std::memory_order_relaxed); } /** * Get cached number of bits set in vector. Called by read or |