diff --git a/src/query.md b/src/query.md index 3d60059bd..268a56558 100644 --- a/src/query.md +++ b/src/query.md @@ -169,31 +169,30 @@ they define both a `provide` and a `provide_extern` function, through How do you add a new query? Defining a query takes place in two steps: -1. Specify the query name and its arguments. +1. Declare the query name, its arguments and description. 2. Supply query providers where needed. -To specify the query name and arguments, you simply add an entry to -the big macro invocation in -[`compiler/rustc_middle/src/query/mod.rs`][query-mod], which looks something like: +To declare the query name and arguments, you simply add an entry to +the big macro invocation in [`compiler/rustc_middle/src/query/mod.rs`][query-mod]. +Then you need to add a documentation comment to it with some _internal_ description. +Then, provide the `desc` attribute which contains a _user-facing_ description of the query. +The `desc` attribute is shown to the user in query cycles. + +This looks something like: [query-mod]: https://doc.rust-lang.org/nightly/nightly-rustc/rustc_middle/query/index.html ```rust,ignore rustc_queries! { - Other { - /// Records the type of every item. - query type_of(key: DefId) -> Ty<'tcx> { - cache { key.is_local() } - } + /// Records the type of every item. + query type_of(key: DefId) -> Ty<'tcx> { + cache_on_disk_if { key.is_local() } + desc { |tcx| "computing the type of `{}`", tcx.def_path_str(key) } } - ... } ``` -Queries are grouped into categories (`Other`, `Codegen`, `TypeChecking`, etc.). -Each group contains one or more queries. - A query definition has the following form: ```rust,ignore @@ -238,62 +237,6 @@ which is used to cheaply modify MIR in place. See the definition of `Steal` for more details. New uses of `Steal` should **not** be added without alerting `@rust-lang/compiler`. -### Query structs and descriptions - -For each query, the `rustc_queries` macro will generate a "query struct" -named after the query. This struct is a kind of placeholder -describing the query. Each query struct implements the -[`self::config::QueryConfig`][QueryConfig] trait, which has associated types for the -key/value of that particular query. Basically the code generated looks something -like this: - -```rust,ignore -// Dummy struct representing a particular kind of query: -pub struct type_of<'tcx> { data: PhantomData<&'tcx ()> } - -impl<'tcx> QueryConfig for type_of<'tcx> { - type Key = DefId; - type Value = Ty<'tcx>; - - const NAME: QueryName = QueryName::type_of; - const CATEGORY: ProfileCategory = ProfileCategory::Other; -} -``` - -There is an additional trait that you may wish to implement called -[`self::config::QueryDescription`][QueryDescription]. This trait is -used during cycle errors to give a "human readable" name for the query, -so that we can summarize what was happening when the cycle occurred. -Implementing this trait is optional if the query key is `DefId`, but -if you *don't* implement it, you get a pretty generic error ("processing `foo`..."). -You can put new impls into the `config` module. They look something like this: - -[QueryConfig]: https://doc.rust-lang.org/nightly/nightly-rustc/rustc_query_system/query/config/trait.QueryConfig.html -[QueryDescription]: https://doc.rust-lang.org/nightly/nightly-rustc/rustc_query_system/query/config/trait.QueryDescription.html - -```rust,ignore -impl<'tcx> QueryDescription for queries::type_of<'tcx> { - fn describe(tcx: TyCtxt, key: DefId) -> String { - format!("computing the type of `{}`", tcx.def_path_str(key)) - } -} -``` - -Another option is to add `desc` modifier: - -```rust,ignore -rustc_queries! { - Other { - /// Records the type of every item. - query type_of(key: DefId) -> Ty<'tcx> { - desc { |tcx| "computing the type of `{}`", tcx.def_path_str(key) } - } - } -} -``` - -`rustc_queries` macro will generate an appropriate `impl` automatically. - ## External links Related design ideas, and tracking issues: