Commit Graph

4502 Commits

Author SHA1 Message Date
Ryan Cumming
2959aa446e Remove parse error on array initializer attributes
This is actually allowed by the `rustc` parser but most attributes will
fail later due to attributes on expressions being experimental.
2019-06-30 19:55:50 +10:00
bors[bot]
fb2534f300 Merge #1459
1459: Include primary span label in VS Code diagnostics r=matklad a=etaoins

In most cases the primary label span repeats information found elsewhere in the diagnostic. For example, with E0061:

```json
{
  "message": "this function takes 2 parameters but 3 parameters were supplied",
  "spans": [{"label": "expected 2 parameters"}]
}
```

However, with some mismatched type errors (E0308) the expected type only appears in the primary span's label, e.g.:

```json
{
  "message": "mismatched types",
  "spans": [{"label": "expected usize, found u32"}]
}
```

I initially added the primary span label to the message unconditionally. However, for most error types the child diagnostics repeat the primary span label with more detail. `rustc` also renders the duplicate text but because the span label and child diagnostics appear in visually distinct places it's not as confusing.

This takes a heuristic approach where it will only add the primary span label if there are no child message lines. For most error types the child messages repeat the primary span label with more detail.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-30 09:54:47 +00:00
bors[bot]
950da94c3a Merge #1460
1460: Consider unreachable code to be unnecessary in VSC r=matklad a=etaoins

This adds `unreachable_code` to the list of diagnostic codes we map to `Unnecessary` in Visual Studio Code. This is consistent with what the TypeScript language server does.

Before:
<img width="308" alt="Screen Shot 2019-06-30 at 12 08 56" src="https://user-images.githubusercontent.com/687534/60391416-133d5480-9b31-11e9-86fb-e252739ab3a8.png">

After:
<img width="303" alt="Screen Shot 2019-06-30 at 12 16 49" src="https://user-images.githubusercontent.com/687534/60391418-19333580-9b31-11e9-9eea-850c62eb9a07.png">


Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-30 09:43:22 +00:00
Ryan Cumming
b01496538c Support attributes on array members
Array members are allow to have attributes such as `#[cfg]`.

This is a bit tricky as we don't know if the first expression is an
initializer or a member until we encounter a `;`. This reuses a trick
from `stmt` where we remember if we saw an attribute and then raise an
error if the first expression ends up being an initializer.

This isn't perfect as the error isn't correctly located on the attribute
or initializer; it ends up immediately after the `;`.
2019-06-30 18:36:54 +10:00
Ryan Cumming
067ca38ecb Consider unreachable code to be unnecessary in VSC
This adds `unreachable_code` to the list of diagnostic codes we map to
`Unnecessary` in Visual Studio Code. This is consistent with what the
TypeScript language server does.
2019-06-30 12:13:56 +10:00
Ryan Cumming
8f726b7db6 Include primary span label in VS Code diagnostics
In most cases the primary label span repeats information found elsewhere
in the diagnostic. For example, with E0061:

```
{
  "message": "this function takes 2 parameters but 3 parameters were supplied",
  "spans": [{"label": "expected 2 parameters"}]
}
```

However, with some mismatched type errors (E0308) the expected type only
appears in the primary span's label, e.g.:

```
{
  "message": "mismatched types",
  "spans": [{"label": "expected usize, found u32"}]
}
```

I initially added the primary span label to the message unconditionally.
However, for most error types the child diagnostics repeat the primary
span label with more detail. `rustc` also renders the duplicate text but
because the span label and child diagnostics appear in visually distinct
places it's not as confusing.

This takes a heuristic approach where it will only add the primary span
label if there are no child message lines.
2019-06-30 11:12:56 +10:00
Ryan Cumming
60ba253753 Run VS Code tests on CI
This is actually much faster than I expected; it takes about 13 seconds
to download VS Code and run the unit tests. This means the VS Code tests
are still significantly faster than the Rust ones.

