260: Include user-readable query keys in cycle errors r=nikomatsakis a=jonas-schievink

Previous output:

```
---- nameres::tests::macros::unexpanded_macro_should_expand_by_fixedpoint_loop stdout ----
thread 'nameres::tests::macros::unexpanded_macro_should_expand_by_fixedpoint_loop' panicked at 'Internal error, cycle detected:

DatabaseKeyIndex { group_index: 2, query_index: 11, key_index: 1 }
', /home/jonas/.cargo/registry/src/github.com-1ecc6299db9ec823/salsa-0.16.1/src/lib.rs:490:48
```

Output after this PR:

```
---- nameres::tests::macros::unexpanded_macro_should_expand_by_fixedpoint_loop stdout ----
thread 'nameres::tests::macros::unexpanded_macro_should_expand_by_fixedpoint_loop' panicked at 'Internal error, cycle detected:

hygiene_frame(HirFileId(MacroFile(MacroFile { macro_call_id: LazyMacro(LazyMacroId(0)) })))
', /home/jonas/dev/salsa/src/lib.rs:492:35
```

Co-authored-by: Jonas Schievink <jonasschievink@gmail.com>
This commit is contained in:
bors[bot] 2021-05-15 09:03:36 +00:00 committed by GitHub
commit 47d409937f
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23

View file

@ -25,6 +25,7 @@ pub mod debug;
#[doc(hidden)]
pub mod plumbing;
use crate::plumbing::DatabaseOps;
use crate::plumbing::DerivedQueryStorageOps;
use crate::plumbing::InputQueryStorageOps;
use crate::plumbing::LruQueryStorageOps;
@ -487,7 +488,8 @@ where
/// queries (those with no inputs, or those with more than one
/// input) the key will be a tuple.
pub fn get(&self, key: Q::Key) -> Q::Value {
self.try_get(key).unwrap_or_else(|err| panic!("{}", err))
self.try_get(key)
.unwrap_or_else(|err| panic!("{:?}", err.debug(self.db)))
}
fn try_get(&self, key: Q::Key) -> Result<Q::Value, CycleError<DatabaseKeyIndex>> {
@ -513,7 +515,8 @@ where
Q::Storage: plumbing::QueryStorageMassOps,
{
self.storage.purge();
}}
}
}
/// Return value from [the `query_mut` method] on `Database`.
/// Gives access to the `set` method, notably, that is used to
@ -604,6 +607,30 @@ pub struct CycleError<K> {
durability: Durability,
}
impl CycleError<DatabaseKeyIndex> {
fn debug<'a, D: ?Sized>(&'a self, db: &'a D) -> impl Debug + 'a
where
D: DatabaseOps,
{
struct CycleErrorDebug<'a, D: ?Sized> {
db: &'a D,
error: &'a CycleError<DatabaseKeyIndex>,
}
impl<'a, D: ?Sized + DatabaseOps> Debug for CycleErrorDebug<'a, D> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
writeln!(f, "Internal error, cycle detected:\n")?;
for i in &self.error.cycle {
writeln!(f, "{:?}", i.debug(self.db))?;
}
Ok(())
}
}
CycleErrorDebug { db, error: self }
}
}
impl<K> fmt::Display for CycleError<K>
where
K: fmt::Debug,