From 3d94f275a2e5bdcaf824817b526cf65e0d714237 Mon Sep 17 00:00:00 2001 From: Stiopa Koltsov Date: Fri, 6 Jan 2023 05:58:01 +0000 Subject: [PATCH] Fix RawTable::allocation_info for empty table Fixes #376 --- src/raw/mod.rs | 12 +++++++++++- tests/raw.rs | 11 +++++++++++ 2 files changed, 22 insertions(+), 1 deletion(-) create mode 100644 tests/raw.rs diff --git a/src/raw/mod.rs b/src/raw/mod.rs index 63f97cffb8..aeef4fff43 100644 --- a/src/raw/mod.rs +++ b/src/raw/mod.rs @@ -531,7 +531,12 @@ impl RawTable { #[inline] #[cfg(feature = "raw")] pub fn allocation_info(&self) -> (NonNull, Layout) { - self.table.allocation_info(Self::TABLE_LAYOUT) + if self.table.is_empty_singleton() { + // `self.table.allocation_info` can only be called when the table is not empty. + return (NonNull::dangling(), Layout::new::<()>()); + } else { + self.table.allocation_info(Self::TABLE_LAYOUT) + } } /// Returns the index of a bucket from a `Bucket`. @@ -1589,6 +1594,11 @@ impl RawTableInner { #[inline] fn allocation_info(&self, table_layout: TableLayout) -> (NonNull, Layout) { + debug_assert!( + !self.is_empty_singleton(), + "this function can only be called on non-empty tables" + ); + // Avoid `Option::unwrap_or_else` because it bloats LLVM IR. let (layout, ctrl_offset) = match table_layout.calculate_layout_for(self.buckets()) { Some(lco) => lco, diff --git a/tests/raw.rs b/tests/raw.rs new file mode 100644 index 0000000000..858836e63b --- /dev/null +++ b/tests/raw.rs @@ -0,0 +1,11 @@ +#![cfg(feature = "raw")] + +use hashbrown::raw::RawTable; +use std::mem; + +#[test] +fn test_allocation_info() { + assert_eq!(RawTable::<()>::new().allocation_info().1.size(), 0); + assert_eq!(RawTable::::new().allocation_info().1.size(), 0); + assert!(RawTable::::with_capacity(1).allocation_info().1.size() > mem::size_of::()); +}