If this ends up being unreliable we can always remove it later or move
it to a separate optional job.

We also need to ignore the `.vscode-test` directory when running
`prettier` or it will get upset about some temporary JSON files VS Code
creates.
2019-06-30 07:12:42 +10:00
bors[bot]
27df89f47d Merge #1456
1456: Deduplicate method candidates r=matklad a=flodiebold

With trait method completion + autoderef, we were getting a lot of duplicates, which was really annoying...

Co-authored-by: Florian Diebold <flodiebold@gmail.com>
2019-06-29 11:12:51 +00:00
bors[bot]
2bfcfb0b0e Merge #1457
1457: Complete associated methods on enums (and unions) as well r=matklad a=flodiebold

This has been seriously annoying me for a while ;)

Co-authored-by: Florian Diebold <flodiebold@gmail.com>
2019-06-29 11:01:36 +00:00
Florian Diebold
d37f960dfa Complete associated methods on enums (and unions) as well 2019-06-29 12:40:01 +02:00
Florian Diebold
5fd3df0868 Deduplicate method candidates 2019-06-29 12:19:03 +02:00
bors[bot]
8865db6768 Merge #1454
1454: Fix `cargo watch` code action filtering r=etaoins a=etaoins

There are two issues with the implementation of `provideCodeActions` introduced in #1439:

1. We're returning the code action based on the file its diagnostic is in; not the file the suggested fix is in. I'm not sure how often fixes are suggested cross-file but it's something we should handle.

2. We're not filtering code actions based on the passed range. The means if there is any suggestion in a file we'll show an action for every line of the file. I naively thought that VS Code would filter for us but that was wrong.

Unfortunately the VS Code `CodeAction` object is very complex - it can handle edits across multiple files, run commands, etc. This makes it complex to check them for equality or see if any of their edits intersects with a specified range.

To make it easier to work with suggestions this introduces a `SuggestedFix` model object and a `SuggestFixCollection` code action provider. This is a layer between the raw Rust JSON and VS Code's `CodeAction`s. I was reluctant to introduce another layer of abstraction here but my attempt to work directly with VS Code's model objects was worse.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-29 09:50:56 +00:00
Ryan Cumming
50c6ab709e Comment on the key of suggestedFixes
This isn't immediately obvious without looking at the users of the map
2019-06-29 19:46:20 +10:00
bors[bot]
64f71dd3ff Merge #1455
1455: Add noUnusedLocals to VsCode tsconfig r=matklad a=etaoins

`tslint` doesn't catch this because TypeScript has had this check builtin since 2.9. However, it's disabled by default so right now nothing is checking for unused variables.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-29 09:12:05 +00:00
Ryan Cumming
c8fc00258d Add noUnusedLocals to VsCode tsconfig
`tslint` doesn't catch this because TypeScript has had this check
builtin since 2.9. However, it's disabled by default so right now
nothing is checking for unused variables.
2019-06-29 18:00:22 +10:00
Ryan Cumming
abc0784e57 Fix cargo watch code action filtering
There are two issues with the implementation of `provideCodeActions`
introduced in #1439:

1. We're returning the code action based on the file its diagnostic is
   in; not the file the suggested fix is in. I'm not sure how often
   fixes are suggested cross-file but it's something we should handle.

2. We're not filtering code actions based on the passed range. The means
   if there is any suggestion in a file we'll show an action for every
   line of the file. I naively thought that VS Code would filter for us
   but that was wrong.

Unfortunately the VS Code `CodeAction` object is very complex - it can
handle edits across multiple files, run commands, etc. This makes it
complex to check them for equality or see if any of their edits
intersects with a specified range.

To make it easier to work with suggestions this introduces a
`SuggestedFix` model object and a `SuggestFixCollection` code action
provider. This is a layer between the raw Rust JSON and VS Code's
`CodeAction`s. I was reluctant to introduce another layer of abstraction
here but my attempt to work directly with VS Code's model objects was
worse.
2019-06-29 17:39:36 +10:00
bors[bot]
0e1912de52 Merge #1453
1453: Add show syntax tree function to emacs r=matklad a=zbelial

