Skip to content

Commit be1b76b

Browse files
authored
fix: Do not unnecessarily require Debug on fields for interned structs (#951)
1 parent 1ffb32f commit be1b76b

File tree

3 files changed

+110
-15
lines changed

3 files changed

+110
-15
lines changed

components/salsa-macro-rules/src/macro_if.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,4 +22,12 @@ macro_rules! macro_if {
2222
(if0 $n:literal { $($t:tt)* } else { $($f:tt)*}) => {
2323
$($f)*
2424
};
25+
26+
(iftt () { $($t:tt)* } else { $($f:tt)*}) => {
27+
$($f)*
28+
};
29+
30+
(iftt ($($tt:tt)+) { $($t:tt)* } else { $($f:tt)*}) => {
31+
$($t)*
32+
};
2533
}

components/salsa-macro-rules/src/setup_interned_struct.rs

Lines changed: 51 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -330,22 +330,58 @@ macro_rules! setup_interned_struct {
330330
)
331331
}
332332
)*
333+
}
333334

334-
/// Default debug formatting for this struct (may be useful if you define your own `Debug` impl)
335-
pub fn default_debug_fmt(this: Self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
336-
$zalsa::with_attached_database(|db| {
337-
let zalsa = db.zalsa();
338-
let fields = $Configuration::ingredient(zalsa).fields(zalsa, this);
339-
let mut f = f.debug_struct(stringify!($Struct));
340-
$(
341-
let f = f.field(stringify!($field_id), &fields.$field_index);
342-
)*
343-
f.finish()
344-
}).unwrap_or_else(|| {
345-
f.debug_tuple(stringify!($Struct))
346-
.field(&$zalsa::AsId::as_id(&this))
347-
.finish()
348-
})
335+
// Duplication can be dropped here once we no longer allow the `no_lifetime` hack
336+
$zalsa::macro_if! {
337+
iftt ($($db_lt_arg)?) {
338+
impl $Struct<'_> {
339+
/// Default debug formatting for this struct (may be useful if you define your own `Debug` impl)
340+
pub fn default_debug_fmt(this: Self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result
341+
where
342+
// rustc rejects trivial bounds, but it cannot see through higher-ranked bounds
343+
// with its check :^)
344+
$(for<$db_lt> $field_ty: std::fmt::Debug),*
345+
{
346+
$zalsa::with_attached_database(|db| {
347+
let zalsa = db.zalsa();
348+
let fields = $Configuration::ingredient(zalsa).fields(zalsa, this);
349+
let mut f = f.debug_struct(stringify!($Struct));
350+
$(
351+
let f = f.field(stringify!($field_id), &fields.$field_index);
352+
)*
353+
f.finish()
354+
}).unwrap_or_else(|| {
355+
f.debug_tuple(stringify!($Struct))
356+
.field(&$zalsa::AsId::as_id(&this))
357+
.finish()
358+
})
359+
}
360+
}
361+
} else {
362+
impl $Struct {
363+
/// Default debug formatting for this struct (may be useful if you define your own `Debug` impl)
364+
pub fn default_debug_fmt(this: Self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result
365+
where
366+
// rustc rejects trivial bounds, but it cannot see through higher-ranked bounds
367+
// with its check :^)
368+
$(for<$db_lt> $field_ty: std::fmt::Debug),*
369+
{
370+
$zalsa::with_attached_database(|db| {
371+
let zalsa = db.zalsa();
372+
let fields = $Configuration::ingredient(zalsa).fields(zalsa, this);
373+
let mut f = f.debug_struct(stringify!($Struct));
374+
$(
375+
let f = f.field(stringify!($field_id), &fields.$field_index);
376+
)*
377+
f.finish()
378+
}).unwrap_or_else(|| {
379+
f.debug_tuple(stringify!($Struct))
380+
.field(&$zalsa::AsId::as_id(&this))
381+
.finish()
382+
})
383+
}
384+
}
349385
}
350386
}
351387
};

tests/debug_bounds.rs

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
#![cfg(feature = "inventory")]
2+
3+
//! Test that debug and non-debug structs compile correctly
4+
5+
#[derive(Ord, PartialOrd, Eq, PartialEq, Copy, Clone, Hash)]
6+
struct NotDebug;
7+
#[derive(Ord, PartialOrd, Eq, PartialEq, Copy, Clone, Hash, Debug)]
8+
struct Debug;
9+
10+
#[salsa::input(debug)]
11+
struct DebugInput {
12+
field: Debug,
13+
}
14+
15+
#[salsa::input]
16+
struct NotDebugInput {
17+
field: NotDebug,
18+
}
19+
20+
#[salsa::interned(debug)]
21+
struct DebugInterned {
22+
field: Debug,
23+
}
24+
25+
#[salsa::interned]
26+
struct NotDebugInterned {
27+
field: NotDebug,
28+
}
29+
30+
#[salsa::interned(no_lifetime, debug)]
31+
struct DebugInternedNoLifetime {
32+
field: Debug,
33+
}
34+
35+
#[salsa::interned(no_lifetime)]
36+
struct NotDebugInternedNoLifetime {
37+
field: NotDebug,
38+
}
39+
40+
#[salsa::tracked(debug)]
41+
struct DebugTracked<'db> {
42+
field: Debug,
43+
}
44+
45+
#[salsa::tracked]
46+
struct NotDebugTracked<'db> {
47+
field: NotDebug,
48+
}
49+
50+
#[test]
51+
fn ok() {}

0 commit comments

Comments
 (0)