diff --git a/common/raw_hashtable.h b/common/raw_hashtable.h index c025be4d45b0b..8adff07b5928e 100644 --- a/common/raw_hashtable.h +++ b/common/raw_hashtable.h @@ -442,7 +442,10 @@ class BaseImpl { : view_impl_(alloc_size, nullptr), growth_budget_(growth_budget), small_alloc_size_(small_alloc_size) {} - ~BaseImpl(); + + // Destruction must be handled by the table where it can destroy entries in + // any small buffer, so make the base destructor protected but defaulted here. + ~BaseImpl() = default; // NOLINTNEXTLINE(google-explicit-constructor): Designed to implicitly decay. operator ViewImplT() const { return view_impl(); } @@ -575,6 +578,7 @@ class TableImpl : public InputBaseT { TableImpl(TableImpl&& arg) noexcept; auto operator=(const TableImpl& arg) -> TableImpl&; auto operator=(TableImpl&& arg) noexcept -> TableImpl&; + ~TableImpl(); // Resets the hashtable to its initial state, clearing all entries and // releasing all memory. If the hashtable had an SSO buffer, that is restored @@ -841,11 +845,6 @@ auto ViewImpl::ComputeMetricsImpl( return metrics; } -template -BaseImpl::~BaseImpl() { - Destroy(); -} - // TODO: Evaluate whether it is worth forcing this out-of-line given the // reasonable ABI boundary it forms and large volume of code necessary to // implement it. @@ -1596,6 +1595,11 @@ auto TableImpl::operator=(TableImpl&& arg) noexcept return *this; } +template +TableImpl::~TableImpl() { + this->Destroy(); +} + // Reset a table to its original state, including releasing any allocated // memory. template