This PR adds preliminary support for showing syntax tree.

Co-authored-by: zbelial <zjytj@qq.com>
2019-06-29 07:06:17 +00:00
zbelial
dc7cec8cf4 Add show syntax tree function to emacs 2019-06-29 09:12:16 +08:00
bors[bot]
1512ab31a0 Merge #1452
1452: Show macros in file structure r=matklad a=viorina



Co-authored-by: Ekaterina Babshukova <ekaterina.babshukova@yandex.ru>
2019-06-28 21:24:25 +00:00
Ekaterina Babshukova
46c453d0d3 show macros in file structure 2019-06-29 00:08:02 +03:00
bors[bot]
5d829841cd Merge #1440
1440: fixed #1384 r=matklad a=zbelial

This PR fixed #1384 .

Co-authored-by: zjy <zhaojiyang1@xiaomi.com>
2019-06-28 12:14:19 +00:00
zjy
de930237ff fixed #1384 2019-06-28 15:22:17 +08:00
bors[bot]
e8dc92ca73 Merge #1450
1450: Extract lint scopes from `cargo watch` r=matklad a=etaoins

Currently all of our VS Code diagnostics are given the source of `rustc`. However, if you have something like `cargo-watch.command` set to `clippy` it will also watch for Clippy lints. The `rustc` source is a bit misleading in that case.

Fortunately, Rust's tool lints ([RFC 2103](https://github.com/rust-lang/rfcs/blob/master/text/2103-tool-attributes.md)) line up perfectly with VS Code's concept of `source`. This checks for lints scoped to a given tool and then splits them in to a `source` and tool-specific `code`.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-27 08:01:23 +00:00
bors[bot]
b13a217a8b Merge #1449
1449: Swallow expected `rustfmt` errors r=matklad a=etaoins

My workflow in Visual Studio Code + Rust Analyzer has become:

1. Make a change to Rust source code using all the analysis magic

2. Save the file to trigger `cargo watch`. I have format on save enabled for all file types so this also runs `rustfmt`

3. Fix any diagnostics that `cargo watch` finds

Unfortunately if the Rust source has any syntax errors the act of saving will pop up a scary "command has failed" message and will switch to the "Output" tab to show the `rustfmt` error and exit code.

I did a quick survey of what other Language Servers do in this case. Both the JSON and TypeScript servers will swallow the error and return success. This is consistent with how I remember my workflow in those languages. The syntax error will show up as a diagnostic so it should be clear why the file isn't formatting.

I checked the `rustfmt` source code and while it does distinguish "parse errors" from "operational errors" internally they both result in exit status of 1. However, more catastrophic errors (missing `rustfmt`, SIGSEGV, etc) will return 127+ error codes which we can distinguish from a normal failure.

This changes our handler to log an info message and feign success if `rustfmt` exits with status 1.

Another option I considered was only swallowing the error if the formatting request came from format-on-save. However, the Language Server Protocol doesn't seem to distinguish those cases.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-27 07:48:36 +00:00
Ryan Cumming
a8a1bc4b15 Extract lint scopes from cargo watch
Currently all of our VS Code diagnostics are given the source of
`rustc`. However, if you have something like `cargo-watch.command` set
to `clippy` it will also watch for Clippy lints. The `rustc` source is a
bit misleading in that case.

Fortunately, Rust's tool lints (RFC 2103) line up perfectly with VS
Code's concept of `source`. This checks for lints scoped to a given tool
and then splits them in to a `source` and tool-specific `code`.
2019-06-27 08:52:22 +10:00
Ryan Cumming
e052ca9d61 Swallow expected rustfmt errors
My workflow in Visual Studio Code + Rust Analyzer has become:

