about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--crates/rust-analyzer/src/diagnostics/test_data/reasonable_line_numbers_from_empty_file.txt64
-rw-r--r--crates/rust-analyzer/src/diagnostics/to_proto.rs53
2 files changed, 115 insertions, 2 deletions
diff --git a/crates/rust-analyzer/src/diagnostics/test_data/reasonable_line_numbers_from_empty_file.txt b/crates/rust-analyzer/src/diagnostics/test_data/reasonable_line_numbers_from_empty_file.txt
new file mode 100644
index 00000000000..df00b330b6e
--- /dev/null
+++ b/crates/rust-analyzer/src/diagnostics/test_data/reasonable_line_numbers_from_empty_file.txt
@@ -0,0 +1,64 @@
+[
+    MappedRustDiagnostic {
+        url: Url {
+            scheme: "file",
+            cannot_be_a_base: false,
+            username: "",
+            password: None,
+            host: None,
+            port: None,
+            path: "/test/src/bin/current.rs",
+            query: None,
+            fragment: None,
+        },
+        diagnostic: Diagnostic {
+            range: Range {
+                start: Position {
+                    line: 0,
+                    character: 0,
+                },
+                end: Position {
+                    line: 0,
+                    character: 0,
+                },
+            },
+            severity: Some(
+                Error,
+            ),
+            code: Some(
+                String(
+                    "E0601",
+                ),
+            ),
+            code_description: Some(
+                CodeDescription {
+                    href: Url {
+                        scheme: "https",
+                        cannot_be_a_base: false,
+                        username: "",
+                        password: None,
+                        host: Some(
+                            Domain(
+                                "doc.rust-lang.org",
+                            ),
+                        ),
+                        port: None,
+                        path: "/error-index.html",
+                        query: None,
+                        fragment: Some(
+                            "E0601",
+                        ),
+                    },
+                },
+            ),
+            source: Some(
+                "rustc",
+            ),
+            message: "`main` function not found in crate `current`\nconsider adding a `main` function to `src/bin/current.rs`",
+            related_information: None,
+            tags: None,
+            data: None,
+        },
+        fix: None,
+    },
+]
diff --git a/crates/rust-analyzer/src/diagnostics/to_proto.rs b/crates/rust-analyzer/src/diagnostics/to_proto.rs
index dd59923cb34..45e46c1a06b 100644
--- a/crates/rust-analyzer/src/diagnostics/to_proto.rs
+++ b/crates/rust-analyzer/src/diagnostics/to_proto.rs
@@ -63,8 +63,14 @@ fn location(
 
     // FIXME: this doesn't handle UTF16 offsets correctly
     let range = lsp_types::Range::new(
-        lsp_types::Position::new(span.line_start as u32 - 1, span.column_start as u32 - 1),
-        lsp_types::Position::new(span.line_end as u32 - 1, span.column_end as u32 - 1),
+        lsp_types::Position::new(
+            (span.line_start as u32).saturating_sub(1),
+            (span.column_start as u32).saturating_sub(1),
+        ),
+        lsp_types::Position::new(
+            (span.line_end as u32).saturating_sub(1),
+            (span.column_end as u32).saturating_sub(1),
+        ),
     );
 
     lsp_types::Location { uri, range }
@@ -1674,4 +1680,47 @@ mod tests {
             expect_file!["./test_data/snap_multi_line_fix.txt"],
         );
     }
+
+    #[test]
+    fn reasonable_line_numbers_from_empty_file() {
+        check(
+            r##"{
+                "message": "`main` function not found in crate `current`",
+                "code": {
+                    "code": "E0601",
+                    "explanation": "No `main` function was found in a binary crate.\n\nTo fix this error, add a `main` function:\n\n```\nfn main() {\n    // Your program will start here.\n    println!(\"Hello world!\");\n}\n```\n\nIf you don't know the basics of Rust, you can look at the\n[Rust Book][rust-book] to get started.\n\n[rust-book]: https://doc.rust-lang.org/book/\n"
+                },
+                "level": "error",
+                "spans": [
+                    {
+                        "file_name": "src/bin/current.rs",
+                        "byte_start": 0,
+                        "byte_end": 0,
+                        "line_start": 0,
+                        "line_end": 0,
+                        "column_start": 1,
+                        "column_end": 1,
+                        "is_primary": true,
+                        "text": [],
+                        "label": null,
+                        "suggested_replacement": null,
+                        "suggestion_applicability": null,
+                        "expansion": null
+                    }
+                ],
+                "children": [
+                    {
+                        "message": "consider adding a `main` function to `src/bin/current.rs`",
+                        "code": null,
+                        "level": "note",
+                        "spans": [],
+                        "children": [],
+                        "rendered": null
+                    }
+                ],
+                "rendered": "error[E0601]: `main` function not found in crate `current`\n  |\n  = note: consider adding a `main` function to `src/bin/current.rs`\n\n"
+            }"##,
+            expect_file!["./test_data/reasonable_line_numbers_from_empty_file.txt"],
+        );
+    }
 }