2021-05-22 08:53:47 -05:00
|
|
|
//! Re-export diagnostics such that clients of `hir` don't have to depend on
|
|
|
|
//! low-level crates.
|
|
|
|
//!
|
|
|
|
//! This probably isn't the best way to do this -- ideally, diagnistics should
|
|
|
|
//! be expressed in terms of hir types themselves.
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
use std::any::Any;
|
|
|
|
|
2021-06-13 09:29:25 -05:00
|
|
|
use cfg::{CfgExpr, CfgOptions};
|
2021-06-13 07:48:54 -05:00
|
|
|
use either::Either;
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
use hir_def::path::ModPath;
|
2021-06-12 11:28:19 -05:00
|
|
|
use hir_expand::{name::Name, HirFileId, InFile};
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
use syntax::{ast, AstPtr, SyntaxNodePtr, TextRange};
|
|
|
|
|
2021-06-12 14:05:23 -05:00
|
|
|
pub use crate::diagnostics_sink::{
|
|
|
|
Diagnostic, DiagnosticCode, DiagnosticSink, DiagnosticSinkBuilder,
|
2020-07-08 12:58:45 -05:00
|
|
|
};
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
|
2021-06-13 06:41:19 -05:00
|
|
|
macro_rules! diagnostics {
|
2021-06-13 09:06:36 -05:00
|
|
|
($($diag:ident,)*) => {
|
2021-06-13 06:41:19 -05:00
|
|
|
pub enum AnyDiagnostic {$(
|
|
|
|
$diag(Box<$diag>),
|
|
|
|
)*}
|
|
|
|
|
|
|
|
$(
|
|
|
|
impl From<$diag> for AnyDiagnostic {
|
|
|
|
fn from(d: $diag) -> AnyDiagnostic {
|
|
|
|
AnyDiagnostic::$diag(Box::new(d))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
)*
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2021-06-13 09:06:36 -05:00
|
|
|
diagnostics![
|
2021-06-13 11:35:30 -05:00
|
|
|
InactiveCode,
|
|
|
|
MacroError,
|
|
|
|
MissingFields,
|
|
|
|
UnimplementedBuiltinMacro,
|
2021-06-13 09:06:36 -05:00
|
|
|
UnresolvedExternCrate,
|
|
|
|
UnresolvedImport,
|
|
|
|
UnresolvedMacroCall,
|
2021-06-13 11:35:30 -05:00
|
|
|
UnresolvedModule,
|
2021-06-13 09:51:44 -05:00
|
|
|
UnresolvedProcMacro,
|
2021-06-13 09:06:36 -05:00
|
|
|
];
|
2021-06-13 06:41:19 -05:00
|
|
|
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct UnresolvedModule {
|
2021-06-13 06:41:19 -05:00
|
|
|
pub decl: InFile<AstPtr<ast::Module>>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
pub candidate: String,
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct UnresolvedExternCrate {
|
2021-06-13 08:05:43 -05:00
|
|
|
pub decl: InFile<AstPtr<ast::ExternCrate>>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct UnresolvedImport {
|
2021-06-13 08:42:34 -05:00
|
|
|
pub decl: InFile<AstPtr<ast::UseTree>>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug, Clone, Eq, PartialEq)]
|
|
|
|
pub struct UnresolvedMacroCall {
|
2021-06-13 09:06:36 -05:00
|
|
|
pub macro_call: InFile<AstPtr<ast::MacroCall>>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
pub path: ModPath,
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug, Clone, Eq, PartialEq)]
|
|
|
|
pub struct InactiveCode {
|
2021-06-13 09:29:25 -05:00
|
|
|
pub node: InFile<SyntaxNodePtr>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
pub cfg: CfgExpr,
|
|
|
|
pub opts: CfgOptions,
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug, Clone, Eq, PartialEq)]
|
|
|
|
pub struct UnresolvedProcMacro {
|
2021-06-13 09:51:44 -05:00
|
|
|
pub node: InFile<SyntaxNodePtr>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
/// If the diagnostic can be pinpointed more accurately than via `node`, this is the `TextRange`
|
|
|
|
/// to use instead.
|
|
|
|
pub precise_location: Option<TextRange>,
|
|
|
|
pub macro_name: Option<String>,
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug, Clone, Eq, PartialEq)]
|
|
|
|
pub struct MacroError {
|
2021-06-13 10:41:04 -05:00
|
|
|
pub node: InFile<SyntaxNodePtr>,
|
internal: move diagnostics to hir
The idea here is to eventually get rid of `dyn Diagnostic` and
`DiagnosticSink` infrastructure altogether, and just have a `enum
hir::Diagnostic` instead.
The problem with `dyn Diagnostic` is that it is defined in the lowest
level of the stack (hir_expand), but is used by the highest level (ide).
As a first step, we free hir_expand and hir_def from `dyn Diagnostic`
and kick the can up to `hir_ty`, as an intermediate state. The plan is
then to move DiagnosticSink similarly to the hir crate, and, as final
third step, remove its usage from the ide.
One currently unsolved problem is testing. You can notice that the test
which checks precise diagnostic ranges, unresolved_import_in_use_tree,
was moved to the ide layer. Logically, only IDE should have the infra to
render a specific range.
At the same time, the range is determined with the data produced in
hir_def and hir crates, so this layering is rather unfortunate. Working
on hir_def shouldn't require compiling `ide` for testing.
2021-05-23 15:31:59 -05:00
|
|
|
pub message: String,
|
|
|
|
}
|
|
|
|
|
2021-05-29 21:19:47 -05:00
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct UnimplementedBuiltinMacro {
|
2021-06-13 11:35:30 -05:00
|
|
|
pub node: InFile<SyntaxNodePtr>,
|
2021-05-29 21:19:47 -05:00
|
|
|
}
|
2021-06-12 09:17:23 -05:00
|
|
|
|
|
|
|
// Diagnostic: no-such-field
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if created structure does not have field provided in record.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct NoSuchField {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub field: AstPtr<ast::RecordExprField>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for NoSuchField {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("no-such-field")
|
|
|
|
}
|
|
|
|
|
|
|
|
fn message(&self) -> String {
|
|
|
|
"no such field".to_string()
|
|
|
|
}
|
|
|
|
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile::new(self.file, self.field.clone().into())
|
|
|
|
}
|
|
|
|
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Diagnostic: break-outside-of-loop
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if the `break` keyword is used outside of a loop.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct BreakOutsideOfLoop {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub expr: AstPtr<ast::Expr>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for BreakOutsideOfLoop {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("break-outside-of-loop")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
"break outside of loop".to_string()
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
2021-06-12 09:39:46 -05:00
|
|
|
|
|
|
|
// Diagnostic: missing-unsafe
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if an operation marked as `unsafe` is used outside of an `unsafe` function or block.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct MissingUnsafe {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub expr: AstPtr<ast::Expr>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for MissingUnsafe {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("missing-unsafe")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
format!("This operation is unsafe and requires an unsafe function or block")
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
2021-06-12 11:28:19 -05:00
|
|
|
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct MissingFields {
|
|
|
|
pub file: HirFileId,
|
2021-06-13 07:48:54 -05:00
|
|
|
pub field_list_parent: Either<AstPtr<ast::RecordExpr>, AstPtr<ast::RecordPat>>,
|
2021-06-12 11:28:19 -05:00
|
|
|
pub field_list_parent_path: Option<AstPtr<ast::Path>>,
|
|
|
|
pub missed_fields: Vec<Name>,
|
|
|
|
}
|
|
|
|
|
|
|
|
// Diagnostic: replace-filter-map-next-with-find-map
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered when `.filter_map(..).next()` is used, rather than the more concise `.find_map(..)`.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct ReplaceFilterMapNextWithFindMap {
|
|
|
|
pub file: HirFileId,
|
|
|
|
/// This expression is the whole method chain up to and including `.filter_map(..).next()`.
|
|
|
|
pub next_expr: AstPtr<ast::Expr>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for ReplaceFilterMapNextWithFindMap {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("replace-filter-map-next-with-find-map")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
"replace filter_map(..).next() with find_map(..)".to_string()
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.next_expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Diagnostic: mismatched-arg-count
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if a function is invoked with an incorrect amount of arguments.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct MismatchedArgCount {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub call_expr: AstPtr<ast::Expr>,
|
|
|
|
pub expected: usize,
|
|
|
|
pub found: usize,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for MismatchedArgCount {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("mismatched-arg-count")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
let s = if self.expected == 1 { "" } else { "s" };
|
|
|
|
format!("Expected {} argument{}, found {}", self.expected, s, self.found)
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.call_expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
fn is_experimental(&self) -> bool {
|
|
|
|
true
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct RemoveThisSemicolon {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub expr: AstPtr<ast::Expr>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for RemoveThisSemicolon {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("remove-this-semicolon")
|
|
|
|
}
|
|
|
|
|
|
|
|
fn message(&self) -> String {
|
|
|
|
"Remove this semicolon".to_string()
|
|
|
|
}
|
|
|
|
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.expr.clone().into() }
|
|
|
|
}
|
|
|
|
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Diagnostic: missing-ok-or-some-in-tail-expr
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if a block that should return `Result` returns a value not wrapped in `Ok`,
|
|
|
|
// or if a block that should return `Option` returns a value not wrapped in `Some`.
|
|
|
|
//
|
|
|
|
// Example:
|
|
|
|
//
|
|
|
|
// ```rust
|
|
|
|
// fn foo() -> Result<u8, ()> {
|
|
|
|
// 10
|
|
|
|
// }
|
|
|
|
// ```
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct MissingOkOrSomeInTailExpr {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub expr: AstPtr<ast::Expr>,
|
|
|
|
// `Some` or `Ok` depending on whether the return type is Result or Option
|
|
|
|
pub required: String,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for MissingOkOrSomeInTailExpr {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("missing-ok-or-some-in-tail-expr")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
format!("wrap return expression in {}", self.required)
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Diagnostic: missing-match-arm
|
|
|
|
//
|
|
|
|
// This diagnostic is triggered if `match` block is missing one or more match arms.
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct MissingMatchArms {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub match_expr: AstPtr<ast::Expr>,
|
|
|
|
pub arms: AstPtr<ast::MatchArmList>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for MissingMatchArms {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("missing-match-arm")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
String::from("Missing match arm")
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.match_expr.clone().into() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
#[derive(Debug)]
|
|
|
|
pub struct InternalBailedOut {
|
|
|
|
pub file: HirFileId,
|
|
|
|
pub pat_syntax_ptr: SyntaxNodePtr,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Diagnostic for InternalBailedOut {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("internal:match-check-bailed-out")
|
|
|
|
}
|
|
|
|
fn message(&self) -> String {
|
|
|
|
format!("Internal: match check bailed out")
|
|
|
|
}
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile { file_id: self.file, value: self.pat_syntax_ptr.clone() }
|
|
|
|
}
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
}
|
2021-06-12 14:05:23 -05:00
|
|
|
|
|
|
|
pub use hir_ty::diagnostics::IncorrectCase;
|
|
|
|
|
|
|
|
impl Diagnostic for IncorrectCase {
|
|
|
|
fn code(&self) -> DiagnosticCode {
|
|
|
|
DiagnosticCode("incorrect-ident-case")
|
|
|
|
}
|
|
|
|
|
|
|
|
fn message(&self) -> String {
|
|
|
|
format!(
|
|
|
|
"{} `{}` should have {} name, e.g. `{}`",
|
|
|
|
self.ident_type,
|
|
|
|
self.ident_text,
|
|
|
|
self.expected_case.to_string(),
|
|
|
|
self.suggested_text
|
|
|
|
)
|
|
|
|
}
|
|
|
|
|
|
|
|
fn display_source(&self) -> InFile<SyntaxNodePtr> {
|
|
|
|
InFile::new(self.file, self.ident.clone().into())
|
|
|
|
}
|
|
|
|
|
|
|
|
fn as_any(&self) -> &(dyn Any + Send + 'static) {
|
|
|
|
self
|
|
|
|
}
|
|
|
|
|
|
|
|
fn is_experimental(&self) -> bool {
|
|
|
|
true
|
|
|
|
}
|
|
|
|
}
|