1. Make a change to Rust source code using all the analysis magic

2. Save the file to trigger `cargo watch`. I have format on save enabled
   for all file types so this also runs `rustfmt`

3. Fix any diagnostics that `cargo watch` finds

Unfortunately if the Rust source has any syntax errors the act of saving
will pop up a scary "command has failed" message and will switch to the
"Output" tab to show the `rustfmt` error and exit code.

I did a quick survey of what other Language Servers do in this case.
Both the JSON and TypeScript servers will swallow the error and return
success. This is consistent with how I remember my workflow in those
languages. The syntax error will show up as a diagnostic so it should
be clear why the file isn't formatting.

I checked the `rustfmt` source code and while it does distinguish "parse
errors" from "operational errors" internally they both result in exit
status of 1. However, more catastrophic errors (missing `rustfmt`,
SIGSEGV, etc) will return 127+ error codes which we can distinguish from
a normal failure.

This changes our handler to log an info message and feign success if
`rustfmt` exits with status 1.

Another option I considered was only swallowing the error if the
formatting request came from format-on-save. However, the Language
Server Protocol doesn't seem to distinguish those cases.
2019-06-27 08:08:26 +10:00
bors[bot]
04a211ff61 Merge #1448
1448: ⬆️ rowan r=matklad a=matklad



Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2019-06-26 22:03:18 +00:00
Aleksey Kladov
d4e2a3b726 ⬆️ rowan
New rowan includes one more memory optimization: green nodes are
deduplicated within a single tree
2019-06-27 01:02:10 +03:00
bors[bot]
5536a24914 Merge #1447
1447: make sure that CrateDefMap is independent from syntax r=matklad a=matklad



Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2019-06-26 18:51:29 +00:00
Aleksey Kladov
6e2369938a make sure that CrateDefMap is independent from syntax 2019-06-26 21:50:42 +03:00
bors[bot]
203d5dd0d0 Merge #1443
1443: cache chalk queries r=flodiebold a=matklad

This gives a significant speedup, because chalk will call these
functions several times even withing a single revision. The only
significant one here is `impl_data`, but I figured it might be good to
cache others just for consistency.

The results I get are:

Before:

from scratch:   16.081457952s
no change:      15.846493ms
trivial change: 352.95592ms
comment change: 361.998408ms
const change:   457.629212ms

After:

from scratch:   14.910610278s
no change:      14.934647ms
trivial change: 85.633023ms
comment change: 96.433023ms
const change:   171.543296ms

Seems like a nice win!

Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2019-06-26 16:35:22 +00:00
bors[bot]
0cff7f84c6 Merge #1446
1446: Initial Visual Studio Code unit tests r=matklad a=etaoins

As promised in #1439 this is an initial attempt at unit testing the VSCode extension. There are two separate parts to this: getting the test framework working and unit testing the code in #1439.

The test framework nearly intact from the VSCode extension generator. The main thing missing was `test/index.ts` which acts as an entry point for Mocha. This was simply copied back in. I also needed to open the test VSCode instance inside a workspace as our file URI generation depends on a workspace being open.

There are two ways to run the test framework:

1. Opening the extension's source in VSCode, pressing F5 and selecting the "Extensions Test" debug target.

2. Closing all copies of VSCode and running `npm test`. This is started from the command line but actually opens a temporary VSCode window to host the tests.

This doesn't attempt to wire this up to CI. That requires running a headless X11 server which is a bit daunting. I'll assess the difficulty of that in a follow-up branch. This PR is at least helpful for local development without having to induce errors on a Rust project.

