Skip to content

Commit cbe3b6f

Browse files
Enforce T: Hash for Interned<...>
This adds panicking Hash impls for several resolver types that don't actually satisfy this condition. It's not obvious to me that rustc_resolve actually upholds the Interned guarantees but fixing that seems pretty hard (the structures have at minimum some interior mutability, so it's not really recursively hashable in place...).
1 parent ce36a96 commit cbe3b6f

File tree

3 files changed

+31
-1
lines changed

3 files changed

+31
-1
lines changed

compiler/rustc_data_structures/src/intern.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ impl<'a, T: Ord> Ord for Interned<'a, T> {
9292
}
9393
}
9494

95-
impl<'a, T> Hash for Interned<'a, T> {
95+
impl<'a, T> Hash for Interned<'a, T> where T: Hash {
9696
#[inline]
9797
fn hash<H: Hasher>(&self, s: &mut H) {
9898
// Pointer hashing is sufficient, due to the uniqueness constraint.

compiler/rustc_resolve/src/imports.rs

+10
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,16 @@ pub(crate) struct ImportData<'ra> {
182182
/// so we can use referential equality to compare them.
183183
pub(crate) type Import<'ra> = Interned<'ra, ImportData<'ra>>;
184184

185+
// Allows us to use Interned without actually enforcing (via Hash/PartialEq/...) uniqueness of the
186+
// contained data.
187+
// FIXME: We may wish to actually have at least debug-level assertions that Interned's guarantees
188+
// are upheld.
189+
impl std::hash::Hash for ImportData<'_> {
190+
fn hash<H>(&self, _: &mut H) where H: std::hash::Hasher {
191+
unreachable!()
192+
}
193+
}
194+
185195
impl<'ra> ImportData<'ra> {
186196
pub(crate) fn is_glob(&self) -> bool {
187197
matches!(self.kind, ImportKind::Glob { .. })

compiler/rustc_resolve/src/lib.rs

+20
Original file line numberDiff line numberDiff line change
@@ -589,6 +589,16 @@ struct ModuleData<'ra> {
589589
#[rustc_pass_by_value]
590590
struct Module<'ra>(Interned<'ra, ModuleData<'ra>>);
591591

592+
// Allows us to use Interned without actually enforcing (via Hash/PartialEq/...) uniqueness of the
593+
// contained data.
594+
// FIXME: We may wish to actually have at least debug-level assertions that Interned's guarantees
595+
// are upheld.
596+
impl std::hash::Hash for ModuleData<'_> {
597+
fn hash<H>(&self, _: &mut H) where H: std::hash::Hasher {
598+
unreachable!()
599+
}
600+
}
601+
592602
impl<'ra> ModuleData<'ra> {
593603
fn new(
594604
parent: Option<Module<'ra>>,
@@ -739,6 +749,16 @@ struct NameBindingData<'ra> {
739749
/// so we can use referential equality to compare them.
740750
type NameBinding<'ra> = Interned<'ra, NameBindingData<'ra>>;
741751

752+
// Allows us to use Interned without actually enforcing (via Hash/PartialEq/...) uniqueness of the
753+
// contained data.
754+
// FIXME: We may wish to actually have at least debug-level assertions that Interned's guarantees
755+
// are upheld.
756+
impl std::hash::Hash for NameBindingData<'_> {
757+
fn hash<H>(&self, _: &mut H) where H: std::hash::Hasher {
758+
unreachable!()
759+
}
760+
}
761+
742762
trait ToNameBinding<'ra> {
743763
fn to_name_binding(self, arenas: &'ra ResolverArenas<'ra>) -> NameBinding<'ra>;
744764
}

0 commit comments

Comments
 (0)