For the actual tests this uses snapshots of `rustc` output from [a real Rust project](https://github.com/etaoins/arret) captured from the command line. Except for extracting the
`message` object and reformatting they're copied verbatim into fixture JSON files.

Only four different types of diagnostics are tested but they represent the main combinations of code actions and related information possible. They can be considered the happy path tests; as we encounter corner-cases we can introduce new tests fixtures.

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-26 11:41:30 +00:00
Ryan Cumming
98ac62c9d7 Document the VS Code extension test framework 2019-06-26 21:38:03 +10:00
Ryan Cumming
f82ceca0bd Initial Visual Studio Code unit tests
As promised in #1439 this is an initial attempt at unit testing the
VSCode extension. There are two separate parts to this: getting the test
framework working and unit testing the code in #1439.

The test framework nearly intact from the VSCode extension generator.
The main thing missing was `test/index.ts` which acts as an entry point
for Mocha. This was simply copied back in. I also needed to open the
test VSCode instance inside a workspace as our file URI generation
depends on a workspace being open.

There are two ways to run the test framework:

1. Opening the extension's source in VSCode, pressing F5 and selecting
   the "Extensions Test" debug target.

2. Closing all copies of VSCode and running `npm test`. This is started
   from the command line but actually opens a temporary VSCode window to
   host the tests.

This doesn't attempt to wire this up to CI. That requires running a
headless X11 server which is a bit daunting. I'll assess the difficulty
of that in a follow-up branch. This PR is at least helpful for local
development without having to induce errors on a Rust project.

For the actual tests this uses snapshots of `rustc` output from a real
Rust project captured from the command line. Except for extracting the
`message` object and reformatting they're copied verbatim into fixture
JSON files.

Only four different types of diagnostics are tested but they represent
the main combinations of code actions and related information possible.
They can be considered the happy path tests; as we encounter
corner-cases we can introduce new tests fixtures.
2019-06-26 20:31:36 +10:00
bors[bot]
afd18dbcb8 Merge #1444
1444: move ra_prof dep where it belongs r=matklad a=matklad



Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2019-06-26 10:09:20 +00:00
Aleksey Kladov
fa55b72c54 move ra_prof dep where it belongs 2019-06-26 13:07:26 +03:00
Aleksey Kladov
a198d78bd1 cache chalk queries
This gives a significant speedup, because chalk will call these
functions several times even withing a single revision. The only
significant one here is `impl_data`, but I figured it might be good to
cache others just for consistency.

The results I get are:

Before:

from scratch:   16.081457952s
no change:      15.846493ms
trivial change: 352.95592ms
comment change: 361.998408ms
const change:   457.629212ms

After:

from scratch:   14.910610278s
no change:      14.934647ms
trivial change: 85.633023ms
comment change: 96.433023ms
const change:   171.543296ms

Seems like a nice win!
2019-06-26 12:54:13 +03:00
bors[bot]
fc0f4ed635 Merge #1442
1442: add cpuprofile to ra_prof r=matklad a=matklad



Co-authored-by: Aleksey Kladov <aleksey.kladov@gmail.com>
2019-06-26 08:13:09 +00:00
Aleksey Kladov
d621533f15 add cpuprofile to ra_prof
Now, one can use `let _p = ra_prof::cpu_profiler()` to capture profile
of a block of code.

This is not an out of the box experience, as that relies on gperfools

See the docs on https://github.com/AtheMathmo/cpuprofiler for more!
2019-06-26 11:11:28 +03:00
bors[bot]
0129790a8f Merge #1432
1432: Make fill_match_arm work with trivial arm r=matklad a=ironyman

Addresses this issue https://github.com/rust-analyzer/rust-analyzer/issues/1399

One minor issue I noticed is that complete_postfix creates an arm like this

```
                match E::X {
                    <|>_ => {},
                }
```

but fill_match_arms creates arms like this
```
                     E::X => (), 
```

Co-authored-by: ironyman <ironyman@users.noreply.github.com>
Co-authored-by: Changyu Li <changyl@microsoft.com>
2019-06-25 21:06:17 +00:00
Changyu Li
3a2a13756f Review 1 2019-06-25 13:26:12 -07:00
bors[bot]
4b0c37bd6e Merge #1439
1439: Rich mapping of cargo watch output r=matklad a=etaoins

Currently we depend on the ASCII rendering string that `rustc` provides to populate Visual Studio Code's diagnostic. This has a number of shortcomings:

1. It's not a very good use of space in the error list
2. We can't jump to secondary spans (e.g. where a called function is defined)
3. We can't use Code Actions aka Quick Fix

This moves all of the low-level parsing and mapping to a `rust_diagnostics.ts`. This uses some heuristics to map Rust diagnostics to VsCode:

1. As before, the Rust diagnostic message and primary span is used for the root diagnostic. However, we now just use the message instead of the rendered version.

2. Every secondary span is converted to "related information". This  shows as child in the error list and can be jumped to.

3. Every child diagnostic is categorised in to three buckets:
    1. If they have no span they're treated as another line of the root messages
    2. If they have replacement text they're treated as a Code Action
    3. If they have a span but no replacement text they're treated as related information (same as secondary spans).

Co-authored-by: Ryan Cumming <etaoins@gmail.com>
2019-06-25 12:37:07 +00:00
bors[bot]
ba97a5fbd2 Merge #1436
1436: Method resolution for slices r=sinkuu a=sinkuu

`impl<T> [T]` is separately defined in `core` and `alloc`, so I changed `def_crate` function in `method_resolution.rs` to return multiple crates.

Co-authored-by: Shotaro Yamada <sinkuu@sinkuu.xyz>
2019-06-25 12:24:13 +00:00
Shotaro Yamada
9668737d05 Add comment 2019-06-25 20:57:42 +09:00
Ryan Cumming
5c6ab11453 Tweak isUnusedOrUnnecessary
The first cut was a bit rough with the blanket `unused_*` rule. This
trigger for things like `unused_mut` where the code is used but it's
suboptimal. It's misleading to grey out the code in those cases.
Instead, use an explicit list of things known to be dead code.
2019-06-25 21:44:27 +10:00
Ryan Cumming
d997fd8ea5 Fix comparison of Code Action edit lengths
This happened to work because we always produce a single edit but this
is obviously dubious.
2019-06-25 21:36:55 +10:00
Ryan Cumming
6d6cb25cf4 Rich mapping of cargo watch output
Currently we depend on the ASCII rendering string that `rustc` provides
to populate Visual Studio Code's diagnostic. This has a number of
shortcomings:

1. It's not a very good use of space in the error list
2. We can't jump to secondary spans (e.g. where a called function is
   defined)
3. We can't use Code Actions aka Quick Fix

This moves all of the low-level parsing and mapping to a
`rust_diagnostics.ts`. This uses some heuristics to map Rust diagnostics
to VsCode:

1. As before, the Rust diagnostic message and primary span is used for
   the root diagnostic. However, we now just use the message instead of
   the rendered version.

2. Every secondary span is converted to "related information". This
   shows as child in the error list and can be jumped to.

3. Every child diagnostic is categorised in to three buckets:
    1. If they have no span they're treated as another line of the root
       messages
    2. If they have replacement text they're treated as a Code Action
    3. If they have a span but no replacement text they're treated as
       related information (same as secondary spans).
2019-06-25 21:16:04 +10:00
Shotaro Yamada
9e7a6bd66e Method resolution for slices 2019-06-25 02:17:44 +09:00
bors[bot]
364ac9b946 Merge #1434
1434: Introduce cargo-watch.check-command option for Code extension r=matklad a=alekseysidorov

By this option you can replace `check` command in `cargo watch` by the something else like `clippy`.

Co-authored-by: Aleksei Sidorov <aleksei.sidorov@xdev.re>
Co-authored-by: Aleksey Sidorov <alekseysidorov@users.noreply.github.com>
2019-06-24 11:03:28 +00:00
Aleksei Sidorov
28e9e8d4cf Fix code after "apply suggestions" 2019-06-24 13:50:34 +03:00