aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.github/workflows/ci.yaml42
-rw-r--r--Cargo.lock117
-rw-r--r--bors.toml7
-rw-r--r--crates/ra_assists/src/assists/flip_binexpr.rs12
-rw-r--r--crates/ra_cargo_watch/src/conv/test.rs2
-rw-r--r--crates/ra_db/src/fixture.rs6
-rw-r--r--crates/ra_db/src/input.rs8
-rw-r--r--crates/ra_hir/src/code_model.rs3
-rw-r--r--crates/ra_hir/src/db.rs18
-rw-r--r--crates/ra_hir_def/src/db.rs11
-rw-r--r--crates/ra_hir_def/src/nameres.rs4
-rw-r--r--crates/ra_hir_def/src/nameres/collector.rs1
-rw-r--r--crates/ra_hir_expand/src/name.rs5
-rw-r--r--crates/ra_hir_ty/src/db.rs11
-rw-r--r--crates/ra_hir_ty/src/infer.rs4
-rw-r--r--crates/ra_hir_ty/src/lib.rs2
-rw-r--r--crates/ra_hir_ty/src/lower.rs2
-rw-r--r--crates/ra_hir_ty/src/tests/regression.rs17
-rw-r--r--crates/ra_ide/Cargo.toml1
-rw-r--r--crates/ra_ide/src/call_hierarchy.rs337
-rw-r--r--crates/ra_ide/src/call_info.rs15
-rw-r--r--crates/ra_ide/src/change.rs11
-rw-r--r--crates/ra_ide/src/diagnostics.rs36
-rw-r--r--crates/ra_ide/src/display/navigation_target.rs2
-rw-r--r--crates/ra_ide/src/expand.rs5
-rw-r--r--crates/ra_ide/src/lib.rs22
-rw-r--r--crates/ra_ide/src/references.rs205
-rw-r--r--crates/ra_ide/src/references/rename.rs8
-rw-r--r--crates/ra_lsp_server/src/caps.rs5
-rw-r--r--crates/ra_lsp_server/src/conv.rs18
-rw-r--r--crates/ra_lsp_server/src/main_loop.rs3
-rw-r--r--crates/ra_lsp_server/src/main_loop/handlers.rs113
-rw-r--r--crates/ra_lsp_server/src/req.rs16
-rw-r--r--crates/ra_parser/src/grammar/items/traits.rs5
-rw-r--r--crates/ra_parser/src/grammar/type_args.rs10
-rw-r--r--crates/ra_parser/src/syntax_kind/generated.rs271
-rw-r--r--crates/ra_prof/src/lib.rs29
-rw-r--r--crates/ra_project_model/src/sysroot.rs5
-rw-r--r--crates/ra_syntax/src/ast/expr_extensions.rs18
-rw-r--r--crates/ra_syntax/src/ast/generated.rs2989
-rw-r--r--crates/ra_syntax/src/grammar.ron736
-rw-r--r--crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.rs2
-rw-r--r--crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.txt51
-rw-r--r--crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.rs1
-rw-r--r--crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.txt38
-rw-r--r--docs/dev/lsp-features.md4
-rw-r--r--docs/user/README.md4
-rw-r--r--editors/code/src/client.ts4
-rw-r--r--xtask/Cargo.toml2
-rw-r--r--xtask/src/ast_src.rs621
-rw-r--r--xtask/src/boilerplate_gen.rs0
-rw-r--r--xtask/src/cmd.rs53
-rw-r--r--xtask/src/codegen.rs1
-rw-r--r--xtask/src/codegen/gen_syntax.rs234
-rw-r--r--xtask/src/help.rs46
-rw-r--r--xtask/src/install.rs178
-rw-r--r--xtask/src/lib.rs126
-rw-r--r--xtask/src/main.rs301
-rw-r--r--xtask/src/pre_commit.rs36
59 files changed, 3772 insertions, 3062 deletions
diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml
index 1d24295ec..e7e0d599e 100644
--- a/.github/workflows/ci.yaml
+++ b/.github/workflows/ci.yaml
@@ -10,16 +10,29 @@ on:
10jobs: 10jobs:
11 rust: 11 rust:
12 name: Rust 12 name: Rust
13 runs-on: ubuntu-latest 13 runs-on: ${{ matrix.os }}
14 strategy:
15 matrix:
16 os: [ubuntu-latest, windows-latest, macos-latest]
14 env: 17 env:
15 RUSTFLAGS: -D warnings 18 RUSTFLAGS: -D warnings
16 CARGO_INCREMENTAL: 0 19 CARGO_INCREMENTAL: 0
17 RUN_SLOW_TESTS: 1 20 RUN_SLOW_TESTS: 1
21 RUSTUP_MAX_RETRIES: 10
22 CARGO_NET_RETRY: 10
18 steps: 23 steps:
19 24
20 - name: Checkout repository 25 - name: Checkout repository
21 uses: actions/checkout@v1 26 uses: actions/checkout@v1
22 27
28 # We need to disable the existing toolchain to avoid updating rust-docs
29 # which takes a long time. The fastest way to do this is to rename the
30 # existing folder, as deleting it takes about as much time as not doing
31 # anything and just updating rust-docs.
32 - name: Rename existing rust toolchain (Windows)
33 if: matrix.os == 'windows-latest'
34 run: Rename-Item C:\Users\runneradmin\.rustup\toolchains\stable-x86_64-pc-windows-msvc C:\Users\runneradmin\.rustup\toolchains\stable-x86_64-pc-windows-msvc.old
35
23 - name: Install Rust toolchain 36 - name: Install Rust toolchain
24 uses: actions-rs/toolchain@v1 37 uses: actions-rs/toolchain@v1
25 with: 38 with:
@@ -28,7 +41,19 @@ jobs:
28 override: true 41 override: true
29 components: rustfmt, rust-src 42 components: rustfmt, rust-src
30 43
31 - name: Cargo target cache 44 - name: Cache cargo registry
45 uses: actions/cache@v1
46 with:
47 path: ~/.cargo/registry
48 key: ${{ runner.os }}-cargo-registry-${{ hashFiles('**/Cargo.lock') }}
49
50 - name: Cache cargo index
51 uses: actions/cache@v1
52 with:
53 path: ~/.cargo/git
54 key: ${{ runner.os }}-cargo-index-${{ hashFiles('**/Cargo.lock') }}
55
56 - name: Cache cargo target dir
32 uses: actions/cache@v1 57 uses: actions/cache@v1
33 with: 58 with:
34 path: target 59 path: target
@@ -45,12 +70,13 @@ jobs:
45 with: 70 with:
46 command: test 71 command: test
47 72
48 - name: Prepare build directory for cache 73 - name: Prepare cache
49 run: | 74 run: cargo xtask pre-cache
50 find ./target/debug -maxdepth 1 -type f -delete \ 75
51 && rm -fr ./target/debug/{deps,.fingerprint}/{*ra_*,*heavy_test*,*gen_lsp*,*thread_worker*} \ 76 - name: Prepare cache 2
52 && rm -f ./target/.rustc_info.json \ 77 if: matrix.os == 'windows-latest'
53 && rm ./target/.slow_tests_cookie 78 run: Remove-Item ./target/debug/xtask.exe
79
54 80
55 type-script: 81 type-script:
56 name: TypeScript 82 name: TypeScript
diff --git a/Cargo.lock b/Cargo.lock
index 65120c362..c570e0c3c 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -25,9 +25,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
25 25
26[[package]] 26[[package]]
27name = "atty" 27name = "atty"
28version = "0.2.13" 28version = "0.2.14"
29source = "registry+https://github.com/rust-lang/crates.io-index" 29source = "registry+https://github.com/rust-lang/crates.io-index"
30dependencies = [ 30dependencies = [
31 "hermit-abi 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
31 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 32 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
32 "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", 33 "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
33] 34]
@@ -53,20 +54,12 @@ name = "backtrace-sys"
53version = "0.1.32" 54version = "0.1.32"
54source = "registry+https://github.com/rust-lang/crates.io-index" 55source = "registry+https://github.com/rust-lang/crates.io-index"
55dependencies = [ 56dependencies = [
56 "cc 1.0.48 (registry+https://github.com/rust-lang/crates.io-index)", 57 "cc 1.0.49 (registry+https://github.com/rust-lang/crates.io-index)",
57 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 58 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
58] 59]
59 60
60[[package]] 61[[package]]
61name = "base64" 62name = "base64"
62version = "0.10.1"
63source = "registry+https://github.com/rust-lang/crates.io-index"
64dependencies = [
65 "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
66]
67
68[[package]]
69name = "base64"
70version = "0.11.0" 63version = "0.11.0"
71source = "registry+https://github.com/rust-lang/crates.io-index" 64source = "registry+https://github.com/rust-lang/crates.io-index"
72 65
@@ -122,7 +115,7 @@ dependencies = [
122 115
123[[package]] 116[[package]]
124name = "cc" 117name = "cc"
125version = "1.0.48" 118version = "1.0.49"
126source = "registry+https://github.com/rust-lang/crates.io-index" 119source = "registry+https://github.com/rust-lang/crates.io-index"
127 120
128[[package]] 121[[package]]
@@ -137,7 +130,7 @@ source = "git+https://github.com/rust-lang/chalk.git?rev=ff65b5ac9860f3c36bd892c
137dependencies = [ 130dependencies = [
138 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 131 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
139 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 132 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
140 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 133 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
141] 134]
142 135
143[[package]] 136[[package]]
@@ -200,7 +193,7 @@ name = "clicolors-control"
200version = "1.0.1" 193version = "1.0.1"
201source = "registry+https://github.com/rust-lang/crates.io-index" 194source = "registry+https://github.com/rust-lang/crates.io-index"
202dependencies = [ 195dependencies = [
203 "atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)", 196 "atty 0.2.14 (registry+https://github.com/rust-lang/crates.io-index)",
204 "lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 197 "lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
205 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 198 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
206 "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", 199 "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -409,12 +402,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
409 402
410[[package]] 403[[package]]
411name = "getrandom" 404name = "getrandom"
412version = "0.1.13" 405version = "0.1.14"
413source = "registry+https://github.com/rust-lang/crates.io-index" 406source = "registry+https://github.com/rust-lang/crates.io-index"
414dependencies = [ 407dependencies = [
415 "cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)", 408 "cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)",
416 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 409 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
417 "wasi 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 410 "wasi 0.9.0+wasi-snapshot-preview1 (registry+https://github.com/rust-lang/crates.io-index)",
418] 411]
419 412
420[[package]] 413[[package]]
@@ -439,7 +432,7 @@ dependencies = [
439 432
440[[package]] 433[[package]]
441name = "hermit-abi" 434name = "hermit-abi"
442version = "0.1.5" 435version = "0.1.6"
443source = "registry+https://github.com/rust-lang/crates.io-index" 436source = "registry+https://github.com/rust-lang/crates.io-index"
444dependencies = [ 437dependencies = [
445 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 438 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -450,7 +443,7 @@ name = "humantime"
450version = "1.3.0" 443version = "1.3.0"
451source = "registry+https://github.com/rust-lang/crates.io-index" 444source = "registry+https://github.com/rust-lang/crates.io-index"
452dependencies = [ 445dependencies = [
453 "quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 446 "quick-error 1.2.3 (registry+https://github.com/rust-lang/crates.io-index)",
454] 447]
455 448
456[[package]] 449[[package]]
@@ -473,7 +466,7 @@ dependencies = [
473 466
474[[package]] 467[[package]]
475name = "inotify" 468name = "inotify"
476version = "0.6.1" 469version = "0.7.0"
477source = "registry+https://github.com/rust-lang/crates.io-index" 470source = "registry+https://github.com/rust-lang/crates.io-index"
478dependencies = [ 471dependencies = [
479 "bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 472 "bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -539,7 +532,7 @@ name = "jemalloc-sys"
539version = "0.3.2" 532version = "0.3.2"
540source = "registry+https://github.com/rust-lang/crates.io-index" 533source = "registry+https://github.com/rust-lang/crates.io-index"
541dependencies = [ 534dependencies = [
542 "cc 1.0.48 (registry+https://github.com/rust-lang/crates.io-index)", 535 "cc 1.0.49 (registry+https://github.com/rust-lang/crates.io-index)",
543 "fs_extra 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 536 "fs_extra 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
544 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 537 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
545] 538]
@@ -599,7 +592,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
599 592
600[[package]] 593[[package]]
601name = "lock_api" 594name = "lock_api"
602version = "0.3.2" 595version = "0.3.3"
603source = "registry+https://github.com/rust-lang/crates.io-index" 596source = "registry+https://github.com/rust-lang/crates.io-index"
604dependencies = [ 597dependencies = [
605 "scopeguard 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 598 "scopeguard 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -626,7 +619,7 @@ dependencies = [
626 619
627[[package]] 620[[package]]
628name = "lsp-types" 621name = "lsp-types"
629version = "0.68.0" 622version = "0.68.1"
630source = "registry+https://github.com/rust-lang/crates.io-index" 623source = "registry+https://github.com/rust-lang/crates.io-index"
631dependencies = [ 624dependencies = [
632 "base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", 625 "base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -707,15 +700,14 @@ dependencies = [
707 700
708[[package]] 701[[package]]
709name = "notify" 702name = "notify"
710version = "4.0.14" 703version = "4.0.15"
711source = "registry+https://github.com/rust-lang/crates.io-index" 704source = "registry+https://github.com/rust-lang/crates.io-index"
712dependencies = [ 705dependencies = [
713 "bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 706 "bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
714 "filetime 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)", 707 "filetime 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)",
715 "fsevent 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 708 "fsevent 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
716 "fsevent-sys 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 709 "fsevent-sys 2.0.1 (registry+https://github.com/rust-lang/crates.io-index)",
717 "inotify 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)", 710 "inotify 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
718 "kernel32-sys 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
719 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 711 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
720 "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)", 712 "mio 0.6.21 (registry+https://github.com/rust-lang/crates.io-index)",
721 "mio-extras 2.0.6 (registry+https://github.com/rust-lang/crates.io-index)", 713 "mio-extras 2.0.6 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -736,7 +728,7 @@ name = "num_cpus"
736version = "1.11.1" 728version = "1.11.1"
737source = "registry+https://github.com/rust-lang/crates.io-index" 729source = "registry+https://github.com/rust-lang/crates.io-index"
738dependencies = [ 730dependencies = [
739 "hermit-abi 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 731 "hermit-abi 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
740 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 732 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
741] 733]
742 734
@@ -755,7 +747,7 @@ name = "parking_lot"
755version = "0.10.0" 747version = "0.10.0"
756source = "registry+https://github.com/rust-lang/crates.io-index" 748source = "registry+https://github.com/rust-lang/crates.io-index"
757dependencies = [ 749dependencies = [
758 "lock_api 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 750 "lock_api 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
759 "parking_lot_core 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 751 "parking_lot_core 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
760] 752]
761 753
@@ -789,7 +781,7 @@ dependencies = [
789 "proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)", 781 "proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)",
790 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 782 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
791 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 783 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
792 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 784 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
793] 785]
794 786
795[[package]] 787[[package]]
@@ -808,7 +800,7 @@ dependencies = [
808 800
809[[package]] 801[[package]]
810name = "pico-args" 802name = "pico-args"
811version = "0.3.0" 803version = "0.3.1"
812source = "registry+https://github.com/rust-lang/crates.io-index" 804source = "registry+https://github.com/rust-lang/crates.io-index"
813 805
814[[package]] 806[[package]]
@@ -823,7 +815,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
823dependencies = [ 815dependencies = [
824 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 816 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
825 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 817 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
826 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 818 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
827] 819]
828 820
829[[package]] 821[[package]]
@@ -844,7 +836,7 @@ dependencies = [
844 "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)", 836 "byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
845 "lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 837 "lazy_static 1.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
846 "num-traits 0.2.10 (registry+https://github.com/rust-lang/crates.io-index)", 838 "num-traits 0.2.10 (registry+https://github.com/rust-lang/crates.io-index)",
847 "quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 839 "quick-error 1.2.3 (registry+https://github.com/rust-lang/crates.io-index)",
848 "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)", 840 "rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
849 "rand_chacha 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 841 "rand_chacha 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
850 "rand_xorshift 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 842 "rand_xorshift 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -853,7 +845,7 @@ dependencies = [
853 845
854[[package]] 846[[package]]
855name = "quick-error" 847name = "quick-error"
856version = "1.2.2" 848version = "1.2.3"
857source = "registry+https://github.com/rust-lang/crates.io-index" 849source = "registry+https://github.com/rust-lang/crates.io-index"
858 850
859[[package]] 851[[package]]
@@ -907,7 +899,7 @@ dependencies = [
907 "insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)", 899 "insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)",
908 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 900 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
909 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", 901 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
910 "lsp-types 0.68.0 (registry+https://github.com/rust-lang/crates.io-index)", 902 "lsp-types 0.68.1 (registry+https://github.com/rust-lang/crates.io-index)",
911 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", 903 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)",
912 "serde_json 1.0.44 (registry+https://github.com/rust-lang/crates.io-index)", 904 "serde_json 1.0.44 (registry+https://github.com/rust-lang/crates.io-index)",
913] 905]
@@ -927,7 +919,7 @@ name = "ra_cli"
927version = "0.1.0" 919version = "0.1.0"
928dependencies = [ 920dependencies = [
929 "env_logger 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", 921 "env_logger 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
930 "pico-args 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 922 "pico-args 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
931 "ra_batch 0.1.0", 923 "ra_batch 0.1.0",
932 "ra_db 0.1.0", 924 "ra_db 0.1.0",
933 "ra_hir 0.1.0", 925 "ra_hir 0.1.0",
@@ -1040,6 +1032,7 @@ dependencies = [
1040 "either 1.5.3 (registry+https://github.com/rust-lang/crates.io-index)", 1032 "either 1.5.3 (registry+https://github.com/rust-lang/crates.io-index)",
1041 "format-buf 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 1033 "format-buf 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
1042 "fst 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)", 1034 "fst 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)",
1035 "indexmap 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
1043 "insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)", 1036 "insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)",
1044 "itertools 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)", 1037 "itertools 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)",
1045 "join_to_string 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)", 1038 "join_to_string 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1071,7 +1064,7 @@ dependencies = [
1071 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1064 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
1072 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", 1065 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
1073 "lsp-server 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1066 "lsp-server 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
1074 "lsp-types 0.68.0 (registry+https://github.com/rust-lang/crates.io-index)", 1067 "lsp-types 0.68.1 (registry+https://github.com/rust-lang/crates.io-index)",
1075 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", 1068 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)",
1076 "ra_cargo_watch 0.1.0", 1069 "ra_cargo_watch 0.1.0",
1077 "ra_ide 0.1.0", 1070 "ra_ide 0.1.0",
@@ -1177,7 +1170,7 @@ dependencies = [
1177 "crossbeam-channel 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 1170 "crossbeam-channel 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
1178 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 1171 "jod-thread 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
1179 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", 1172 "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)",
1180 "notify 4.0.14 (registry+https://github.com/rust-lang/crates.io-index)", 1173 "notify 4.0.15 (registry+https://github.com/rust-lang/crates.io-index)",
1181 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)", 1174 "parking_lot 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)",
1182 "relative-path 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)", 1175 "relative-path 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
1183 "rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", 1176 "rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1215,7 +1208,7 @@ name = "rand"
1215version = "0.7.2" 1208version = "0.7.2"
1216source = "registry+https://github.com/rust-lang/crates.io-index" 1209source = "registry+https://github.com/rust-lang/crates.io-index"
1217dependencies = [ 1210dependencies = [
1218 "getrandom 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)", 1211 "getrandom 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
1219 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)", 1212 "libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)",
1220 "rand_chacha 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 1213 "rand_chacha 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
1221 "rand_core 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)", 1214 "rand_core 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1259,7 +1252,7 @@ name = "rand_core"
1259version = "0.5.1" 1252version = "0.5.1"
1260source = "registry+https://github.com/rust-lang/crates.io-index" 1253source = "registry+https://github.com/rust-lang/crates.io-index"
1261dependencies = [ 1254dependencies = [
1262 "getrandom 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)", 1255 "getrandom 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
1263] 1256]
1264 1257
1265[[package]] 1258[[package]]
@@ -1399,16 +1392,6 @@ dependencies = [
1399] 1392]
1400 1393
1401[[package]] 1394[[package]]
1402name = "ron"
1403version = "0.5.1"
1404source = "registry+https://github.com/rust-lang/crates.io-index"
1405dependencies = [
1406 "base64 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)",
1407 "bitflags 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
1408 "serde 1.0.104 (registry+https://github.com/rust-lang/crates.io-index)",
1409]
1410
1411[[package]]
1412name = "rowan" 1395name = "rowan"
1413version = "0.8.2" 1396version = "0.8.2"
1414source = "registry+https://github.com/rust-lang/crates.io-index" 1397source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -1476,7 +1459,7 @@ dependencies = [
1476 "heck 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)", 1459 "heck 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
1477 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 1460 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
1478 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1461 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
1479 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 1462 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
1480] 1463]
1481 1464
1482[[package]] 1465[[package]]
@@ -1521,7 +1504,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
1521dependencies = [ 1504dependencies = [
1522 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 1505 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
1523 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1506 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
1524 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 1507 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
1525] 1508]
1526 1509
1527[[package]] 1510[[package]]
@@ -1541,7 +1524,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
1541dependencies = [ 1524dependencies = [
1542 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 1525 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
1543 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1526 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
1544 "syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)", 1527 "syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)",
1545] 1528]
1546 1529
1547[[package]] 1530[[package]]
@@ -1580,7 +1563,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
1580 1563
1581[[package]] 1564[[package]]
1582name = "syn" 1565name = "syn"
1583version = "1.0.12" 1566version = "1.0.13"
1584source = "registry+https://github.com/rust-lang/crates.io-index" 1567source = "registry+https://github.com/rust-lang/crates.io-index"
1585dependencies = [ 1568dependencies = [
1586 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 1569 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
@@ -1715,7 +1698,7 @@ dependencies = [
1715 1698
1716[[package]] 1699[[package]]
1717name = "wasi" 1700name = "wasi"
1718version = "0.7.0" 1701version = "0.9.0+wasi-snapshot-preview1"
1719source = "registry+https://github.com/rust-lang/crates.io-index" 1702source = "registry+https://github.com/rust-lang/crates.io-index"
1720 1703
1721[[package]] 1704[[package]]
@@ -1769,11 +1752,9 @@ name = "xtask"
1769version = "0.1.0" 1752version = "0.1.0"
1770dependencies = [ 1753dependencies = [
1771 "anyhow 1.0.26 (registry+https://github.com/rust-lang/crates.io-index)", 1754 "anyhow 1.0.26 (registry+https://github.com/rust-lang/crates.io-index)",
1772 "pico-args 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 1755 "pico-args 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
1773 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)", 1756 "proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)",
1774 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)", 1757 "quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
1775 "ron 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)",
1776 "serde 1.0.104 (registry+https://github.com/rust-lang/crates.io-index)",
1777 "walkdir 2.2.9 (registry+https://github.com/rust-lang/crates.io-index)", 1758 "walkdir 2.2.9 (registry+https://github.com/rust-lang/crates.io-index)",
1778] 1759]
1779 1760
@@ -1790,11 +1771,10 @@ dependencies = [
1790"checksum anyhow 1.0.26 (registry+https://github.com/rust-lang/crates.io-index)" = "7825f6833612eb2414095684fcf6c635becf3ce97fe48cf6421321e93bfbd53c" 1771"checksum anyhow 1.0.26 (registry+https://github.com/rust-lang/crates.io-index)" = "7825f6833612eb2414095684fcf6c635becf3ce97fe48cf6421321e93bfbd53c"
1791"checksum anymap 0.12.1 (registry+https://github.com/rust-lang/crates.io-index)" = "33954243bd79057c2de7338850b85983a44588021f8a5fee574a8888c6de4344" 1772"checksum anymap 0.12.1 (registry+https://github.com/rust-lang/crates.io-index)" = "33954243bd79057c2de7338850b85983a44588021f8a5fee574a8888c6de4344"
1792"checksum arrayvec 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cff77d8686867eceff3105329d4698d96c2391c176d5d03adc90c7389162b5b8" 1773"checksum arrayvec 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "cff77d8686867eceff3105329d4698d96c2391c176d5d03adc90c7389162b5b8"
1793"checksum atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)" = "1803c647a3ec87095e7ae7acfca019e98de5ec9a7d01343f611cf3152ed71a90" 1774"checksum atty 0.2.14 (registry+https://github.com/rust-lang/crates.io-index)" = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8"
1794"checksum autocfg 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "1d49d90015b3c36167a20fe2810c5cd875ad504b39cff3d4eae7977e6b7c1cb2" 1775"checksum autocfg 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "1d49d90015b3c36167a20fe2810c5cd875ad504b39cff3d4eae7977e6b7c1cb2"
1795"checksum backtrace 0.3.40 (registry+https://github.com/rust-lang/crates.io-index)" = "924c76597f0d9ca25d762c25a4d369d51267536465dc5064bdf0eb073ed477ea" 1776"checksum backtrace 0.3.40 (registry+https://github.com/rust-lang/crates.io-index)" = "924c76597f0d9ca25d762c25a4d369d51267536465dc5064bdf0eb073ed477ea"
1796"checksum backtrace-sys 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)" = "5d6575f128516de27e3ce99689419835fce9643a9b215a14d2b5b685be018491" 1777"checksum backtrace-sys 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)" = "5d6575f128516de27e3ce99689419835fce9643a9b215a14d2b5b685be018491"
1797"checksum base64 0.10.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0b25d992356d2eb0ed82172f5248873db5560c4721f564b13cb5193bda5e668e"
1798"checksum base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b41b7ea54a0c9d92199de89e20e58d49f02f8e699814ef3fdf266f6f748d15c7" 1778"checksum base64 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b41b7ea54a0c9d92199de89e20e58d49f02f8e699814ef3fdf266f6f748d15c7"
1799"checksum bit-set 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e84c238982c4b1e1ee668d136c510c67a13465279c0cb367ea6baf6310620a80" 1779"checksum bit-set 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "e84c238982c4b1e1ee668d136c510c67a13465279c0cb367ea6baf6310620a80"
1800"checksum bit-vec 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "f59bbe95d4e52a6398ec21238d31577f2b28a9d86807f06ca59d191d8440d0bb" 1780"checksum bit-vec 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "f59bbe95d4e52a6398ec21238d31577f2b28a9d86807f06ca59d191d8440d0bb"
@@ -1803,7 +1783,7 @@ dependencies = [
1803"checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5" 1783"checksum byteorder 1.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "a7c3dd8985a7111efc5c80b44e23ecdd8c007de8ade3b96595387e812b957cf5"
1804"checksum c2-chacha 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "214238caa1bf3a496ec3392968969cab8549f96ff30652c9e56885329315f6bb" 1784"checksum c2-chacha 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "214238caa1bf3a496ec3392968969cab8549f96ff30652c9e56885329315f6bb"
1805"checksum cargo_metadata 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "46e3374c604fb39d1a2f35ed5e4a4e30e60d01fab49446e08f1b3e9a90aef202" 1785"checksum cargo_metadata 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "46e3374c604fb39d1a2f35ed5e4a4e30e60d01fab49446e08f1b3e9a90aef202"
1806"checksum cc 1.0.48 (registry+https://github.com/rust-lang/crates.io-index)" = "f52a465a666ca3d838ebbf08b241383421412fe7ebb463527bba275526d89f76" 1786"checksum cc 1.0.49 (registry+https://github.com/rust-lang/crates.io-index)" = "e450b8da92aa6f274e7c6437692f9f2ce6d701fb73bacfcf87897b3f89a4c20e"
1807"checksum cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)" = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" 1787"checksum cfg-if 0.1.10 (registry+https://github.com/rust-lang/crates.io-index)" = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
1808"checksum chalk-derive 0.1.0 (git+https://github.com/rust-lang/chalk.git?rev=ff65b5ac9860f3c36bd892c865ab23d5ff0bbae5)" = "<none>" 1788"checksum chalk-derive 0.1.0 (git+https://github.com/rust-lang/chalk.git?rev=ff65b5ac9860f3c36bd892c865ab23d5ff0bbae5)" = "<none>"
1809"checksum chalk-engine 0.9.0 (git+https://github.com/rust-lang/chalk.git?rev=ff65b5ac9860f3c36bd892c865ab23d5ff0bbae5)" = "<none>" 1789"checksum chalk-engine 0.9.0 (git+https://github.com/rust-lang/chalk.git?rev=ff65b5ac9860f3c36bd892c865ab23d5ff0bbae5)" = "<none>"
@@ -1838,14 +1818,14 @@ dependencies = [
1838"checksum fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" 1818"checksum fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba"
1839"checksum fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" 1819"checksum fuchsia-zircon 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82"
1840"checksum fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" 1820"checksum fuchsia-zircon-sys 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7"
1841"checksum getrandom 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)" = "e7db7ca94ed4cd01190ceee0d8a8052f08a247aa1b469a7f68c6a3b71afcf407" 1821"checksum getrandom 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)" = "7abc8dd8451921606d809ba32e95b6111925cd2906060d2dcc29c070220503eb"
1842"checksum globset 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "925aa2cac82d8834e2b2a4415b6f6879757fb5c0928fc445ae76461a12eed8f2" 1822"checksum globset 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)" = "925aa2cac82d8834e2b2a4415b6f6879757fb5c0928fc445ae76461a12eed8f2"
1843"checksum heck 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "20564e78d53d2bb135c343b3f47714a56af2061f1c928fdb541dc7b9fdd94205" 1823"checksum heck 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "20564e78d53d2bb135c343b3f47714a56af2061f1c928fdb541dc7b9fdd94205"
1844"checksum hermit-abi 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "f629dc602392d3ec14bfc8a09b5e644d7ffd725102b48b81e59f90f2633621d7" 1824"checksum hermit-abi 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "eff2656d88f158ce120947499e971d743c05dbcbed62e5bd2f38f1698bbc3772"
1845"checksum humantime 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "df004cfca50ef23c36850aaaa59ad52cc70d0e90243c3c7737a4dd32dc7a3c4f" 1825"checksum humantime 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "df004cfca50ef23c36850aaaa59ad52cc70d0e90243c3c7737a4dd32dc7a3c4f"
1846"checksum idna 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "02e2673c30ee86b5b96a9cb52ad15718aa1f966f5ab9ad54a8b95d5ca33120a9" 1826"checksum idna 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "02e2673c30ee86b5b96a9cb52ad15718aa1f966f5ab9ad54a8b95d5ca33120a9"
1847"checksum indexmap 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712d7b3ea5827fcb9d4fda14bf4da5f136f0db2ae9c8f4bd4e2d1c6fde4e6db2" 1827"checksum indexmap 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712d7b3ea5827fcb9d4fda14bf4da5f136f0db2ae9c8f4bd4e2d1c6fde4e6db2"
1848"checksum inotify 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)" = "40b54539f3910d6f84fbf9a643efd6e3aa6e4f001426c0329576128255994718" 1828"checksum inotify 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "24e40d6fd5d64e2082e0c796495c8ef5ad667a96d03e5aaa0becfd9d47bcbfb8"
1849"checksum inotify-sys 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "e74a1aa87c59aeff6ef2cc2fa62d41bc43f54952f55652656b18a02fd5e356c0" 1829"checksum inotify-sys 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "e74a1aa87c59aeff6ef2cc2fa62d41bc43f54952f55652656b18a02fd5e356c0"
1850"checksum insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d499dc062e841590a67230d853bce62d0abeb91304927871670b7c55c461349" 1830"checksum insta 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)" = "0d499dc062e841590a67230d853bce62d0abeb91304927871670b7c55c461349"
1851"checksum iovec 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e" 1831"checksum iovec 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e"
@@ -1862,10 +1842,10 @@ dependencies = [
1862"checksum lazycell 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b294d6fa9ee409a054354afc4352b0b9ef7ca222c69b8812cbea9e7d2bf3783f" 1842"checksum lazycell 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b294d6fa9ee409a054354afc4352b0b9ef7ca222c69b8812cbea9e7d2bf3783f"
1863"checksum libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)" = "d515b1f41455adea1313a4a2ac8a8a477634fbae63cc6100e3aebb207ce61558" 1843"checksum libc 0.2.66 (registry+https://github.com/rust-lang/crates.io-index)" = "d515b1f41455adea1313a4a2ac8a8a477634fbae63cc6100e3aebb207ce61558"
1864"checksum linked-hash-map 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "ae91b68aebc4ddb91978b11a1b02ddd8602a05ec19002801c5666000e05e0f83" 1844"checksum linked-hash-map 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "ae91b68aebc4ddb91978b11a1b02ddd8602a05ec19002801c5666000e05e0f83"
1865"checksum lock_api 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e57b3997725d2b60dbec1297f6c2e2957cc383db1cebd6be812163f969c7d586" 1845"checksum lock_api 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "79b2de95ecb4691949fea4716ca53cdbcfccb2c612e19644a8bad05edcf9f47b"
1866"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7" 1846"checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7"
1867"checksum lsp-server 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "5383e043329615624bbf45e1ba27bd75c176762b2592855c659bc28ac580a06b" 1847"checksum lsp-server 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "5383e043329615624bbf45e1ba27bd75c176762b2592855c659bc28ac580a06b"
1868"checksum lsp-types 0.68.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1b08121a463f43ee67f09da45c0a61d447793adc8dc23e52b009e8cf80278a16" 1848"checksum lsp-types 0.68.1 (registry+https://github.com/rust-lang/crates.io-index)" = "19b79f72914b929daa263483134b8974962cdebc731593b11508afb7f9acec80"
1869"checksum matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08" 1849"checksum matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08"
1870"checksum memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88579771288728879b57485cc7d6b07d648c9f0141eb955f8ab7f9d45394468e" 1850"checksum memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88579771288728879b57485cc7d6b07d648c9f0141eb955f8ab7f9d45394468e"
1871"checksum memoffset 0.5.3 (registry+https://github.com/rust-lang/crates.io-index)" = "75189eb85871ea5c2e2c15abbdd541185f63b408415e5051f5cac122d8c774b9" 1851"checksum memoffset 0.5.3 (registry+https://github.com/rust-lang/crates.io-index)" = "75189eb85871ea5c2e2c15abbdd541185f63b408415e5051f5cac122d8c774b9"
@@ -1873,7 +1853,7 @@ dependencies = [
1873"checksum mio-extras 2.0.6 (registry+https://github.com/rust-lang/crates.io-index)" = "52403fe290012ce777c4626790c8951324a2b9e3316b3143779c72b029742f19" 1853"checksum mio-extras 2.0.6 (registry+https://github.com/rust-lang/crates.io-index)" = "52403fe290012ce777c4626790c8951324a2b9e3316b3143779c72b029742f19"
1874"checksum miow 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "8c1f2f3b1cf331de6896aabf6e9d55dca90356cc9960cca7eaaf408a355ae919" 1854"checksum miow 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "8c1f2f3b1cf331de6896aabf6e9d55dca90356cc9960cca7eaaf408a355ae919"
1875"checksum net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)" = "42550d9fb7b6684a6d404d9fa7250c2eb2646df731d1c06afc06dcee9e1bcf88" 1855"checksum net2 0.2.33 (registry+https://github.com/rust-lang/crates.io-index)" = "42550d9fb7b6684a6d404d9fa7250c2eb2646df731d1c06afc06dcee9e1bcf88"
1876"checksum notify 4.0.14 (registry+https://github.com/rust-lang/crates.io-index)" = "199628fc33b21bc767baa057490b00b382ecbae030803a7b36292422d15b778b" 1856"checksum notify 4.0.15 (registry+https://github.com/rust-lang/crates.io-index)" = "80ae4a7688d1fab81c5bf19c64fc8db920be8d519ce6336ed4e7efe024724dbd"
1877"checksum num-traits 0.2.10 (registry+https://github.com/rust-lang/crates.io-index)" = "d4c81ffc11c212fa327657cb19dd85eb7419e163b5b076bede2bdb5c974c07e4" 1857"checksum num-traits 0.2.10 (registry+https://github.com/rust-lang/crates.io-index)" = "d4c81ffc11c212fa327657cb19dd85eb7419e163b5b076bede2bdb5c974c07e4"
1878"checksum num_cpus 1.11.1 (registry+https://github.com/rust-lang/crates.io-index)" = "76dac5ed2a876980778b8b85f75a71b6cbf0db0b1232ee12f826bccb00d09d72" 1858"checksum num_cpus 1.11.1 (registry+https://github.com/rust-lang/crates.io-index)" = "76dac5ed2a876980778b8b85f75a71b6cbf0db0b1232ee12f826bccb00d09d72"
1879"checksum once_cell 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "891f486f630e5c5a4916c7e16c4b24a53e78c860b646e9f8e005e4f16847bfed" 1859"checksum once_cell 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "891f486f630e5c5a4916c7e16c4b24a53e78c860b646e9f8e005e4f16847bfed"
@@ -1884,12 +1864,12 @@ dependencies = [
1884"checksum paste-impl 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "4214c9e912ef61bf42b81ba9a47e8aad1b2ffaf739ab162bf96d1e011f54e6c5" 1864"checksum paste-impl 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "4214c9e912ef61bf42b81ba9a47e8aad1b2ffaf739ab162bf96d1e011f54e6c5"
1885"checksum percent-encoding 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e" 1865"checksum percent-encoding 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d4fd5641d01c8f18a23da7b6fe29298ff4b55afcccdf78973b24cf3175fee32e"
1886"checksum petgraph 0.4.13 (registry+https://github.com/rust-lang/crates.io-index)" = "9c3659d1ee90221741f65dd128d9998311b0e40c5d3c23a62445938214abce4f" 1866"checksum petgraph 0.4.13 (registry+https://github.com/rust-lang/crates.io-index)" = "9c3659d1ee90221741f65dd128d9998311b0e40c5d3c23a62445938214abce4f"
1887"checksum pico-args 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "22e32b0f3771287ebb436130477eabf0f11f934ed036099ad548bc885e708667" 1867"checksum pico-args 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "3ad1f1b834a05d42dae330066e9699a173b28185b3bdc3dbf14ca239585de8cc"
1888"checksum ppv-lite86 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)" = "74490b50b9fbe561ac330df47c08f3f33073d2d00c150f719147d7c54522fa1b" 1868"checksum ppv-lite86 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)" = "74490b50b9fbe561ac330df47c08f3f33073d2d00c150f719147d7c54522fa1b"
1889"checksum proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)" = "ecd45702f76d6d3c75a80564378ae228a85f0b59d2f3ed43c91b4a69eb2ebfc5" 1869"checksum proc-macro-hack 0.5.11 (registry+https://github.com/rust-lang/crates.io-index)" = "ecd45702f76d6d3c75a80564378ae228a85f0b59d2f3ed43c91b4a69eb2ebfc5"
1890"checksum proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)" = "0319972dcae462681daf4da1adeeaa066e3ebd29c69be96c6abb1259d2ee2bcc" 1870"checksum proc-macro2 1.0.7 (registry+https://github.com/rust-lang/crates.io-index)" = "0319972dcae462681daf4da1adeeaa066e3ebd29c69be96c6abb1259d2ee2bcc"
1891"checksum proptest 0.9.4 (registry+https://github.com/rust-lang/crates.io-index)" = "cf147e022eacf0c8a054ab864914a7602618adba841d800a9a9868a5237a529f" 1871"checksum proptest 0.9.4 (registry+https://github.com/rust-lang/crates.io-index)" = "cf147e022eacf0c8a054ab864914a7602618adba841d800a9a9868a5237a529f"
1892"checksum quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "9274b940887ce9addde99c4eee6b5c44cc494b182b97e73dc8ffdcb3397fd3f0" 1872"checksum quick-error 1.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "a1d01941d82fa2ab50be1e79e6714289dd7cde78eba4c074bc5a4374f650dfe0"
1893"checksum quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "053a8c8bcc71fcce321828dc897a98ab9760bef03a4fc36693c231e5b3216cfe" 1873"checksum quote 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)" = "053a8c8bcc71fcce321828dc897a98ab9760bef03a4fc36693c231e5b3216cfe"
1894"checksum ra_vfs 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "bc898f237e4b4498959ae0100c688793a23e77624d44ef710ba70094217f98e0" 1874"checksum ra_vfs 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "bc898f237e4b4498959ae0100c688793a23e77624d44ef710ba70094217f98e0"
1895"checksum rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "6d71dacdc3c88c1fde3885a3be3fbab9f35724e6ce99467f7d9c5026132184ca" 1875"checksum rand 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "6d71dacdc3c88c1fde3885a3be3fbab9f35724e6ce99467f7d9c5026132184ca"
@@ -1915,7 +1895,6 @@ dependencies = [
1915"checksum regex-syntax 0.6.12 (registry+https://github.com/rust-lang/crates.io-index)" = "11a7e20d1cce64ef2fed88b66d347f88bd9babb82845b2b858f3edbf59a4f716" 1895"checksum regex-syntax 0.6.12 (registry+https://github.com/rust-lang/crates.io-index)" = "11a7e20d1cce64ef2fed88b66d347f88bd9babb82845b2b858f3edbf59a4f716"
1916"checksum relative-path 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bedde000f40f2921ce439ea165c9c53fd629bfa115140c72e22aceacb4a21954" 1896"checksum relative-path 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bedde000f40f2921ce439ea165c9c53fd629bfa115140c72e22aceacb4a21954"
1917"checksum remove_dir_all 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4a83fa3702a688b9359eccba92d153ac33fd2e8462f9e0e3fdf155239ea7792e" 1897"checksum remove_dir_all 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4a83fa3702a688b9359eccba92d153ac33fd2e8462f9e0e3fdf155239ea7792e"
1918"checksum ron 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2ece421e0c4129b90e4a35b6f625e472e96c552136f5093a2f4fa2bbb75a62d5"
1919"checksum rowan 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "3eb10a10a48f0f809a217bcf074b85a03dcf79831bae80e7f1a043d0897463e2" 1898"checksum rowan 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "3eb10a10a48f0f809a217bcf074b85a03dcf79831bae80e7f1a043d0897463e2"
1920"checksum rustc-demangle 0.1.16 (registry+https://github.com/rust-lang/crates.io-index)" = "4c691c0e608126e00913e33f0ccf3727d5fc84573623b8d65b2df340b5201783" 1899"checksum rustc-demangle 0.1.16 (registry+https://github.com/rust-lang/crates.io-index)" = "4c691c0e608126e00913e33f0ccf3727d5fc84573623b8d65b2df340b5201783"
1921"checksum rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7540fc8b0c49f096ee9c961cda096467dce8084bec6bdca2fc83895fd9b28cb8" 1900"checksum rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7540fc8b0c49f096ee9c961cda096467dce8084bec6bdca2fc83895fd9b28cb8"
@@ -1937,7 +1916,7 @@ dependencies = [
1937"checksum smallvec 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "44e59e0c9fa00817912ae6e4e6e3c4fe04455e75699d06eedc7d85917ed8e8f4" 1916"checksum smallvec 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "44e59e0c9fa00817912ae6e4e6e3c4fe04455e75699d06eedc7d85917ed8e8f4"
1938"checksum smol_str 0.1.15 (registry+https://github.com/rust-lang/crates.io-index)" = "34836c9a295c62c2ce3514471117c5cb269891e8421b2aafdd910050576c4d8b" 1917"checksum smol_str 0.1.15 (registry+https://github.com/rust-lang/crates.io-index)" = "34836c9a295c62c2ce3514471117c5cb269891e8421b2aafdd910050576c4d8b"
1939"checksum superslice 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ab16ced94dbd8a46c82fd81e3ed9a8727dac2977ea869d217bcc4ea1f122e81f" 1918"checksum superslice 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ab16ced94dbd8a46c82fd81e3ed9a8727dac2977ea869d217bcc4ea1f122e81f"
1940"checksum syn 1.0.12 (registry+https://github.com/rust-lang/crates.io-index)" = "ddc157159e2a7df58cd67b1cace10b8ed256a404fb0070593f137d8ba6bef4de" 1919"checksum syn 1.0.13 (registry+https://github.com/rust-lang/crates.io-index)" = "1e4ff033220a41d1a57d8125eab57bf5263783dfdcc18688b1dacc6ce9651ef8"
1941"checksum tempfile 3.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6e24d9338a0a5be79593e2fa15a648add6138caa803e2d5bc782c371732ca9" 1920"checksum tempfile 3.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7a6e24d9338a0a5be79593e2fa15a648add6138caa803e2d5bc782c371732ca9"
1942"checksum termios 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "72b620c5ea021d75a735c943269bb07d30c9b77d6ac6b236bc8b5c496ef05625" 1921"checksum termios 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "72b620c5ea021d75a735c943269bb07d30c9b77d6ac6b236bc8b5c496ef05625"
1943"checksum text_unit 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "e08bbcb7a3adbda0eb23431206b653bdad3d8dea311e72d36bf2215e27a42579" 1922"checksum text_unit 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "e08bbcb7a3adbda0eb23431206b653bdad3d8dea311e72d36bf2215e27a42579"
@@ -1953,7 +1932,7 @@ dependencies = [
1953"checksum uuid 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "9fde2f6a4bea1d6e007c4ad38c6839fa71cbb63b6dbf5b595aa38dc9b1093c11" 1932"checksum uuid 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "9fde2f6a4bea1d6e007c4ad38c6839fa71cbb63b6dbf5b595aa38dc9b1093c11"
1954"checksum version_check 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "078775d0255232fb988e6fccf26ddc9d1ac274299aaedcedce21c6f72cc533ce" 1933"checksum version_check 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "078775d0255232fb988e6fccf26ddc9d1ac274299aaedcedce21c6f72cc533ce"
1955"checksum walkdir 2.2.9 (registry+https://github.com/rust-lang/crates.io-index)" = "9658c94fa8b940eab2250bd5a457f9c48b748420d71293b165c8cdbe2f55f71e" 1934"checksum walkdir 2.2.9 (registry+https://github.com/rust-lang/crates.io-index)" = "9658c94fa8b940eab2250bd5a457f9c48b748420d71293b165c8cdbe2f55f71e"
1956"checksum wasi 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b89c3ce4ce14bdc6fb6beaf9ec7928ca331de5df7e5ea278375642a2f478570d" 1935"checksum wasi 0.9.0+wasi-snapshot-preview1 (registry+https://github.com/rust-lang/crates.io-index)" = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519"
1957"checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" 1936"checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a"
1958"checksum winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)" = "8093091eeb260906a183e6ae1abdba2ef5ef2257a21801128899c3fc699229c6" 1937"checksum winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)" = "8093091eeb260906a183e6ae1abdba2ef5ef2257a21801128899c3fc699229c6"
1959"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" 1938"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
diff --git a/bors.toml b/bors.toml
index 7ffbc9294..0bc71860f 100644
--- a/bors.toml
+++ b/bors.toml
@@ -1,2 +1,7 @@
1status = ["Rust", "TypeScript"] 1status = [
2 "Rust (ubuntu-latest)",
3 "Rust (windows-latest)",
4 "Rust (macos-latest)",
5 "TypeScript"
6]
2delete_merged_branches = true 7delete_merged_branches = true
diff --git a/crates/ra_assists/src/assists/flip_binexpr.rs b/crates/ra_assists/src/assists/flip_binexpr.rs
index 386045eb0..2d91b2a7e 100644
--- a/crates/ra_assists/src/assists/flip_binexpr.rs
+++ b/crates/ra_assists/src/assists/flip_binexpr.rs
@@ -56,17 +56,7 @@ enum FlipAction {
56impl From<BinOp> for FlipAction { 56impl From<BinOp> for FlipAction {
57 fn from(op_kind: BinOp) -> Self { 57 fn from(op_kind: BinOp) -> Self {
58 match op_kind { 58 match op_kind {
59 BinOp::Assignment => FlipAction::DontFlip, 59 kind if kind.is_assignment() => FlipAction::DontFlip,
60 BinOp::AddAssign => FlipAction::DontFlip,
61 BinOp::DivAssign => FlipAction::DontFlip,
62 BinOp::MulAssign => FlipAction::DontFlip,
63 BinOp::RemAssign => FlipAction::DontFlip,
64 BinOp::ShrAssign => FlipAction::DontFlip,
65 BinOp::ShlAssign => FlipAction::DontFlip,
66 BinOp::SubAssign => FlipAction::DontFlip,
67 BinOp::BitOrAssign => FlipAction::DontFlip,
68 BinOp::BitAndAssign => FlipAction::DontFlip,
69 BinOp::BitXorAssign => FlipAction::DontFlip,
70 BinOp::GreaterTest => FlipAction::FlipAndReplaceOp("<"), 60 BinOp::GreaterTest => FlipAction::FlipAndReplaceOp("<"),
71 BinOp::GreaterEqualTest => FlipAction::FlipAndReplaceOp("<="), 61 BinOp::GreaterEqualTest => FlipAction::FlipAndReplaceOp("<="),
72 BinOp::LesserTest => FlipAction::FlipAndReplaceOp(">"), 62 BinOp::LesserTest => FlipAction::FlipAndReplaceOp(">"),
diff --git a/crates/ra_cargo_watch/src/conv/test.rs b/crates/ra_cargo_watch/src/conv/test.rs
index f77ef1b4d..6b86525b8 100644
--- a/crates/ra_cargo_watch/src/conv/test.rs
+++ b/crates/ra_cargo_watch/src/conv/test.rs
@@ -1,7 +1,9 @@
1//! This module contains the large and verbose snapshot tests for the 1//! This module contains the large and verbose snapshot tests for the
2//! conversions between `cargo check` json and LSP diagnostics. 2//! conversions between `cargo check` json and LSP diagnostics.
3#[cfg(not(windows))]
3use crate::*; 4use crate::*;
4 5
6#[cfg(not(windows))]
5fn parse_diagnostic(val: &str) -> cargo_metadata::diagnostic::Diagnostic { 7fn parse_diagnostic(val: &str) -> cargo_metadata::diagnostic::Diagnostic {
6 serde_json::from_str::<cargo_metadata::diagnostic::Diagnostic>(val).unwrap() 8 serde_json::from_str::<cargo_metadata::diagnostic::Diagnostic>(val).unwrap()
7} 9}
diff --git a/crates/ra_db/src/fixture.rs b/crates/ra_db/src/fixture.rs
index e8f335e33..30b598e9a 100644
--- a/crates/ra_db/src/fixture.rs
+++ b/crates/ra_db/src/fixture.rs
@@ -49,7 +49,7 @@ fn with_single_file(db: &mut dyn SourceDatabaseExt, text: &str) -> FileId {
49 let file_id = FileId(0); 49 let file_id = FileId(0);
50 let rel_path: RelativePathBuf = "/main.rs".into(); 50 let rel_path: RelativePathBuf = "/main.rs".into();
51 51
52 let mut source_root = SourceRoot::default(); 52 let mut source_root = SourceRoot::new_local();
53 source_root.insert_file(rel_path.clone(), file_id); 53 source_root.insert_file(rel_path.clone(), file_id);
54 54
55 let mut crate_graph = CrateGraph::default(); 55 let mut crate_graph = CrateGraph::default();
@@ -77,7 +77,7 @@ fn with_files(db: &mut dyn SourceDatabaseExt, fixture: &str) -> Option<FilePosit
77 let mut crate_deps = Vec::new(); 77 let mut crate_deps = Vec::new();
78 let mut default_crate_root: Option<FileId> = None; 78 let mut default_crate_root: Option<FileId> = None;
79 79
80 let mut source_root = SourceRoot::default(); 80 let mut source_root = SourceRoot::new_local();
81 let mut source_root_id = WORKSPACE; 81 let mut source_root_id = WORKSPACE;
82 let mut source_root_prefix: RelativePathBuf = "/".into(); 82 let mut source_root_prefix: RelativePathBuf = "/".into();
83 let mut file_id = FileId(0); 83 let mut file_id = FileId(0);
@@ -87,7 +87,7 @@ fn with_files(db: &mut dyn SourceDatabaseExt, fixture: &str) -> Option<FilePosit
87 for entry in fixture.iter() { 87 for entry in fixture.iter() {
88 let meta = match parse_meta(&entry.meta) { 88 let meta = match parse_meta(&entry.meta) {
89 ParsedMeta::Root { path } => { 89 ParsedMeta::Root { path } => {
90 let source_root = std::mem::replace(&mut source_root, SourceRoot::default()); 90 let source_root = std::mem::replace(&mut source_root, SourceRoot::new_local());
91 db.set_source_root(source_root_id, Arc::new(source_root)); 91 db.set_source_root(source_root_id, Arc::new(source_root));
92 source_root_id.0 += 1; 92 source_root_id.0 += 1;
93 source_root_prefix = path; 93 source_root_prefix = path;
diff --git a/crates/ra_db/src/input.rs b/crates/ra_db/src/input.rs
index 2a7ed20d1..07269237a 100644
--- a/crates/ra_db/src/input.rs
+++ b/crates/ra_db/src/input.rs
@@ -33,7 +33,7 @@ pub struct FileId(pub u32);
33#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, PartialOrd, Ord)] 33#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, PartialOrd, Ord)]
34pub struct SourceRootId(pub u32); 34pub struct SourceRootId(pub u32);
35 35
36#[derive(Default, Clone, Debug, PartialEq, Eq)] 36#[derive(Clone, Debug, PartialEq, Eq)]
37pub struct SourceRoot { 37pub struct SourceRoot {
38 /// Sysroot or crates.io library. 38 /// Sysroot or crates.io library.
39 /// 39 ///
@@ -44,11 +44,11 @@ pub struct SourceRoot {
44} 44}
45 45
46impl SourceRoot { 46impl SourceRoot {
47 pub fn new() -> SourceRoot { 47 pub fn new_local() -> SourceRoot {
48 Default::default() 48 SourceRoot { is_library: false, files: Default::default() }
49 } 49 }
50 pub fn new_library() -> SourceRoot { 50 pub fn new_library() -> SourceRoot {
51 SourceRoot { is_library: true, ..SourceRoot::new() } 51 SourceRoot { is_library: true, files: Default::default() }
52 } 52 }
53 pub fn insert_file(&mut self, path: RelativePathBuf, file_id: FileId) { 53 pub fn insert_file(&mut self, path: RelativePathBuf, file_id: FileId) {
54 self.files.insert(path, file_id); 54 self.files.insert(path, file_id);
diff --git a/crates/ra_hir/src/code_model.rs b/crates/ra_hir/src/code_model.rs
index 488f74cfb..cc42068a1 100644
--- a/crates/ra_hir/src/code_model.rs
+++ b/crates/ra_hir/src/code_model.rs
@@ -25,6 +25,7 @@ use hir_ty::{
25 TraitEnvironment, Ty, TyDefId, TypeCtor, TypeWalk, 25 TraitEnvironment, Ty, TyDefId, TypeCtor, TypeWalk,
26}; 26};
27use ra_db::{CrateId, Edition, FileId}; 27use ra_db::{CrateId, Edition, FileId};
28use ra_prof::profile;
28use ra_syntax::ast; 29use ra_syntax::ast;
29 30
30use crate::{ 31use crate::{
@@ -189,6 +190,7 @@ impl Module {
189 } 190 }
190 191
191 pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) { 192 pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
193 let _p = profile("Module::diagnostics");
192 db.crate_def_map(self.id.krate).add_diagnostics(db, self.id.local_id, sink); 194 db.crate_def_map(self.id.krate).add_diagnostics(db, self.id.local_id, sink);
193 for decl in self.declarations(db) { 195 for decl in self.declarations(db) {
194 match decl { 196 match decl {
@@ -507,6 +509,7 @@ impl Function {
507 } 509 }
508 510
509 pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) { 511 pub fn diagnostics(self, db: &impl HirDatabase, sink: &mut DiagnosticSink) {
512 let _p = profile("Function::diagnostics");
510 let infer = db.infer(self.id.into()); 513 let infer = db.infer(self.id.into());
511 infer.add_diagnostics(db, self.id, sink); 514 infer.add_diagnostics(db, self.id, sink);
512 let mut validator = ExprValidator::new(self.id, infer, sink); 515 let mut validator = ExprValidator::new(self.id, infer, sink);
diff --git a/crates/ra_hir/src/db.rs b/crates/ra_hir/src/db.rs
index f5ffd64fa..e6079b88d 100644
--- a/crates/ra_hir/src/db.rs
+++ b/crates/ra_hir/src/db.rs
@@ -1,21 +1,21 @@
1//! FIXME: write short doc here 1//! FIXME: write short doc here
2 2
3pub use hir_def::db::{ 3pub use hir_def::db::{
4 BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQuery, CrateLangItemsQuery, 4 BodyQuery, BodyWithSourceMapQuery, ComputeCrateDefMapQuery, ConstDataQuery,
5 DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery, ExprScopesQuery, 5 CrateLangItemsQuery, DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery,
6 FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase, InternDatabaseStorage, 6 ExprScopesQuery, FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase,
7 LangItemQuery, ModuleLangItemsQuery, RawItemsQuery, StaticDataQuery, StructDataQuery, 7 InternDatabaseStorage, LangItemQuery, ModuleLangItemsQuery, RawItemsQuery, StaticDataQuery,
8 TraitDataQuery, TypeAliasDataQuery, 8 StructDataQuery, TraitDataQuery, TypeAliasDataQuery,
9}; 9};
10pub use hir_expand::db::{ 10pub use hir_expand::db::{
11 AstDatabase, AstDatabaseStorage, AstIdMapQuery, MacroArgQuery, MacroDefQuery, MacroExpandQuery, 11 AstDatabase, AstDatabaseStorage, AstIdMapQuery, MacroArgQuery, MacroDefQuery, MacroExpandQuery,
12 ParseMacroQuery, 12 ParseMacroQuery,
13}; 13};
14pub use hir_ty::db::{ 14pub use hir_ty::db::{
15 AssociatedTyDataQuery, CallableItemSignatureQuery, FieldTypesQuery, GenericDefaultsQuery, 15 AssociatedTyDataQuery, CallableItemSignatureQuery, DoInferQuery, FieldTypesQuery,
16 GenericPredicatesQuery, HirDatabase, HirDatabaseStorage, ImplDatumQuery, ImplsForTraitQuery, 16 GenericDefaultsQuery, GenericPredicatesQuery, HirDatabase, HirDatabaseStorage, ImplDatumQuery,
17 ImplsInCrateQuery, InferQuery, StructDatumQuery, TraitDatumQuery, TraitSolveQuery, TyQuery, 17 ImplsForTraitQuery, ImplsInCrateQuery, StructDatumQuery, TraitDatumQuery, TraitSolveQuery,
18 ValueTyQuery, 18 TyQuery, ValueTyQuery,
19}; 19};
20 20
21#[test] 21#[test]
diff --git a/crates/ra_hir_def/src/db.rs b/crates/ra_hir_def/src/db.rs
index c55fd4111..da273eb11 100644
--- a/crates/ra_hir_def/src/db.rs
+++ b/crates/ra_hir_def/src/db.rs
@@ -3,6 +3,7 @@ use std::sync::Arc;
3 3
4use hir_expand::{db::AstDatabase, HirFileId}; 4use hir_expand::{db::AstDatabase, HirFileId};
5use ra_db::{salsa, CrateId, SourceDatabase}; 5use ra_db::{salsa, CrateId, SourceDatabase};
6use ra_prof::profile;
6use ra_syntax::SmolStr; 7use ra_syntax::SmolStr;
7 8
8use crate::{ 9use crate::{
@@ -46,9 +47,12 @@ pub trait DefDatabase: InternDatabase + AstDatabase {
46 #[salsa::invoke(RawItems::raw_items_query)] 47 #[salsa::invoke(RawItems::raw_items_query)]
47 fn raw_items(&self, file_id: HirFileId) -> Arc<RawItems>; 48 fn raw_items(&self, file_id: HirFileId) -> Arc<RawItems>;
48 49
49 #[salsa::invoke(CrateDefMap::crate_def_map_query)] 50 #[salsa::transparent]
50 fn crate_def_map(&self, krate: CrateId) -> Arc<CrateDefMap>; 51 fn crate_def_map(&self, krate: CrateId) -> Arc<CrateDefMap>;
51 52
53 #[salsa::invoke(CrateDefMap::compute_crate_def_map_query)]
54 fn compute_crate_def_map(&self, krate: CrateId) -> Arc<CrateDefMap>;
55
52 #[salsa::invoke(StructData::struct_data_query)] 56 #[salsa::invoke(StructData::struct_data_query)]
53 fn struct_data(&self, id: StructId) -> Arc<StructData>; 57 fn struct_data(&self, id: StructId) -> Arc<StructData>;
54 #[salsa::invoke(StructData::union_data_query)] 58 #[salsa::invoke(StructData::union_data_query)]
@@ -104,3 +108,8 @@ pub trait DefDatabase: InternDatabase + AstDatabase {
104 #[salsa::invoke(Documentation::documentation_query)] 108 #[salsa::invoke(Documentation::documentation_query)]
105 fn documentation(&self, def: AttrDefId) -> Option<Documentation>; 109 fn documentation(&self, def: AttrDefId) -> Option<Documentation>;
106} 110}
111
112fn crate_def_map(db: &impl DefDatabase, krate: CrateId) -> Arc<CrateDefMap> {
113 let _p = profile("crate_def_map");
114 db.compute_crate_def_map(krate)
115}
diff --git a/crates/ra_hir_def/src/nameres.rs b/crates/ra_hir_def/src/nameres.rs
index 5d4ca73a3..4d210eab1 100644
--- a/crates/ra_hir_def/src/nameres.rs
+++ b/crates/ra_hir_def/src/nameres.rs
@@ -172,13 +172,13 @@ pub struct ModuleData {
172} 172}
173 173
174impl CrateDefMap { 174impl CrateDefMap {
175 pub(crate) fn crate_def_map_query( 175 pub(crate) fn compute_crate_def_map_query(
176 // Note that this doesn't have `+ AstDatabase`! 176 // Note that this doesn't have `+ AstDatabase`!
177 // This gurantess that `CrateDefMap` is stable across reparses. 177 // This gurantess that `CrateDefMap` is stable across reparses.
178 db: &impl DefDatabase, 178 db: &impl DefDatabase,
179 krate: CrateId, 179 krate: CrateId,
180 ) -> Arc<CrateDefMap> { 180 ) -> Arc<CrateDefMap> {
181 let _p = profile("crate_def_map_query"); 181 let _p = profile("compute_crate_def_map");
182 let def_map = { 182 let def_map = {
183 let crate_graph = db.crate_graph(); 183 let crate_graph = db.crate_graph();
184 let edition = crate_graph.edition(krate); 184 let edition = crate_graph.edition(krate);
diff --git a/crates/ra_hir_def/src/nameres/collector.rs b/crates/ra_hir_def/src/nameres/collector.rs
index 8a22b0585..35b852ee2 100644
--- a/crates/ra_hir_def/src/nameres/collector.rs
+++ b/crates/ra_hir_def/src/nameres/collector.rs
@@ -45,7 +45,6 @@ pub(super) fn collect_defs(db: &impl DefDatabase, mut def_map: CrateDefMap) -> C
45 // If the dependency defines a prelude, we overwrite an already defined 45 // If the dependency defines a prelude, we overwrite an already defined
46 // prelude. This is necessary to import the "std" prelude if a crate 46 // prelude. This is necessary to import the "std" prelude if a crate
47 // depends on both "core" and "std". 47 // depends on both "core" and "std".
48 let dep_def_map = db.crate_def_map(dep.crate_id);
49 if dep_def_map.prelude.is_some() { 48 if dep_def_map.prelude.is_some() {
50 def_map.prelude = dep_def_map.prelude; 49 def_map.prelude = dep_def_map.prelude;
51 } 50 }
diff --git a/crates/ra_hir_expand/src/name.rs b/crates/ra_hir_expand/src/name.rs
index e62693b68..b3fa1efba 100644
--- a/crates/ra_hir_expand/src/name.rs
+++ b/crates/ra_hir_expand/src/name.rs
@@ -93,7 +93,10 @@ impl AsName for ast::FieldKind {
93 fn as_name(&self) -> Name { 93 fn as_name(&self) -> Name {
94 match self { 94 match self {
95 ast::FieldKind::Name(nr) => nr.as_name(), 95 ast::FieldKind::Name(nr) => nr.as_name(),
96 ast::FieldKind::Index(idx) => Name::new_tuple_field(idx.text().parse().unwrap()), 96 ast::FieldKind::Index(idx) => {
97 let idx = idx.text().parse::<usize>().unwrap_or(0);
98 Name::new_tuple_field(idx)
99 }
97 } 100 }
98 } 101 }
99} 102}
diff --git a/crates/ra_hir_ty/src/db.rs b/crates/ra_hir_ty/src/db.rs
index d52f65b83..eb521c7a0 100644
--- a/crates/ra_hir_ty/src/db.rs
+++ b/crates/ra_hir_ty/src/db.rs
@@ -7,6 +7,7 @@ use hir_def::{
7}; 7};
8use ra_arena::map::ArenaMap; 8use ra_arena::map::ArenaMap;
9use ra_db::{salsa, CrateId}; 9use ra_db::{salsa, CrateId};
10use ra_prof::profile;
10 11
11use crate::{ 12use crate::{
12 method_resolution::CrateImplBlocks, 13 method_resolution::CrateImplBlocks,
@@ -18,9 +19,12 @@ use crate::{
18#[salsa::query_group(HirDatabaseStorage)] 19#[salsa::query_group(HirDatabaseStorage)]
19#[salsa::requires(salsa::Database)] 20#[salsa::requires(salsa::Database)]
20pub trait HirDatabase: DefDatabase { 21pub trait HirDatabase: DefDatabase {
21 #[salsa::invoke(crate::infer_query)] 22 #[salsa::transparent]
22 fn infer(&self, def: DefWithBodyId) -> Arc<InferenceResult>; 23 fn infer(&self, def: DefWithBodyId) -> Arc<InferenceResult>;
23 24
25 #[salsa::invoke(crate::do_infer_query)]
26 fn do_infer(&self, def: DefWithBodyId) -> Arc<InferenceResult>;
27
24 #[salsa::invoke(crate::lower::ty_query)] 28 #[salsa::invoke(crate::lower::ty_query)]
25 #[salsa::cycle(crate::lower::ty_recover)] 29 #[salsa::cycle(crate::lower::ty_recover)]
26 fn ty(&self, def: TyDefId) -> Ty; 30 fn ty(&self, def: TyDefId) -> Ty;
@@ -104,6 +108,11 @@ pub trait HirDatabase: DefDatabase {
104 ) -> Option<crate::traits::Solution>; 108 ) -> Option<crate::traits::Solution>;
105} 109}
106 110
111fn infer(db: &impl HirDatabase, def: DefWithBodyId) -> Arc<InferenceResult> {
112 let _p = profile("infer");
113 db.do_infer(def)
114}
115
107#[test] 116#[test]
108fn hir_database_is_object_safe() { 117fn hir_database_is_object_safe() {
109 fn _assert_object_safe(_: &dyn HirDatabase) {} 118 fn _assert_object_safe(_: &dyn HirDatabase) {}
diff --git a/crates/ra_hir_ty/src/infer.rs b/crates/ra_hir_ty/src/infer.rs
index 37e69599d..e2eda3134 100644
--- a/crates/ra_hir_ty/src/infer.rs
+++ b/crates/ra_hir_ty/src/infer.rs
@@ -62,8 +62,8 @@ mod pat;
62mod coerce; 62mod coerce;
63 63
64/// The entry point of type inference. 64/// The entry point of type inference.
65pub fn infer_query(db: &impl HirDatabase, def: DefWithBodyId) -> Arc<InferenceResult> { 65pub fn do_infer_query(db: &impl HirDatabase, def: DefWithBodyId) -> Arc<InferenceResult> {
66 let _p = profile("infer_query"); 66 let _p = profile("do_infer");
67 let resolver = def.resolver(db); 67 let resolver = def.resolver(db);
68 let mut ctx = InferenceContext::new(db, def, resolver); 68 let mut ctx = InferenceContext::new(db, def, resolver);
69 69
diff --git a/crates/ra_hir_ty/src/lib.rs b/crates/ra_hir_ty/src/lib.rs
index 55b6dd836..d63f862dc 100644
--- a/crates/ra_hir_ty/src/lib.rs
+++ b/crates/ra_hir_ty/src/lib.rs
@@ -58,7 +58,7 @@ use crate::{
58use display::{HirDisplay, HirFormatter}; 58use display::{HirDisplay, HirFormatter};
59 59
60pub use autoderef::autoderef; 60pub use autoderef::autoderef;
61pub use infer::{infer_query, InferTy, InferenceResult}; 61pub use infer::{do_infer_query, InferTy, InferenceResult};
62pub use lower::CallableDef; 62pub use lower::CallableDef;
63pub use lower::{callable_item_sig, TyDefId, ValueTyDefId}; 63pub use lower::{callable_item_sig, TyDefId, ValueTyDefId};
64pub use traits::{InEnvironment, Obligation, ProjectionPredicate, TraitEnvironment}; 64pub use traits::{InEnvironment, Obligation, ProjectionPredicate, TraitEnvironment};
diff --git a/crates/ra_hir_ty/src/lower.rs b/crates/ra_hir_ty/src/lower.rs
index af3db2e1d..2c2ecee9c 100644
--- a/crates/ra_hir_ty/src/lower.rs
+++ b/crates/ra_hir_ty/src/lower.rs
@@ -331,7 +331,7 @@ pub(super) fn substs_from_path_segment(
331 if let Some(generic_args) = &segment.args_and_bindings { 331 if let Some(generic_args) = &segment.args_and_bindings {
332 // if args are provided, it should be all of them, but we can't rely on that 332 // if args are provided, it should be all of them, but we can't rely on that
333 let self_param_correction = if add_self_param { 1 } else { 0 }; 333 let self_param_correction = if add_self_param { 1 } else { 0 };
334 let child_len = child_len + self_param_correction; 334 let child_len = child_len - self_param_correction;
335 for arg in generic_args.args.iter().take(child_len) { 335 for arg in generic_args.args.iter().take(child_len) {
336 match arg { 336 match arg {
337 GenericArg::Type(type_ref) => { 337 GenericArg::Type(type_ref) => {
diff --git a/crates/ra_hir_ty/src/tests/regression.rs b/crates/ra_hir_ty/src/tests/regression.rs
index 8b3aa8564..13c5f62e4 100644
--- a/crates/ra_hir_ty/src/tests/regression.rs
+++ b/crates/ra_hir_ty/src/tests/regression.rs
@@ -365,3 +365,20 @@ fn issue_2669() {
365 "### 365 "###
366 ) 366 )
367} 367}
368
369#[test]
370fn issue_2705() {
371 assert_snapshot!(
372 infer(r#"
373trait Trait {}
374fn test() {
375 <Trait<u32>>::foo()
376}
377"#),
378 @r###"
379 [26; 53) '{ ...oo() }': ()
380 [32; 49) '<Trait...>::foo': {unknown}
381 [32; 51) '<Trait...:foo()': ()
382 "###
383 );
384}
diff --git a/crates/ra_ide/Cargo.toml b/crates/ra_ide/Cargo.toml
index e3439ae31..2c9f9dce0 100644
--- a/crates/ra_ide/Cargo.toml
+++ b/crates/ra_ide/Cargo.toml
@@ -13,6 +13,7 @@ wasm = []
13[dependencies] 13[dependencies]
14either = "1.5" 14either = "1.5"
15format-buf = "1.0.0" 15format-buf = "1.0.0"
16indexmap = "1.3.0"
16itertools = "0.8.0" 17itertools = "0.8.0"
17join_to_string = "0.1.3" 18join_to_string = "0.1.3"
18log = "0.4.5" 19log = "0.4.5"
diff --git a/crates/ra_ide/src/call_hierarchy.rs b/crates/ra_ide/src/call_hierarchy.rs
new file mode 100644
index 000000000..1cb712e32
--- /dev/null
+++ b/crates/ra_ide/src/call_hierarchy.rs
@@ -0,0 +1,337 @@
1//! Entry point for call-hierarchy
2
3use indexmap::IndexMap;
4
5use hir::db::AstDatabase;
6use ra_syntax::{
7 ast::{self, DocCommentsOwner},
8 match_ast, AstNode, TextRange,
9};
10
11use crate::{
12 call_info::FnCallNode,
13 db::RootDatabase,
14 display::{ShortLabel, ToNav},
15 expand::descend_into_macros,
16 goto_definition, references, FilePosition, NavigationTarget, RangeInfo,
17};
18
19#[derive(Debug, Clone)]
20pub struct CallItem {
21 pub target: NavigationTarget,
22 pub ranges: Vec<TextRange>,
23}
24
25impl CallItem {
26 #[cfg(test)]
27 pub(crate) fn assert_match(&self, expected: &str) {
28 let actual = self.debug_render();
29 test_utils::assert_eq_text!(expected.trim(), actual.trim(),);
30 }
31
32 #[cfg(test)]
33 pub(crate) fn debug_render(&self) -> String {
34 format!("{} : {:?}", self.target.debug_render(), self.ranges)
35 }
36}
37
38pub(crate) fn call_hierarchy(
39 db: &RootDatabase,
40 position: FilePosition,
41) -> Option<RangeInfo<Vec<NavigationTarget>>> {
42 goto_definition::goto_definition(db, position)
43}
44
45pub(crate) fn incoming_calls(db: &RootDatabase, position: FilePosition) -> Option<Vec<CallItem>> {
46 // 1. Find all refs
47 // 2. Loop through refs and determine unique fndef. This will become our `from: CallHierarchyItem,` in the reply.
48 // 3. Add ranges relative to the start of the fndef.
49 let refs = references::find_all_refs(db, position, None)?;
50
51 let mut calls = CallLocations::default();
52
53 for reference in refs.info.references() {
54 let file_id = reference.file_range.file_id;
55 let file = db.parse_or_expand(file_id.into())?;
56 let token = file.token_at_offset(reference.file_range.range.start()).next()?;
57 let token = descend_into_macros(db, file_id, token);
58 let syntax = token.value.parent();
59
60 // This target is the containing function
61 if let Some(nav) = syntax.ancestors().find_map(|node| {
62 match_ast! {
63 match node {
64 ast::FnDef(it) => {
65 Some(NavigationTarget::from_named(
66 db,
67 token.with_value(&it),
68 it.doc_comment_text(),
69 it.short_label(),
70 ))
71 },
72 _ => { None },
73 }
74 }
75 }) {
76 let relative_range = reference.file_range.range;
77 calls.add(&nav, relative_range);
78 }
79 }
80
81 Some(calls.into_items())
82}
83
84pub(crate) fn outgoing_calls(db: &RootDatabase, position: FilePosition) -> Option<Vec<CallItem>> {
85 let file_id = position.file_id;
86 let file = db.parse_or_expand(file_id.into())?;
87 let token = file.token_at_offset(position.offset).next()?;
88 let token = descend_into_macros(db, file_id, token);
89 let syntax = token.value.parent();
90
91 let mut calls = CallLocations::default();
92
93 syntax
94 .descendants()
95 .filter_map(|node| FnCallNode::with_node_exact(&node))
96 .filter_map(|call_node| {
97 let name_ref = call_node.name_ref()?;
98 let name_ref = token.with_value(name_ref.syntax());
99
100 let analyzer = hir::SourceAnalyzer::new(db, name_ref, None);
101
102 if let Some(func_target) = match &call_node {
103 FnCallNode::CallExpr(expr) => {
104 //FIXME: Type::as_callable is broken
105 let callable_def = analyzer.type_of(db, &expr.expr()?)?.as_callable()?;
106 match callable_def {
107 hir::CallableDef::FunctionId(it) => {
108 let fn_def: hir::Function = it.into();
109 let nav = fn_def.to_nav(db);
110 Some(nav)
111 }
112 _ => None,
113 }
114 }
115 FnCallNode::MethodCallExpr(expr) => {
116 let function = analyzer.resolve_method_call(&expr)?;
117 Some(function.to_nav(db))
118 }
119 FnCallNode::MacroCallExpr(expr) => {
120 let macro_def = analyzer.resolve_macro_call(db, name_ref.with_value(&expr))?;
121 Some(macro_def.to_nav(db))
122 }
123 } {
124 Some((func_target.clone(), name_ref.value.text_range()))
125 } else {
126 None
127 }
128 })
129 .for_each(|(nav, range)| calls.add(&nav, range));
130
131 Some(calls.into_items())
132}
133
134#[derive(Default)]
135struct CallLocations {
136 funcs: IndexMap<NavigationTarget, Vec<TextRange>>,
137}
138
139impl CallLocations {
140 fn add(&mut self, target: &NavigationTarget, range: TextRange) {
141 self.funcs.entry(target.clone()).or_default().push(range);
142 }
143
144 fn into_items(self) -> Vec<CallItem> {
145 self.funcs.into_iter().map(|(target, ranges)| CallItem { target, ranges }).collect()
146 }
147}
148
149#[cfg(test)]
150mod tests {
151 use ra_db::FilePosition;
152
153 use crate::mock_analysis::analysis_and_position;
154
155 fn check_hierarchy(
156 fixture: &str,
157 expected: &str,
158 expected_incoming: &[&str],
159 expected_outgoing: &[&str],
160 ) {
161 let (analysis, pos) = analysis_and_position(fixture);
162
163 let mut navs = analysis.call_hierarchy(pos).unwrap().unwrap().info;
164 assert_eq!(navs.len(), 1);
165 let nav = navs.pop().unwrap();
166 nav.assert_match(expected);
167
168 let item_pos = FilePosition { file_id: nav.file_id(), offset: nav.range().start() };
169 let incoming_calls = analysis.incoming_calls(item_pos).unwrap().unwrap();
170 assert_eq!(incoming_calls.len(), expected_incoming.len());
171
172 for call in 0..incoming_calls.len() {
173 incoming_calls[call].assert_match(expected_incoming[call]);
174 }
175
176 let outgoing_calls = analysis.outgoing_calls(item_pos).unwrap().unwrap();
177 assert_eq!(outgoing_calls.len(), expected_outgoing.len());
178
179 for call in 0..outgoing_calls.len() {
180 outgoing_calls[call].assert_match(expected_outgoing[call]);
181 }
182 }
183
184 #[test]
185 fn test_call_hierarchy_on_ref() {
186 check_hierarchy(
187 r#"
188 //- /lib.rs
189 fn callee() {}
190 fn caller() {
191 call<|>ee();
192 }
193 "#,
194 "callee FN_DEF FileId(1) [0; 14) [3; 9)",
195 &["caller FN_DEF FileId(1) [15; 44) [18; 24) : [[33; 39)]"],
196 &[],
197 );
198 }
199
200 #[test]
201 fn test_call_hierarchy_on_def() {
202 check_hierarchy(
203 r#"
204 //- /lib.rs
205 fn call<|>ee() {}
206 fn caller() {
207 callee();
208 }
209 "#,
210 "callee FN_DEF FileId(1) [0; 14) [3; 9)",
211 &["caller FN_DEF FileId(1) [15; 44) [18; 24) : [[33; 39)]"],
212 &[],
213 );
214 }
215
216 #[test]
217 fn test_call_hierarchy_in_same_fn() {
218 check_hierarchy(
219 r#"
220 //- /lib.rs
221 fn callee() {}
222 fn caller() {
223 call<|>ee();
224 callee();
225 }
226 "#,
227 "callee FN_DEF FileId(1) [0; 14) [3; 9)",
228 &["caller FN_DEF FileId(1) [15; 58) [18; 24) : [[33; 39), [47; 53)]"],
229 &[],
230 );
231 }
232
233 #[test]
234 fn test_call_hierarchy_in_different_fn() {
235 check_hierarchy(
236 r#"
237 //- /lib.rs
238 fn callee() {}
239 fn caller1() {
240 call<|>ee();
241 }
242
243 fn caller2() {
244 callee();
245 }
246 "#,
247 "callee FN_DEF FileId(1) [0; 14) [3; 9)",
248 &[
249 "caller1 FN_DEF FileId(1) [15; 45) [18; 25) : [[34; 40)]",
250 "caller2 FN_DEF FileId(1) [46; 76) [49; 56) : [[65; 71)]",
251 ],
252 &[],
253 );
254 }
255
256 #[test]
257 fn test_call_hierarchy_in_different_files() {
258 check_hierarchy(
259 r#"
260 //- /lib.rs
261 mod foo;
262 use foo::callee;
263
264 fn caller() {
265 call<|>ee();
266 }
267
268 //- /foo/mod.rs
269 pub fn callee() {}
270 "#,
271 "callee FN_DEF FileId(2) [0; 18) [7; 13)",
272 &["caller FN_DEF FileId(1) [26; 55) [29; 35) : [[44; 50)]"],
273 &[],
274 );
275 }
276
277 #[test]
278 fn test_call_hierarchy_outgoing() {
279 check_hierarchy(
280 r#"
281 //- /lib.rs
282 fn callee() {}
283 fn call<|>er() {
284 callee();
285 callee();
286 }
287 "#,
288 "caller FN_DEF FileId(1) [15; 58) [18; 24)",
289 &[],
290 &["callee FN_DEF FileId(1) [0; 14) [3; 9) : [[33; 39), [47; 53)]"],
291 );
292 }
293
294 #[test]
295 fn test_call_hierarchy_outgoing_in_different_files() {
296 check_hierarchy(
297 r#"
298 //- /lib.rs
299 mod foo;
300 use foo::callee;
301
302 fn call<|>er() {
303 callee();
304 }
305
306 //- /foo/mod.rs
307 pub fn callee() {}
308 "#,
309 "caller FN_DEF FileId(1) [26; 55) [29; 35)",
310 &[],
311 &["callee FN_DEF FileId(2) [0; 18) [7; 13) : [[44; 50)]"],
312 );
313 }
314
315 #[test]
316 fn test_call_hierarchy_incoming_outgoing() {
317 check_hierarchy(
318 r#"
319 //- /lib.rs
320 fn caller1() {
321 call<|>er2();
322 }
323
324 fn caller2() {
325 caller3();
326 }
327
328 fn caller3() {
329
330 }
331 "#,
332 "caller2 FN_DEF FileId(1) [32; 63) [35; 42)",
333 &["caller1 FN_DEF FileId(1) [0; 31) [3; 10) : [[19; 26)]"],
334 &["caller3 FN_DEF FileId(1) [64; 80) [67; 74) : [[51; 58)]"],
335 );
336 }
337}
diff --git a/crates/ra_ide/src/call_info.rs b/crates/ra_ide/src/call_info.rs
index 2c2b6fa48..a7023529b 100644
--- a/crates/ra_ide/src/call_info.rs
+++ b/crates/ra_ide/src/call_info.rs
@@ -88,7 +88,7 @@ pub(crate) fn call_info(db: &RootDatabase, position: FilePosition) -> Option<Cal
88} 88}
89 89
90#[derive(Debug)] 90#[derive(Debug)]
91enum FnCallNode { 91pub(crate) enum FnCallNode {
92 CallExpr(ast::CallExpr), 92 CallExpr(ast::CallExpr),
93 MethodCallExpr(ast::MethodCallExpr), 93 MethodCallExpr(ast::MethodCallExpr),
94 MacroCallExpr(ast::MacroCall), 94 MacroCallExpr(ast::MacroCall),
@@ -108,7 +108,18 @@ impl FnCallNode {
108 }) 108 })
109 } 109 }
110 110
111 fn name_ref(&self) -> Option<ast::NameRef> { 111 pub(crate) fn with_node_exact(node: &SyntaxNode) -> Option<FnCallNode> {
112 match_ast! {
113 match node {
114 ast::CallExpr(it) => { Some(FnCallNode::CallExpr(it)) },
115 ast::MethodCallExpr(it) => { Some(FnCallNode::MethodCallExpr(it)) },
116 ast::MacroCall(it) => { Some(FnCallNode::MacroCallExpr(it)) },
117 _ => { None },
118 }
119 }
120 }
121
122 pub(crate) fn name_ref(&self) -> Option<ast::NameRef> {
112 match self { 123 match self {
113 FnCallNode::CallExpr(call_expr) => Some(match call_expr.expr()? { 124 FnCallNode::CallExpr(call_expr) => Some(match call_expr.expr()? {
114 ast::Expr::PathExpr(path_expr) => path_expr.path()?.segment()?.name_ref()?, 125 ast::Expr::PathExpr(path_expr) => path_expr.path()?.segment()?.name_ref()?,
diff --git a/crates/ra_ide/src/change.rs b/crates/ra_ide/src/change.rs
index 387a9cafb..b0aa2c8e0 100644
--- a/crates/ra_ide/src/change.rs
+++ b/crates/ra_ide/src/change.rs
@@ -176,7 +176,8 @@ impl RootDatabase {
176 if !change.new_roots.is_empty() { 176 if !change.new_roots.is_empty() {
177 let mut local_roots = Vec::clone(&self.local_roots()); 177 let mut local_roots = Vec::clone(&self.local_roots());
178 for (root_id, is_local) in change.new_roots { 178 for (root_id, is_local) in change.new_roots {
179 let root = if is_local { SourceRoot::new() } else { SourceRoot::new_library() }; 179 let root =
180 if is_local { SourceRoot::new_local() } else { SourceRoot::new_library() };
180 let durability = durability(&root); 181 let durability = durability(&root);
181 self.set_source_root_with_durability(root_id, Arc::new(root), durability); 182 self.set_source_root_with_durability(root_id, Arc::new(root), durability);
182 if is_local { 183 if is_local {
@@ -201,7 +202,7 @@ impl RootDatabase {
201 libraries.push(library.root_id); 202 libraries.push(library.root_id);
202 self.set_source_root_with_durability( 203 self.set_source_root_with_durability(
203 library.root_id, 204 library.root_id,
204 Default::default(), 205 Arc::new(SourceRoot::new_library()),
205 Durability::HIGH, 206 Durability::HIGH,
206 ); 207 );
207 self.set_library_symbols_with_durability( 208 self.set_library_symbols_with_durability(
@@ -273,7 +274,7 @@ impl RootDatabase {
273 self.query(hir::db::BodyWithSourceMapQuery).sweep(sweep); 274 self.query(hir::db::BodyWithSourceMapQuery).sweep(sweep);
274 275
275 self.query(hir::db::ExprScopesQuery).sweep(sweep); 276 self.query(hir::db::ExprScopesQuery).sweep(sweep);
276 self.query(hir::db::InferQuery).sweep(sweep); 277 self.query(hir::db::DoInferQuery).sweep(sweep);
277 self.query(hir::db::BodyQuery).sweep(sweep); 278 self.query(hir::db::BodyQuery).sweep(sweep);
278 } 279 }
279 280
@@ -309,7 +310,7 @@ impl RootDatabase {
309 hir::db::EnumDataQuery 310 hir::db::EnumDataQuery
310 hir::db::TraitDataQuery 311 hir::db::TraitDataQuery
311 hir::db::RawItemsQuery 312 hir::db::RawItemsQuery
312 hir::db::CrateDefMapQuery 313 hir::db::ComputeCrateDefMapQuery
313 hir::db::GenericParamsQuery 314 hir::db::GenericParamsQuery
314 hir::db::FunctionDataQuery 315 hir::db::FunctionDataQuery
315 hir::db::TypeAliasDataQuery 316 hir::db::TypeAliasDataQuery
@@ -320,7 +321,7 @@ impl RootDatabase {
320 hir::db::LangItemQuery 321 hir::db::LangItemQuery
321 hir::db::DocumentationQuery 322 hir::db::DocumentationQuery
322 hir::db::ExprScopesQuery 323 hir::db::ExprScopesQuery
323 hir::db::InferQuery 324 hir::db::DoInferQuery
324 hir::db::TyQuery 325 hir::db::TyQuery
325 hir::db::ValueTyQuery 326 hir::db::ValueTyQuery
326 hir::db::FieldTypesQuery 327 hir::db::FieldTypesQuery
diff --git a/crates/ra_ide/src/diagnostics.rs b/crates/ra_ide/src/diagnostics.rs
index c50a70d99..478368529 100644
--- a/crates/ra_ide/src/diagnostics.rs
+++ b/crates/ra_ide/src/diagnostics.rs
@@ -64,22 +64,36 @@ pub(crate) fn diagnostics(db: &RootDatabase, file_id: FileId) -> Vec<Diagnostic>
64 }) 64 })
65 }) 65 })
66 .on::<hir::diagnostics::MissingFields, _>(|d| { 66 .on::<hir::diagnostics::MissingFields, _>(|d| {
67 let mut field_list = d.ast(db); 67 // Note that although we could add a diagnostics to
68 for f in d.missed_fields.iter() { 68 // fill the missing tuple field, e.g :
69 let field = make::record_field(make::name_ref(&f.to_string()), Some(make::expr_unit())); 69 // `struct A(usize);`
70 field_list = field_list.append_field(&field); 70 // `let a = A { 0: () }`
71 } 71 // but it is uncommon usage and it should not be encouraged.
72 72 let fix = if d.missed_fields.iter().any(|it| it.as_tuple_index().is_some()) {
73 let mut builder = TextEditBuilder::default(); 73 None
74 algo::diff(&d.ast(db).syntax(), &field_list.syntax()).into_text_edit(&mut builder); 74 } else {
75 let mut field_list = d.ast(db);
76 for f in d.missed_fields.iter() {
77 let field =
78 make::record_field(make::name_ref(&f.to_string()), Some(make::expr_unit()));
79 field_list = field_list.append_field(&field);
80 }
81
82 let mut builder = TextEditBuilder::default();
83 algo::diff(&d.ast(db).syntax(), &field_list.syntax()).into_text_edit(&mut builder);
84
85 Some(SourceChange::source_file_edit_from(
86 "fill struct fields",
87 file_id,
88 builder.finish(),
89 ))
90 };
75 91
76 let fix =
77 SourceChange::source_file_edit_from("fill struct fields", file_id, builder.finish());
78 res.borrow_mut().push(Diagnostic { 92 res.borrow_mut().push(Diagnostic {
79 range: d.highlight_range(), 93 range: d.highlight_range(),
80 message: d.message(), 94 message: d.message(),
81 severity: Severity::Error, 95 severity: Severity::Error,
82 fix: Some(fix), 96 fix,
83 }) 97 })
84 }) 98 })
85 .on::<hir::diagnostics::MissingOkInTailExpr, _>(|d| { 99 .on::<hir::diagnostics::MissingOkInTailExpr, _>(|d| {
diff --git a/crates/ra_ide/src/display/navigation_target.rs b/crates/ra_ide/src/display/navigation_target.rs
index b9ae67828..f2e45fa31 100644
--- a/crates/ra_ide/src/display/navigation_target.rs
+++ b/crates/ra_ide/src/display/navigation_target.rs
@@ -19,7 +19,7 @@ use super::short_label::ShortLabel;
19/// 19///
20/// Typically, a `NavigationTarget` corresponds to some element in the source 20/// Typically, a `NavigationTarget` corresponds to some element in the source
21/// code, like a function or a struct, but this is not strictly required. 21/// code, like a function or a struct, but this is not strictly required.
22#[derive(Debug, Clone)] 22#[derive(Debug, Clone, PartialEq, Eq, Hash)]
23pub struct NavigationTarget { 23pub struct NavigationTarget {
24 file_id: FileId, 24 file_id: FileId,
25 name: SmolStr, 25 name: SmolStr,
diff --git a/crates/ra_ide/src/expand.rs b/crates/ra_ide/src/expand.rs
index 7a22bb0a4..b82259a3d 100644
--- a/crates/ra_ide/src/expand.rs
+++ b/crates/ra_ide/src/expand.rs
@@ -76,14 +76,15 @@ pub(crate) fn descend_into_macros(
76) -> InFile<SyntaxToken> { 76) -> InFile<SyntaxToken> {
77 let src = InFile::new(file_id.into(), token); 77 let src = InFile::new(file_id.into(), token);
78 78
79 let source_analyzer =
80 hir::SourceAnalyzer::new(db, src.with_value(src.value.parent()).as_ref(), None);
81
79 successors(Some(src), |token| { 82 successors(Some(src), |token| {
80 let macro_call = token.value.ancestors().find_map(ast::MacroCall::cast)?; 83 let macro_call = token.value.ancestors().find_map(ast::MacroCall::cast)?;
81 let tt = macro_call.token_tree()?; 84 let tt = macro_call.token_tree()?;
82 if !token.value.text_range().is_subrange(&tt.syntax().text_range()) { 85 if !token.value.text_range().is_subrange(&tt.syntax().text_range()) {
83 return None; 86 return None;
84 } 87 }
85 let source_analyzer =
86 hir::SourceAnalyzer::new(db, token.with_value(token.value.parent()).as_ref(), None);
87 let exp = source_analyzer.expand(db, token.with_value(&macro_call))?; 88 let exp = source_analyzer.expand(db, token.with_value(&macro_call))?;
88 exp.map_token_down(db, token.as_ref()) 89 exp.map_token_down(db, token.as_ref())
89 }) 90 })
diff --git a/crates/ra_ide/src/lib.rs b/crates/ra_ide/src/lib.rs
index 779a81b2c..7b187eba3 100644
--- a/crates/ra_ide/src/lib.rs
+++ b/crates/ra_ide/src/lib.rs
@@ -24,6 +24,7 @@ mod goto_definition;
24mod goto_type_definition; 24mod goto_type_definition;
25mod extend_selection; 25mod extend_selection;
26mod hover; 26mod hover;
27mod call_hierarchy;
27mod call_info; 28mod call_info;
28mod syntax_highlighting; 29mod syntax_highlighting;
29mod parent_module; 30mod parent_module;
@@ -62,6 +63,7 @@ use crate::{db::LineIndexDatabase, display::ToNav, symbol_index::FileSymbol};
62 63
63pub use crate::{ 64pub use crate::{
64 assists::{Assist, AssistId}, 65 assists::{Assist, AssistId},
66 call_hierarchy::CallItem,
65 change::{AnalysisChange, LibraryData}, 67 change::{AnalysisChange, LibraryData},
66 completion::{CompletionItem, CompletionItemKind, InsertTextFormat}, 68 completion::{CompletionItem, CompletionItemKind, InsertTextFormat},
67 diagnostics::Severity, 69 diagnostics::Severity,
@@ -73,7 +75,7 @@ pub use crate::{
73 inlay_hints::{InlayHint, InlayKind}, 75 inlay_hints::{InlayHint, InlayKind},
74 line_index::{LineCol, LineIndex}, 76 line_index::{LineCol, LineIndex},
75 line_index_utils::translate_offset_with_edit, 77 line_index_utils::translate_offset_with_edit,
76 references::{ReferenceSearchResult, SearchScope}, 78 references::{Reference, ReferenceKind, ReferenceSearchResult, SearchScope},
77 runnables::{Runnable, RunnableKind}, 79 runnables::{Runnable, RunnableKind},
78 source_change::{FileSystemEdit, SourceChange, SourceFileEdit}, 80 source_change::{FileSystemEdit, SourceChange, SourceFileEdit},
79 syntax_highlighting::HighlightedRange, 81 syntax_highlighting::HighlightedRange,
@@ -412,6 +414,24 @@ impl Analysis {
412 self.with_db(|db| call_info::call_info(db, position)) 414 self.with_db(|db| call_info::call_info(db, position))
413 } 415 }
414 416
417 /// Computes call hierarchy candidates for the given file position.
418 pub fn call_hierarchy(
419 &self,
420 position: FilePosition,
421 ) -> Cancelable<Option<RangeInfo<Vec<NavigationTarget>>>> {
422 self.with_db(|db| call_hierarchy::call_hierarchy(db, position))
423 }
424
425 /// Computes incoming calls for the given file position.
426 pub fn incoming_calls(&self, position: FilePosition) -> Cancelable<Option<Vec<CallItem>>> {
427 self.with_db(|db| call_hierarchy::incoming_calls(db, position))
428 }
429
430 /// Computes incoming calls for the given file position.
431 pub fn outgoing_calls(&self, position: FilePosition) -> Cancelable<Option<Vec<CallItem>>> {
432 self.with_db(|db| call_hierarchy::outgoing_calls(db, position))
433 }
434
415 /// Returns a `mod name;` declaration which created the current module. 435 /// Returns a `mod name;` declaration which created the current module.
416 pub fn parent_module(&self, position: FilePosition) -> Cancelable<Vec<NavigationTarget>> { 436 pub fn parent_module(&self, position: FilePosition) -> Cancelable<Vec<NavigationTarget>> {
417 self.with_db(|db| parent_module::parent_module(db, position)) 437 self.with_db(|db| parent_module::parent_module(db, position))
diff --git a/crates/ra_ide/src/references.rs b/crates/ra_ide/src/references.rs
index e3ecde50d..5a3ec4eb9 100644
--- a/crates/ra_ide/src/references.rs
+++ b/crates/ra_ide/src/references.rs
@@ -18,7 +18,10 @@ use hir::InFile;
18use once_cell::unsync::Lazy; 18use once_cell::unsync::Lazy;
19use ra_db::{SourceDatabase, SourceDatabaseExt}; 19use ra_db::{SourceDatabase, SourceDatabaseExt};
20use ra_prof::profile; 20use ra_prof::profile;
21use ra_syntax::{algo::find_node_at_offset, ast, AstNode, SourceFile, SyntaxNode, TextUnit}; 21use ra_syntax::{
22 algo::find_node_at_offset, ast, AstNode, SourceFile, SyntaxKind, SyntaxNode, TextUnit,
23 TokenAtOffset,
24};
22 25
23use crate::{ 26use crate::{
24 db::RootDatabase, display::ToNav, FilePosition, FileRange, NavigationTarget, RangeInfo, 27 db::RootDatabase, display::ToNav, FilePosition, FileRange, NavigationTarget, RangeInfo,
@@ -35,7 +38,20 @@ pub use self::search_scope::SearchScope;
35#[derive(Debug, Clone)] 38#[derive(Debug, Clone)]
36pub struct ReferenceSearchResult { 39pub struct ReferenceSearchResult {
37 declaration: NavigationTarget, 40 declaration: NavigationTarget,
38 references: Vec<FileRange>, 41 declaration_kind: ReferenceKind,
42 references: Vec<Reference>,
43}
44
45#[derive(Debug, Clone)]
46pub struct Reference {
47 pub file_range: FileRange,
48 pub kind: ReferenceKind,
49}
50
51#[derive(Debug, Clone, PartialEq)]
52pub enum ReferenceKind {
53 StructLiteral,
54 Other,
39} 55}
40 56
41impl ReferenceSearchResult { 57impl ReferenceSearchResult {
@@ -43,7 +59,7 @@ impl ReferenceSearchResult {
43 &self.declaration 59 &self.declaration
44 } 60 }
45 61
46 pub fn references(&self) -> &[FileRange] { 62 pub fn references(&self) -> &[Reference] {
47 &self.references 63 &self.references
48 } 64 }
49 65
@@ -58,12 +74,18 @@ impl ReferenceSearchResult {
58// allow turning ReferenceSearchResult into an iterator 74// allow turning ReferenceSearchResult into an iterator
59// over FileRanges 75// over FileRanges
60impl IntoIterator for ReferenceSearchResult { 76impl IntoIterator for ReferenceSearchResult {
61 type Item = FileRange; 77 type Item = Reference;
62 type IntoIter = std::vec::IntoIter<FileRange>; 78 type IntoIter = std::vec::IntoIter<Reference>;
63 79
64 fn into_iter(mut self) -> Self::IntoIter { 80 fn into_iter(mut self) -> Self::IntoIter {
65 let mut v = Vec::with_capacity(self.len()); 81 let mut v = Vec::with_capacity(self.len());
66 v.push(FileRange { file_id: self.declaration.file_id(), range: self.declaration.range() }); 82 v.push(Reference {
83 file_range: FileRange {
84 file_id: self.declaration.file_id(),
85 range: self.declaration.range(),
86 },
87 kind: self.declaration_kind,
88 });
67 v.append(&mut self.references); 89 v.append(&mut self.references);
68 v.into_iter() 90 v.into_iter()
69 } 91 }
@@ -71,11 +93,24 @@ impl IntoIterator for ReferenceSearchResult {
71 93
72pub(crate) fn find_all_refs( 94pub(crate) fn find_all_refs(
73 db: &RootDatabase, 95 db: &RootDatabase,
74 position: FilePosition, 96 mut position: FilePosition,
75 search_scope: Option<SearchScope>, 97 search_scope: Option<SearchScope>,
76) -> Option<RangeInfo<ReferenceSearchResult>> { 98) -> Option<RangeInfo<ReferenceSearchResult>> {
77 let parse = db.parse(position.file_id); 99 let parse = db.parse(position.file_id);
78 let syntax = parse.tree().syntax().clone(); 100 let syntax = parse.tree().syntax().clone();
101
102 let token = syntax.token_at_offset(position.offset);
103 let mut search_kind = ReferenceKind::Other;
104
105 if let TokenAtOffset::Between(ref left, ref right) = token {
106 if (right.kind() == SyntaxKind::L_CURLY || right.kind() == SyntaxKind::L_PAREN)
107 && left.kind() != SyntaxKind::IDENT
108 {
109 position = FilePosition { offset: left.text_range().start(), ..position };
110 search_kind = ReferenceKind::StructLiteral;
111 }
112 }
113
79 let RangeInfo { range, info: (name, def) } = find_name(db, &syntax, position)?; 114 let RangeInfo { range, info: (name, def) } = find_name(db, &syntax, position)?;
80 115
81 let declaration = match def.kind { 116 let declaration = match def.kind {
@@ -96,9 +131,15 @@ pub(crate) fn find_all_refs(
96 } 131 }
97 }; 132 };
98 133
99 let references = process_definition(db, def, name, search_scope); 134 let references = process_definition(db, def, name, search_scope)
135 .into_iter()
136 .filter(|r| search_kind == ReferenceKind::Other || search_kind == r.kind)
137 .collect();
100 138
101 Some(RangeInfo::new(range, ReferenceSearchResult { declaration, references })) 139 Some(RangeInfo::new(
140 range,
141 ReferenceSearchResult { declaration, references, declaration_kind: ReferenceKind::Other },
142 ))
102} 143}
103 144
104fn find_name<'a>( 145fn find_name<'a>(
@@ -122,7 +163,7 @@ fn process_definition(
122 def: NameDefinition, 163 def: NameDefinition,
123 name: String, 164 name: String,
124 scope: SearchScope, 165 scope: SearchScope,
125) -> Vec<FileRange> { 166) -> Vec<Reference> {
126 let _p = profile("process_definition"); 167 let _p = profile("process_definition");
127 168
128 let pat = name.as_str(); 169 let pat = name.as_str();
@@ -146,7 +187,21 @@ fn process_definition(
146 } 187 }
147 if let Some(d) = classify_name_ref(db, InFile::new(file_id.into(), &name_ref)) { 188 if let Some(d) = classify_name_ref(db, InFile::new(file_id.into(), &name_ref)) {
148 if d == def { 189 if d == def {
149 refs.push(FileRange { file_id, range }); 190 let kind = if name_ref
191 .syntax()
192 .ancestors()
193 .find_map(ast::RecordLit::cast)
194 .and_then(|l| l.path())
195 .and_then(|p| p.segment())
196 .and_then(|p| p.name_ref())
197 .map(|n| n == name_ref)
198 .unwrap_or(false)
199 {
200 ReferenceKind::StructLiteral
201 } else {
202 ReferenceKind::Other
203 };
204 refs.push(Reference { file_range: FileRange { file_id, range }, kind });
150 } 205 }
151 } 206 }
152 } 207 }
@@ -159,10 +214,33 @@ fn process_definition(
159mod tests { 214mod tests {
160 use crate::{ 215 use crate::{
161 mock_analysis::{analysis_and_position, single_file_with_position, MockAnalysis}, 216 mock_analysis::{analysis_and_position, single_file_with_position, MockAnalysis},
162 ReferenceSearchResult, SearchScope, 217 Reference, ReferenceKind, ReferenceSearchResult, SearchScope,
163 }; 218 };
164 219
165 #[test] 220 #[test]
221 fn test_struct_literal() {
222 let code = r#"
223 struct Foo <|>{
224 a: i32,
225 }
226 impl Foo {
227 fn f() -> i32 { 42 }
228 }
229 fn main() {
230 let f: Foo;
231 f = Foo {a: Foo::f()};
232 }"#;
233
234 let refs = get_all_refs(code);
235 check_result(
236 refs,
237 "Foo STRUCT_DEF FileId(1) [5; 39) [12; 15)",
238 ReferenceKind::Other,
239 &["FileId(1) [142; 145) StructLiteral"],
240 );
241 }
242
243 #[test]
166 fn test_find_all_refs_for_local() { 244 fn test_find_all_refs_for_local() {
167 let code = r#" 245 let code = r#"
168 fn main() { 246 fn main() {
@@ -178,7 +256,17 @@ mod tests {
178 }"#; 256 }"#;
179 257
180 let refs = get_all_refs(code); 258 let refs = get_all_refs(code);
181 assert_eq!(refs.len(), 5); 259 check_result(
260 refs,
261 "i BIND_PAT FileId(1) [33; 34)",
262 ReferenceKind::Other,
263 &[
264 "FileId(1) [67; 68) Other",
265 "FileId(1) [71; 72) Other",
266 "FileId(1) [101; 102) Other",
267 "FileId(1) [127; 128) Other",
268 ],
269 );
182 } 270 }
183 271
184 #[test] 272 #[test]
@@ -189,7 +277,12 @@ mod tests {
189 }"#; 277 }"#;
190 278
191 let refs = get_all_refs(code); 279 let refs = get_all_refs(code);
192 assert_eq!(refs.len(), 2); 280 check_result(
281 refs,
282 "i BIND_PAT FileId(1) [12; 13)",
283 ReferenceKind::Other,
284 &["FileId(1) [38; 39) Other"],
285 );
193 } 286 }
194 287
195 #[test] 288 #[test]
@@ -200,7 +293,12 @@ mod tests {
200 }"#; 293 }"#;
201 294
202 let refs = get_all_refs(code); 295 let refs = get_all_refs(code);
203 assert_eq!(refs.len(), 2); 296 check_result(
297 refs,
298 "i BIND_PAT FileId(1) [12; 13)",
299 ReferenceKind::Other,
300 &["FileId(1) [38; 39) Other"],
301 );
204 } 302 }
205 303
206 #[test] 304 #[test]
@@ -217,7 +315,12 @@ mod tests {
217 "#; 315 "#;
218 316
219 let refs = get_all_refs(code); 317 let refs = get_all_refs(code);
220 assert_eq!(refs.len(), 2); 318 check_result(
319 refs,
320 "spam RECORD_FIELD_DEF FileId(1) [66; 79) [70; 74)",
321 ReferenceKind::Other,
322 &["FileId(1) [152; 156) Other"],
323 );
221 } 324 }
222 325
223 #[test] 326 #[test]
@@ -231,7 +334,7 @@ mod tests {
231 "#; 334 "#;
232 335
233 let refs = get_all_refs(code); 336 let refs = get_all_refs(code);
234 assert_eq!(refs.len(), 1); 337 check_result(refs, "f FN_DEF FileId(1) [88; 104) [91; 92)", ReferenceKind::Other, &[]);
235 } 338 }
236 339
237 #[test] 340 #[test]
@@ -246,7 +349,7 @@ mod tests {
246 "#; 349 "#;
247 350
248 let refs = get_all_refs(code); 351 let refs = get_all_refs(code);
249 assert_eq!(refs.len(), 1); 352 check_result(refs, "B ENUM_VARIANT FileId(1) [83; 84) [83; 84)", ReferenceKind::Other, &[]);
250 } 353 }
251 354
252 #[test] 355 #[test]
@@ -285,7 +388,12 @@ mod tests {
285 388
286 let (analysis, pos) = analysis_and_position(code); 389 let (analysis, pos) = analysis_and_position(code);
287 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap(); 390 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap();
288 assert_eq!(refs.len(), 3); 391 check_result(
392 refs,
393 "Foo STRUCT_DEF FileId(2) [16; 50) [27; 30)",
394 ReferenceKind::Other,
395 &["FileId(1) [52; 55) StructLiteral", "FileId(3) [77; 80) StructLiteral"],
396 );
289 } 397 }
290 398
291 // `mod foo;` is not in the results because `foo` is an `ast::Name`. 399 // `mod foo;` is not in the results because `foo` is an `ast::Name`.
@@ -311,7 +419,12 @@ mod tests {
311 419
312 let (analysis, pos) = analysis_and_position(code); 420 let (analysis, pos) = analysis_and_position(code);
313 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap(); 421 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap();
314 assert_eq!(refs.len(), 2); 422 check_result(
423 refs,
424 "foo SOURCE_FILE FileId(2) [0; 35)",
425 ReferenceKind::Other,
426 &["FileId(1) [13; 16) Other"],
427 );
315 } 428 }
316 429
317 #[test] 430 #[test]
@@ -336,7 +449,12 @@ mod tests {
336 449
337 let (analysis, pos) = analysis_and_position(code); 450 let (analysis, pos) = analysis_and_position(code);
338 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap(); 451 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap();
339 assert_eq!(refs.len(), 3); 452 check_result(
453 refs,
454 "Foo STRUCT_DEF FileId(3) [0; 41) [18; 21)",
455 ReferenceKind::Other,
456 &["FileId(2) [20; 23) Other", "FileId(2) [46; 49) StructLiteral"],
457 );
340 } 458 }
341 459
342 #[test] 460 #[test]
@@ -360,11 +478,21 @@ mod tests {
360 let analysis = mock.analysis(); 478 let analysis = mock.analysis();
361 479
362 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap(); 480 let refs = analysis.find_all_refs(pos, None).unwrap().unwrap();
363 assert_eq!(refs.len(), 3); 481 check_result(
482 refs,
483 "quux FN_DEF FileId(1) [18; 34) [25; 29)",
484 ReferenceKind::Other,
485 &["FileId(2) [16; 20) Other", "FileId(3) [16; 20) Other"],
486 );
364 487
365 let refs = 488 let refs =
366 analysis.find_all_refs(pos, Some(SearchScope::single_file(bar))).unwrap().unwrap(); 489 analysis.find_all_refs(pos, Some(SearchScope::single_file(bar))).unwrap().unwrap();
367 assert_eq!(refs.len(), 2); 490 check_result(
491 refs,
492 "quux FN_DEF FileId(1) [18; 34) [25; 29)",
493 ReferenceKind::Other,
494 &["FileId(3) [16; 20) Other"],
495 );
368 } 496 }
369 497
370 #[test] 498 #[test]
@@ -379,11 +507,40 @@ mod tests {
379 }"#; 507 }"#;
380 508
381 let refs = get_all_refs(code); 509 let refs = get_all_refs(code);
382 assert_eq!(refs.len(), 3); 510 check_result(
511 refs,
512 "m1 MACRO_CALL FileId(1) [9; 63) [46; 48)",
513 ReferenceKind::Other,
514 &["FileId(1) [96; 98) Other", "FileId(1) [114; 116) Other"],
515 );
383 } 516 }
384 517
385 fn get_all_refs(text: &str) -> ReferenceSearchResult { 518 fn get_all_refs(text: &str) -> ReferenceSearchResult {
386 let (analysis, position) = single_file_with_position(text); 519 let (analysis, position) = single_file_with_position(text);
387 analysis.find_all_refs(position, None).unwrap().unwrap() 520 analysis.find_all_refs(position, None).unwrap().unwrap()
388 } 521 }
522
523 fn check_result(
524 res: ReferenceSearchResult,
525 expected_decl: &str,
526 decl_kind: ReferenceKind,
527 expected_refs: &[&str],
528 ) {
529 res.declaration().assert_match(expected_decl);
530 assert_eq!(res.declaration_kind, decl_kind);
531
532 assert_eq!(res.references.len(), expected_refs.len());
533 res.references().iter().enumerate().for_each(|(i, r)| r.assert_match(expected_refs[i]));
534 }
535
536 impl Reference {
537 fn debug_render(&self) -> String {
538 format!("{:?} {:?} {:?}", self.file_range.file_id, self.file_range.range, self.kind)
539 }
540
541 fn assert_match(&self, expected: &str) {
542 let actual = self.debug_render();
543 test_utils::assert_eq_text!(expected.trim(), actual.trim(),);
544 }
545 }
389} 546}
diff --git a/crates/ra_ide/src/references/rename.rs b/crates/ra_ide/src/references/rename.rs
index b804d5f6d..e02985dcd 100644
--- a/crates/ra_ide/src/references/rename.rs
+++ b/crates/ra_ide/src/references/rename.rs
@@ -110,7 +110,13 @@ fn rename_reference(
110 110
111 let edit = refs 111 let edit = refs
112 .into_iter() 112 .into_iter()
113 .map(|range| source_edit_from_file_id_range(range.file_id, range.range, new_name)) 113 .map(|reference| {
114 source_edit_from_file_id_range(
115 reference.file_range.file_id,
116 reference.file_range.range,
117 new_name,
118 )
119 })
114 .collect::<Vec<_>>(); 120 .collect::<Vec<_>>();
115 121
116 if edit.is_empty() { 122 if edit.is_empty() {
diff --git a/crates/ra_lsp_server/src/caps.rs b/crates/ra_lsp_server/src/caps.rs
index adfc9fb2c..c4711076c 100644
--- a/crates/ra_lsp_server/src/caps.rs
+++ b/crates/ra_lsp_server/src/caps.rs
@@ -1,8 +1,8 @@
1//! Advertizes the capabilities of the LSP Server. 1//! Advertizes the capabilities of the LSP Server.
2 2
3use lsp_types::{ 3use lsp_types::{
4 CodeActionProviderCapability, CodeLensOptions, CompletionOptions, 4 CallHierarchyServerCapability, CodeActionProviderCapability, CodeLensOptions,
5 DocumentOnTypeFormattingOptions, FoldingRangeProviderCapability, 5 CompletionOptions, DocumentOnTypeFormattingOptions, FoldingRangeProviderCapability,
6 ImplementationProviderCapability, RenameOptions, RenameProviderCapability, SaveOptions, 6 ImplementationProviderCapability, RenameOptions, RenameProviderCapability, SaveOptions,
7 SelectionRangeProviderCapability, ServerCapabilities, SignatureHelpOptions, 7 SelectionRangeProviderCapability, ServerCapabilities, SignatureHelpOptions,
8 TextDocumentSyncCapability, TextDocumentSyncKind, TextDocumentSyncOptions, 8 TextDocumentSyncCapability, TextDocumentSyncKind, TextDocumentSyncOptions,
@@ -56,6 +56,7 @@ pub fn server_capabilities() -> ServerCapabilities {
56 color_provider: None, 56 color_provider: None,
57 execute_command_provider: None, 57 execute_command_provider: None,
58 workspace: None, 58 workspace: None,
59 call_hierarchy_provider: Some(CallHierarchyServerCapability::Simple(true)),
59 experimental: Default::default(), 60 experimental: Default::default(),
60 } 61 }
61} 62}
diff --git a/crates/ra_lsp_server/src/conv.rs b/crates/ra_lsp_server/src/conv.rs
index e93d4ea33..c260b51c4 100644
--- a/crates/ra_lsp_server/src/conv.rs
+++ b/crates/ra_lsp_server/src/conv.rs
@@ -490,6 +490,24 @@ impl TryConvWith<&WorldSnapshot> for (FileId, RangeInfo<Vec<NavigationTarget>>)
490 } 490 }
491} 491}
492 492
493pub fn to_call_hierarchy_item(
494 file_id: FileId,
495 range: TextRange,
496 world: &WorldSnapshot,
497 line_index: &LineIndex,
498 nav: NavigationTarget,
499) -> Result<lsp_types::CallHierarchyItem> {
500 Ok(lsp_types::CallHierarchyItem {
501 name: nav.name().to_string(),
502 kind: nav.kind().conv(),
503 tags: None,
504 detail: nav.description().map(|it| it.to_string()),
505 uri: file_id.try_conv_with(&world)?,
506 range: nav.range().conv_with(&line_index),
507 selection_range: range.conv_with(&line_index),
508 })
509}
510
493pub fn to_location( 511pub fn to_location(
494 file_id: FileId, 512 file_id: FileId,
495 range: TextRange, 513 range: TextRange,
diff --git a/crates/ra_lsp_server/src/main_loop.rs b/crates/ra_lsp_server/src/main_loop.rs
index 53c6834d0..7a49cad86 100644
--- a/crates/ra_lsp_server/src/main_loop.rs
+++ b/crates/ra_lsp_server/src/main_loop.rs
@@ -504,6 +504,9 @@ fn on_request(
504 .on::<req::Formatting>(handlers::handle_formatting)? 504 .on::<req::Formatting>(handlers::handle_formatting)?
505 .on::<req::DocumentHighlightRequest>(handlers::handle_document_highlight)? 505 .on::<req::DocumentHighlightRequest>(handlers::handle_document_highlight)?
506 .on::<req::InlayHints>(handlers::handle_inlay_hints)? 506 .on::<req::InlayHints>(handlers::handle_inlay_hints)?
507 .on::<req::CallHierarchyPrepare>(handlers::handle_call_hierarchy_prepare)?
508 .on::<req::CallHierarchyIncomingCalls>(handlers::handle_call_hierarchy_incoming)?
509 .on::<req::CallHierarchyOutgoingCalls>(handlers::handle_call_hierarchy_outgoing)?
507 .finish(); 510 .finish();
508 Ok(()) 511 Ok(())
509} 512}
diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs
index 331beab13..a5b6f48af 100644
--- a/crates/ra_lsp_server/src/main_loop/handlers.rs
+++ b/crates/ra_lsp_server/src/main_loop/handlers.rs
@@ -5,13 +5,16 @@ use std::{fmt::Write as _, io::Write as _};
5 5
6use lsp_server::ErrorCode; 6use lsp_server::ErrorCode;
7use lsp_types::{ 7use lsp_types::{
8 CallHierarchyIncomingCall, CallHierarchyIncomingCallsParams, CallHierarchyItem,
9 CallHierarchyOutgoingCall, CallHierarchyOutgoingCallsParams, CallHierarchyPrepareParams,
8 CodeAction, CodeActionResponse, CodeLens, Command, CompletionItem, Diagnostic, 10 CodeAction, CodeActionResponse, CodeLens, Command, CompletionItem, Diagnostic,
9 DocumentFormattingParams, DocumentHighlight, DocumentSymbol, FoldingRange, FoldingRangeParams, 11 DocumentFormattingParams, DocumentHighlight, DocumentSymbol, FoldingRange, FoldingRangeParams,
10 Hover, HoverContents, Location, MarkupContent, MarkupKind, Position, PrepareRenameResponse, 12 Hover, HoverContents, Location, MarkupContent, MarkupKind, Position, PrepareRenameResponse,
11 Range, RenameParams, SymbolInformation, TextDocumentIdentifier, TextEdit, WorkspaceEdit, 13 Range, RenameParams, SymbolInformation, TextDocumentIdentifier, TextEdit, WorkspaceEdit,
12}; 14};
13use ra_ide::{ 15use ra_ide::{
14 AssistId, FileId, FilePosition, FileRange, Query, Runnable, RunnableKind, SearchScope, 16 AssistId, FileId, FilePosition, FileRange, Query, RangeInfo, Runnable, RunnableKind,
17 SearchScope,
15}; 18};
16use ra_prof::profile; 19use ra_prof::profile;
17use ra_syntax::{AstNode, SyntaxKind, TextRange, TextUnit}; 20use ra_syntax::{AstNode, SyntaxKind, TextRange, TextUnit};
@@ -21,7 +24,10 @@ use serde_json::to_value;
21 24
22use crate::{ 25use crate::{
23 cargo_target_spec::{runnable_args, CargoTargetSpec}, 26 cargo_target_spec::{runnable_args, CargoTargetSpec},
24 conv::{to_location, Conv, ConvWith, FoldConvCtx, MapConvWith, TryConvWith, TryConvWithToVec}, 27 conv::{
28 to_call_hierarchy_item, to_location, Conv, ConvWith, FoldConvCtx, MapConvWith, TryConvWith,
29 TryConvWithToVec,
30 },
25 req::{self, Decoration, InlayHint, InlayHintsParams, InlayKind}, 31 req::{self, Decoration, InlayHint, InlayHintsParams, InlayKind},
26 world::WorldSnapshot, 32 world::WorldSnapshot,
27 LspError, Result, 33 LspError, Result,
@@ -531,8 +537,8 @@ pub fn handle_references(
531 let locations = if params.context.include_declaration { 537 let locations = if params.context.include_declaration {
532 refs.into_iter() 538 refs.into_iter()
533 .filter_map(|r| { 539 .filter_map(|r| {
534 let line_index = world.analysis().file_line_index(r.file_id).ok()?; 540 let line_index = world.analysis().file_line_index(r.file_range.file_id).ok()?;
535 to_location(r.file_id, r.range, &world, &line_index).ok() 541 to_location(r.file_range.file_id, r.file_range.range, &world, &line_index).ok()
536 }) 542 })
537 .collect() 543 .collect()
538 } else { 544 } else {
@@ -540,8 +546,8 @@ pub fn handle_references(
540 refs.references() 546 refs.references()
541 .iter() 547 .iter()
542 .filter_map(|r| { 548 .filter_map(|r| {
543 let line_index = world.analysis().file_line_index(r.file_id).ok()?; 549 let line_index = world.analysis().file_line_index(r.file_range.file_id).ok()?;
544 to_location(r.file_id, r.range, &world, &line_index).ok() 550 to_location(r.file_range.file_id, r.file_range.range, &world, &line_index).ok()
545 }) 551 })
546 .collect() 552 .collect()
547 }; 553 };
@@ -830,8 +836,11 @@ pub fn handle_document_highlight(
830 836
831 Ok(Some( 837 Ok(Some(
832 refs.into_iter() 838 refs.into_iter()
833 .filter(|r| r.file_id == file_id) 839 .filter(|r| r.file_range.file_id == file_id)
834 .map(|r| DocumentHighlight { range: r.range.conv_with(&line_index), kind: None }) 840 .map(|r| DocumentHighlight {
841 range: r.file_range.range.conv_with(&line_index),
842 kind: None,
843 })
835 .collect(), 844 .collect(),
836 )) 845 ))
837} 846}
@@ -933,3 +942,91 @@ pub fn handle_inlay_hints(
933 }) 942 })
934 .collect()) 943 .collect())
935} 944}
945
946pub fn handle_call_hierarchy_prepare(
947 world: WorldSnapshot,
948 params: CallHierarchyPrepareParams,
949) -> Result<Option<Vec<CallHierarchyItem>>> {
950 let _p = profile("handle_call_hierarchy_prepare");
951 let position = params.text_document_position_params.try_conv_with(&world)?;
952 let file_id = position.file_id;
953
954 let nav_info = match world.analysis().call_hierarchy(position)? {
955 None => return Ok(None),
956 Some(it) => it,
957 };
958
959 let line_index = world.analysis().file_line_index(file_id)?;
960 let RangeInfo { range, info: navs } = nav_info;
961 let res = navs
962 .into_iter()
963 .filter(|it| it.kind() == SyntaxKind::FN_DEF)
964 .filter_map(|it| to_call_hierarchy_item(file_id, range, &world, &line_index, it).ok())
965 .collect();
966
967 Ok(Some(res))
968}
969
970pub fn handle_call_hierarchy_incoming(
971 world: WorldSnapshot,
972 params: CallHierarchyIncomingCallsParams,
973) -> Result<Option<Vec<CallHierarchyIncomingCall>>> {
974 let _p = profile("handle_call_hierarchy_incoming");
975 let item = params.item;
976
977 let doc = TextDocumentIdentifier::new(item.uri);
978 let frange: FileRange = (&doc, item.range).try_conv_with(&world)?;
979 let fpos = FilePosition { file_id: frange.file_id, offset: frange.range.start() };
980
981 let call_items = match world.analysis().incoming_calls(fpos)? {
982 None => return Ok(None),
983 Some(it) => it,
984 };
985
986 let mut res = vec![];
987
988 for call_item in call_items.into_iter() {
989 let file_id = call_item.target.file_id();
990 let line_index = world.analysis().file_line_index(file_id)?;
991 let range = call_item.target.range();
992 let item = to_call_hierarchy_item(file_id, range, &world, &line_index, call_item.target)?;
993 res.push(CallHierarchyIncomingCall {
994 from: item,
995 from_ranges: call_item.ranges.iter().map(|it| it.conv_with(&line_index)).collect(),
996 });
997 }
998
999 Ok(Some(res))
1000}
1001
1002pub fn handle_call_hierarchy_outgoing(
1003 world: WorldSnapshot,
1004 params: CallHierarchyOutgoingCallsParams,
1005) -> Result<Option<Vec<CallHierarchyOutgoingCall>>> {
1006 let _p = profile("handle_call_hierarchy_outgoing");
1007 let item = params.item;
1008
1009 let doc = TextDocumentIdentifier::new(item.uri);
1010 let frange: FileRange = (&doc, item.range).try_conv_with(&world)?;
1011 let fpos = FilePosition { file_id: frange.file_id, offset: frange.range.start() };
1012
1013 let call_items = match world.analysis().outgoing_calls(fpos)? {
1014 None => return Ok(None),
1015 Some(it) => it,
1016 };
1017
1018 let mut res = vec![];
1019
1020 for call_item in call_items.into_iter() {
1021 let file_id = call_item.target.file_id();
1022 let line_index = world.analysis().file_line_index(file_id)?;
1023 let range = call_item.target.range();
1024 let item = to_call_hierarchy_item(file_id, range, &world, &line_index, call_item.target)?;
1025 res.push(CallHierarchyOutgoingCall {
1026 to: item,
1027 from_ranges: call_item.ranges.iter().map(|it| it.conv_with(&line_index)).collect(),
1028 });
1029 }
1030
1031 Ok(Some(res))
1032}
diff --git a/crates/ra_lsp_server/src/req.rs b/crates/ra_lsp_server/src/req.rs
index 40edaf677..8098ff31d 100644
--- a/crates/ra_lsp_server/src/req.rs
+++ b/crates/ra_lsp_server/src/req.rs
@@ -6,13 +6,15 @@ use serde::{Deserialize, Serialize};
6 6
7pub use lsp_types::{ 7pub use lsp_types::{
8 notification::*, request::*, ApplyWorkspaceEditParams, CodeActionParams, CodeLens, 8 notification::*, request::*, ApplyWorkspaceEditParams, CodeActionParams, CodeLens,
9 CodeLensParams, CompletionParams, CompletionResponse, DidChangeConfigurationParams, 9 CodeLensParams, CompletionParams, CompletionResponse, DiagnosticTag,
10 DidChangeWatchedFilesParams, DidChangeWatchedFilesRegistrationOptions, 10 DidChangeConfigurationParams, DidChangeWatchedFilesParams,
11 DocumentOnTypeFormattingParams, DocumentSymbolParams, DocumentSymbolResponse, 11 DidChangeWatchedFilesRegistrationOptions, DocumentOnTypeFormattingParams, DocumentSymbolParams,
12 FileSystemWatcher, Hover, InitializeResult, MessageType, ProgressParams, ProgressParamsValue, 12 DocumentSymbolResponse, FileSystemWatcher, Hover, InitializeResult, MessageType,
13 ProgressToken, PublishDiagnosticsParams, ReferenceParams, Registration, RegistrationParams, 13 PartialResultParams, ProgressParams, ProgressParamsValue, ProgressToken,
14 SelectionRange, SelectionRangeParams, ShowMessageParams, SignatureHelp, TextDocumentEdit, 14 PublishDiagnosticsParams, ReferenceParams, Registration, RegistrationParams, SelectionRange,
15 TextDocumentPositionParams, TextEdit, WorkspaceEdit, WorkspaceSymbolParams, 15 SelectionRangeParams, ServerCapabilities, ShowMessageParams, SignatureHelp, SymbolKind,
16 TextDocumentEdit, TextDocumentPositionParams, TextEdit, WorkDoneProgressParams, WorkspaceEdit,
17 WorkspaceSymbolParams,
16}; 18};
17 19
18pub enum AnalyzerStatus {} 20pub enum AnalyzerStatus {}
diff --git a/crates/ra_parser/src/grammar/items/traits.rs b/crates/ra_parser/src/grammar/items/traits.rs
index 2c560e824..964fd3041 100644
--- a/crates/ra_parser/src/grammar/items/traits.rs
+++ b/crates/ra_parser/src/grammar/items/traits.rs
@@ -100,6 +100,8 @@ pub(crate) fn impl_item_list(p: &mut Parser) {
100 m.complete(p, ITEM_LIST); 100 m.complete(p, ITEM_LIST);
101} 101}
102 102
103// test impl_type_params
104// impl<const N: u32> Bar<N> {}
103fn choose_type_params_over_qpath(p: &Parser) -> bool { 105fn choose_type_params_over_qpath(p: &Parser) -> bool {
104 // There's an ambiguity between generic parameters and qualified paths in impls. 106 // There's an ambiguity between generic parameters and qualified paths in impls.
105 // If we see `<` it may start both, so we have to inspect some following tokens. 107 // If we see `<` it may start both, so we have to inspect some following tokens.
@@ -107,6 +109,7 @@ fn choose_type_params_over_qpath(p: &Parser) -> bool {
107 // but not qualified paths (with one exception): 109 // but not qualified paths (with one exception):
108 // `<` `>` - empty generic parameters 110 // `<` `>` - empty generic parameters
109 // `<` `#` - generic parameters with attributes 111 // `<` `#` - generic parameters with attributes
112 // `<` `const` - const generic parameters
110 // `<` (LIFETIME|IDENT) `>` - single generic parameter 113 // `<` (LIFETIME|IDENT) `>` - single generic parameter
111 // `<` (LIFETIME|IDENT) `,` - first generic parameter in a list 114 // `<` (LIFETIME|IDENT) `,` - first generic parameter in a list
112 // `<` (LIFETIME|IDENT) `:` - generic parameter with bounds 115 // `<` (LIFETIME|IDENT) `:` - generic parameter with bounds
@@ -119,7 +122,7 @@ fn choose_type_params_over_qpath(p: &Parser) -> bool {
119 if !p.at(T![<]) { 122 if !p.at(T![<]) {
120 return false; 123 return false;
121 } 124 }
122 if p.nth(1) == T![#] || p.nth(1) == T![>] { 125 if p.nth(1) == T![#] || p.nth(1) == T![>] || p.nth(1) == CONST_KW {
123 return true; 126 return true;
124 } 127 }
125 (p.nth(1) == LIFETIME || p.nth(1) == IDENT) 128 (p.nth(1) == LIFETIME || p.nth(1) == IDENT)
diff --git a/crates/ra_parser/src/grammar/type_args.rs b/crates/ra_parser/src/grammar/type_args.rs
index 7256c2697..33d9973e9 100644
--- a/crates/ra_parser/src/grammar/type_args.rs
+++ b/crates/ra_parser/src/grammar/type_args.rs
@@ -26,7 +26,7 @@ pub(super) fn opt_type_arg_list(p: &mut Parser, colon_colon_required: bool) {
26} 26}
27 27
28// test type_arg 28// test type_arg
29// type A = B<'static, i32, Item=u64>; 29// type A = B<'static, i32, 1, { 2 }, Item=u64>;
30fn type_arg(p: &mut Parser) { 30fn type_arg(p: &mut Parser) {
31 let m = p.start(); 31 let m = p.start();
32 match p.current() { 32 match p.current() {
@@ -47,6 +47,14 @@ fn type_arg(p: &mut Parser) {
47 types::type_(p); 47 types::type_(p);
48 m.complete(p, ASSOC_TYPE_ARG); 48 m.complete(p, ASSOC_TYPE_ARG);
49 } 49 }
50 T!['{'] => {
51 expressions::block(p);
52 m.complete(p, CONST_ARG);
53 }
54 k if k.is_literal() => {
55 p.bump(k);
56 m.complete(p, CONST_ARG);
57 }
50 _ => { 58 _ => {
51 types::type_(p); 59 types::type_(p);
52 m.complete(p, TYPE_ARG); 60 m.complete(p, TYPE_ARG);
diff --git a/crates/ra_parser/src/syntax_kind/generated.rs b/crates/ra_parser/src/syntax_kind/generated.rs
index af2945f57..4b301d67a 100644
--- a/crates/ra_parser/src/syntax_kind/generated.rs
+++ b/crates/ra_parser/src/syntax_kind/generated.rs
@@ -61,46 +61,46 @@ pub enum SyntaxKind {
61 SHR, 61 SHR,
62 SHLEQ, 62 SHLEQ,
63 SHREQ, 63 SHREQ,
64 AS_KW,
64 ASYNC_KW, 65 ASYNC_KW,
65 USE_KW, 66 AWAIT_KW,
66 FN_KW, 67 BOX_KW,
67 STRUCT_KW, 68 BREAK_KW,
68 ENUM_KW, 69 CONST_KW,
69 TRAIT_KW, 70 CONTINUE_KW,
70 IMPL_KW, 71 CRATE_KW,
71 DYN_KW, 72 DYN_KW,
72 TRUE_KW, 73 ELSE_KW,
73 FALSE_KW, 74 ENUM_KW,
74 AS_KW,
75 EXTERN_KW, 75 EXTERN_KW,
76 CRATE_KW, 76 FALSE_KW,
77 MOD_KW, 77 FN_KW,
78 PUB_KW,
79 SELF_KW,
80 SUPER_KW,
81 IN_KW,
82 WHERE_KW,
83 FOR_KW, 78 FOR_KW,
84 LOOP_KW,
85 WHILE_KW,
86 CONTINUE_KW,
87 BREAK_KW,
88 IF_KW, 79 IF_KW,
89 ELSE_KW, 80 IMPL_KW,
81 IN_KW,
82 LET_KW,
83 LOOP_KW,
84 MACRO_KW,
90 MATCH_KW, 85 MATCH_KW,
91 CONST_KW, 86 MOD_KW,
92 STATIC_KW, 87 MOVE_KW,
93 MUT_KW, 88 MUT_KW,
94 UNSAFE_KW, 89 PUB_KW,
95 TYPE_KW,
96 REF_KW, 90 REF_KW,
97 LET_KW,
98 MOVE_KW,
99 RETURN_KW, 91 RETURN_KW,
92 SELF_KW,
93 STATIC_KW,
94 STRUCT_KW,
95 SUPER_KW,
96 TRAIT_KW,
97 TRUE_KW,
100 TRY_KW, 98 TRY_KW,
101 BOX_KW, 99 TYPE_KW,
102 AWAIT_KW, 100 UNSAFE_KW,
103 MACRO_KW, 101 USE_KW,
102 WHERE_KW,
103 WHILE_KW,
104 AUTO_KW, 104 AUTO_KW,
105 DEFAULT_KW, 105 DEFAULT_KW,
106 EXISTENTIAL_KW, 106 EXISTENTIAL_KW,
@@ -234,6 +234,7 @@ pub enum SyntaxKind {
234 LIFETIME_ARG, 234 LIFETIME_ARG,
235 TYPE_ARG, 235 TYPE_ARG,
236 ASSOC_TYPE_ARG, 236 ASSOC_TYPE_ARG,
237 CONST_ARG,
237 PARAM_LIST, 238 PARAM_LIST,
238 PARAM, 239 PARAM,
239 SELF_PARAM, 240 SELF_PARAM,
@@ -249,12 +250,12 @@ use self::SyntaxKind::*;
249impl SyntaxKind { 250impl SyntaxKind {
250 pub fn is_keyword(self) -> bool { 251 pub fn is_keyword(self) -> bool {
251 match self { 252 match self {
252 ASYNC_KW | USE_KW | FN_KW | STRUCT_KW | ENUM_KW | TRAIT_KW | IMPL_KW | DYN_KW 253 AS_KW | ASYNC_KW | AWAIT_KW | BOX_KW | BREAK_KW | CONST_KW | CONTINUE_KW | CRATE_KW
253 | TRUE_KW | FALSE_KW | AS_KW | EXTERN_KW | CRATE_KW | MOD_KW | PUB_KW | SELF_KW 254 | DYN_KW | ELSE_KW | ENUM_KW | EXTERN_KW | FALSE_KW | FN_KW | FOR_KW | IF_KW
254 | SUPER_KW | IN_KW | WHERE_KW | FOR_KW | LOOP_KW | WHILE_KW | CONTINUE_KW 255 | IMPL_KW | IN_KW | LET_KW | LOOP_KW | MACRO_KW | MATCH_KW | MOD_KW | MOVE_KW
255 | BREAK_KW | IF_KW | ELSE_KW | MATCH_KW | CONST_KW | STATIC_KW | MUT_KW | UNSAFE_KW 256 | MUT_KW | PUB_KW | REF_KW | RETURN_KW | SELF_KW | STATIC_KW | STRUCT_KW | SUPER_KW
256 | TYPE_KW | REF_KW | LET_KW | MOVE_KW | RETURN_KW | TRY_KW | BOX_KW | AWAIT_KW 257 | TRAIT_KW | TRUE_KW | TRY_KW | TYPE_KW | UNSAFE_KW | USE_KW | WHERE_KW | WHILE_KW
257 | MACRO_KW | AUTO_KW | DEFAULT_KW | EXISTENTIAL_KW | UNION_KW => true, 258 | AUTO_KW | DEFAULT_KW | EXISTENTIAL_KW | UNION_KW => true,
258 _ => false, 259 _ => false,
259 } 260 }
260 } 261 }
@@ -278,46 +279,46 @@ impl SyntaxKind {
278 } 279 }
279 pub fn from_keyword(ident: &str) -> Option<SyntaxKind> { 280 pub fn from_keyword(ident: &str) -> Option<SyntaxKind> {
280 let kw = match ident { 281 let kw = match ident {
282 "as" => AS_KW,
281 "async" => ASYNC_KW, 283 "async" => ASYNC_KW,
282 "use" => USE_KW, 284 "await" => AWAIT_KW,
283 "fn" => FN_KW, 285 "box" => BOX_KW,
284 "struct" => STRUCT_KW, 286 "break" => BREAK_KW,
285 "enum" => ENUM_KW, 287 "const" => CONST_KW,
286 "trait" => TRAIT_KW, 288 "continue" => CONTINUE_KW,
287 "impl" => IMPL_KW, 289 "crate" => CRATE_KW,
288 "dyn" => DYN_KW, 290 "dyn" => DYN_KW,
289 "true" => TRUE_KW, 291 "else" => ELSE_KW,
290 "false" => FALSE_KW, 292 "enum" => ENUM_KW,
291 "as" => AS_KW,
292 "extern" => EXTERN_KW, 293 "extern" => EXTERN_KW,
293 "crate" => CRATE_KW, 294 "false" => FALSE_KW,
294 "mod" => MOD_KW, 295 "fn" => FN_KW,
295 "pub" => PUB_KW,
296 "self" => SELF_KW,
297 "super" => SUPER_KW,
298 "in" => IN_KW,
299 "where" => WHERE_KW,
300 "for" => FOR_KW, 296 "for" => FOR_KW,
301 "loop" => LOOP_KW,
302 "while" => WHILE_KW,
303 "continue" => CONTINUE_KW,
304 "break" => BREAK_KW,
305 "if" => IF_KW, 297 "if" => IF_KW,
306 "else" => ELSE_KW, 298 "impl" => IMPL_KW,
299 "in" => IN_KW,
300 "let" => LET_KW,
301 "loop" => LOOP_KW,
302 "macro" => MACRO_KW,
307 "match" => MATCH_KW, 303 "match" => MATCH_KW,
308 "const" => CONST_KW, 304 "mod" => MOD_KW,
309 "static" => STATIC_KW, 305 "move" => MOVE_KW,
310 "mut" => MUT_KW, 306 "mut" => MUT_KW,
311 "unsafe" => UNSAFE_KW, 307 "pub" => PUB_KW,
312 "type" => TYPE_KW,
313 "ref" => REF_KW, 308 "ref" => REF_KW,
314 "let" => LET_KW,
315 "move" => MOVE_KW,
316 "return" => RETURN_KW, 309 "return" => RETURN_KW,
310 "self" => SELF_KW,
311 "static" => STATIC_KW,
312 "struct" => STRUCT_KW,
313 "super" => SUPER_KW,
314 "trait" => TRAIT_KW,
315 "true" => TRUE_KW,
317 "try" => TRY_KW, 316 "try" => TRY_KW,
318 "box" => BOX_KW, 317 "type" => TYPE_KW,
319 "await" => AWAIT_KW, 318 "unsafe" => UNSAFE_KW,
320 "macro" => MACRO_KW, 319 "use" => USE_KW,
320 "where" => WHERE_KW,
321 "while" => WHILE_KW,
321 _ => return None, 322 _ => return None,
322 }; 323 };
323 Some(kw) 324 Some(kw)
@@ -515,125 +516,125 @@ macro_rules! T {
515 ( >>= ) => { 516 ( >>= ) => {
516 $crate::SyntaxKind::SHREQ 517 $crate::SyntaxKind::SHREQ
517 }; 518 };
519 ( as ) => {
520 $crate::SyntaxKind::AS_KW
521 };
518 ( async ) => { 522 ( async ) => {
519 $crate::SyntaxKind::ASYNC_KW 523 $crate::SyntaxKind::ASYNC_KW
520 }; 524 };
521 ( use ) => { 525 ( await ) => {
522 $crate::SyntaxKind::USE_KW 526 $crate::SyntaxKind::AWAIT_KW
523 }; 527 };
524 ( fn ) => { 528 ( box ) => {
525 $crate::SyntaxKind::FN_KW 529 $crate::SyntaxKind::BOX_KW
526 }; 530 };
527 ( struct ) => { 531 ( break ) => {
528 $crate::SyntaxKind::STRUCT_KW 532 $crate::SyntaxKind::BREAK_KW
529 }; 533 };
530 ( enum ) => { 534 ( const ) => {
531 $crate::SyntaxKind::ENUM_KW 535 $crate::SyntaxKind::CONST_KW
532 }; 536 };
533 ( trait ) => { 537 ( continue ) => {
534 $crate::SyntaxKind::TRAIT_KW 538 $crate::SyntaxKind::CONTINUE_KW
535 }; 539 };
536 ( impl ) => { 540 ( crate ) => {
537 $crate::SyntaxKind::IMPL_KW 541 $crate::SyntaxKind::CRATE_KW
538 }; 542 };
539 ( dyn ) => { 543 ( dyn ) => {
540 $crate::SyntaxKind::DYN_KW 544 $crate::SyntaxKind::DYN_KW
541 }; 545 };
542 ( true ) => { 546 ( else ) => {
543 $crate::SyntaxKind::TRUE_KW 547 $crate::SyntaxKind::ELSE_KW
544 };
545 ( false ) => {
546 $crate::SyntaxKind::FALSE_KW
547 }; 548 };
548 ( as ) => { 549 ( enum ) => {
549 $crate::SyntaxKind::AS_KW 550 $crate::SyntaxKind::ENUM_KW
550 }; 551 };
551 ( extern ) => { 552 ( extern ) => {
552 $crate::SyntaxKind::EXTERN_KW 553 $crate::SyntaxKind::EXTERN_KW
553 }; 554 };
554 ( crate ) => { 555 ( false ) => {
555 $crate::SyntaxKind::CRATE_KW 556 $crate::SyntaxKind::FALSE_KW
556 }; 557 };
557 ( mod ) => { 558 ( fn ) => {
558 $crate::SyntaxKind::MOD_KW 559 $crate::SyntaxKind::FN_KW
559 }; 560 };
560 ( pub ) => { 561 ( for ) => {
561 $crate::SyntaxKind::PUB_KW 562 $crate::SyntaxKind::FOR_KW
562 }; 563 };
563 ( self ) => { 564 ( if ) => {
564 $crate::SyntaxKind::SELF_KW 565 $crate::SyntaxKind::IF_KW
565 }; 566 };
566 ( super ) => { 567 ( impl ) => {
567 $crate::SyntaxKind::SUPER_KW 568 $crate::SyntaxKind::IMPL_KW
568 }; 569 };
569 ( in ) => { 570 ( in ) => {
570 $crate::SyntaxKind::IN_KW 571 $crate::SyntaxKind::IN_KW
571 }; 572 };
572 ( where ) => { 573 ( let ) => {
573 $crate::SyntaxKind::WHERE_KW 574 $crate::SyntaxKind::LET_KW
574 };
575 ( for ) => {
576 $crate::SyntaxKind::FOR_KW
577 }; 575 };
578 ( loop ) => { 576 ( loop ) => {
579 $crate::SyntaxKind::LOOP_KW 577 $crate::SyntaxKind::LOOP_KW
580 }; 578 };
581 ( while ) => { 579 ( macro ) => {
582 $crate::SyntaxKind::WHILE_KW 580 $crate::SyntaxKind::MACRO_KW
583 };
584 ( continue ) => {
585 $crate::SyntaxKind::CONTINUE_KW
586 };
587 ( break ) => {
588 $crate::SyntaxKind::BREAK_KW
589 };
590 ( if ) => {
591 $crate::SyntaxKind::IF_KW
592 };
593 ( else ) => {
594 $crate::SyntaxKind::ELSE_KW
595 }; 581 };
596 ( match ) => { 582 ( match ) => {
597 $crate::SyntaxKind::MATCH_KW 583 $crate::SyntaxKind::MATCH_KW
598 }; 584 };
599 ( const ) => { 585 ( mod ) => {
600 $crate::SyntaxKind::CONST_KW 586 $crate::SyntaxKind::MOD_KW
601 }; 587 };
602 ( static ) => { 588 ( move ) => {
603 $crate::SyntaxKind::STATIC_KW 589 $crate::SyntaxKind::MOVE_KW
604 }; 590 };
605 ( mut ) => { 591 ( mut ) => {
606 $crate::SyntaxKind::MUT_KW 592 $crate::SyntaxKind::MUT_KW
607 }; 593 };
608 ( unsafe ) => { 594 ( pub ) => {
609 $crate::SyntaxKind::UNSAFE_KW 595 $crate::SyntaxKind::PUB_KW
610 };
611 ( type ) => {
612 $crate::SyntaxKind::TYPE_KW
613 }; 596 };
614 ( ref ) => { 597 ( ref ) => {
615 $crate::SyntaxKind::REF_KW 598 $crate::SyntaxKind::REF_KW
616 }; 599 };
617 ( let ) => {
618 $crate::SyntaxKind::LET_KW
619 };
620 ( move ) => {
621 $crate::SyntaxKind::MOVE_KW
622 };
623 ( return ) => { 600 ( return ) => {
624 $crate::SyntaxKind::RETURN_KW 601 $crate::SyntaxKind::RETURN_KW
625 }; 602 };
603 ( self ) => {
604 $crate::SyntaxKind::SELF_KW
605 };
606 ( static ) => {
607 $crate::SyntaxKind::STATIC_KW
608 };
609 ( struct ) => {
610 $crate::SyntaxKind::STRUCT_KW
611 };
612 ( super ) => {
613 $crate::SyntaxKind::SUPER_KW
614 };
615 ( trait ) => {
616 $crate::SyntaxKind::TRAIT_KW
617 };
618 ( true ) => {
619 $crate::SyntaxKind::TRUE_KW
620 };
626 ( try ) => { 621 ( try ) => {
627 $crate::SyntaxKind::TRY_KW 622 $crate::SyntaxKind::TRY_KW
628 }; 623 };
629 ( box ) => { 624 ( type ) => {
630 $crate::SyntaxKind::BOX_KW 625 $crate::SyntaxKind::TYPE_KW
631 }; 626 };
632 ( await ) => { 627 ( unsafe ) => {
633 $crate::SyntaxKind::AWAIT_KW 628 $crate::SyntaxKind::UNSAFE_KW
634 }; 629 };
635 ( macro ) => { 630 ( use ) => {
636 $crate::SyntaxKind::MACRO_KW 631 $crate::SyntaxKind::USE_KW
632 };
633 ( where ) => {
634 $crate::SyntaxKind::WHERE_KW
635 };
636 ( while ) => {
637 $crate::SyntaxKind::WHILE_KW
637 }; 638 };
638 ( auto ) => { 639 ( auto ) => {
639 $crate::SyntaxKind::AUTO_KW 640 $crate::SyntaxKind::AUTO_KW
diff --git a/crates/ra_prof/src/lib.rs b/crates/ra_prof/src/lib.rs
index f260c40a3..6dde304b1 100644
--- a/crates/ra_prof/src/lib.rs
+++ b/crates/ra_prof/src/lib.rs
@@ -197,7 +197,10 @@ impl Drop for Profiler {
197 if level == 0 { 197 if level == 0 {
198 let stdout = stderr(); 198 let stdout = stderr();
199 let longer_than = stack.filter_data.longer_than; 199 let longer_than = stack.filter_data.longer_than;
200 if duration >= longer_than { 200 // Convert to millis for comparison to avoid problems with rounding
201 // (otherwise we could print `0ms` despite user's `>0` filter when
202 // `duration` is just a few nanos).
203 if duration.as_millis() > longer_than.as_millis() {
201 print(0, &stack.messages, &mut stdout.lock(), longer_than, None); 204 print(0, &stack.messages, &mut stdout.lock(), longer_than, None);
202 } 205 }
203 stack.messages.clear(); 206 stack.messages.clear();
@@ -226,7 +229,7 @@ fn print(
226 continue; 229 continue;
227 } 230 }
228 accounted_for += duration; 231 accounted_for += duration;
229 if duration >= longer_than { 232 if duration.as_millis() > longer_than.as_millis() {
230 writeln!(out, "{}{:5}ms - {}", indent, duration.as_millis(), msg) 233 writeln!(out, "{}{:5}ms - {}", indent, duration.as_millis(), msg)
231 .expect("printing profiling info to stdout"); 234 .expect("printing profiling info to stdout");
232 235
@@ -251,8 +254,9 @@ fn print(
251 254
252 if let Some(total) = total { 255 if let Some(total) = total {
253 if let Some(unaccounted) = total.checked_sub(accounted_for) { 256 if let Some(unaccounted) = total.checked_sub(accounted_for) {
254 if unaccounted >= longer_than && last > 0 { 257 let unaccounted_millis = unaccounted.as_millis();
255 writeln!(out, "{}{:5}ms - ???", indent, unaccounted.as_millis()) 258 if unaccounted_millis > longer_than.as_millis() && unaccounted_millis > 0 && last > 0 {
259 writeln!(out, "{}{:5}ms - ???", indent, unaccounted_millis)
256 .expect("printing profiling info to stdout"); 260 .expect("printing profiling info to stdout");
257 } 261 }
258 } 262 }
@@ -356,4 +360,21 @@ mod tests {
356 fn profiling_function2() { 360 fn profiling_function2() {
357 let _p = profile("profile2"); 361 let _p = profile("profile2");
358 } 362 }
363
364 #[test]
365 fn test_longer_than() {
366 let mut result = vec![];
367 let msgs = vec![
368 Message { level: 1, duration: Duration::from_nanos(3), message: "bar".to_owned() },
369 Message { level: 1, duration: Duration::from_nanos(2), message: "bar".to_owned() },
370 Message { level: 0, duration: Duration::from_millis(1), message: "foo".to_owned() },
371 ];
372 print(0, &msgs, &mut result, Duration::from_millis(0), Some(Duration::from_millis(1)));
373 // The calls to `bar` are so short that they'll be rounded to 0ms and should get collapsed
374 // when printing.
375 assert_eq!(
376 std::str::from_utf8(&result).unwrap(),
377 " 1ms - foo\n 0ms - bar (2 calls)\n"
378 );
379 }
359} 380}
diff --git a/crates/ra_project_model/src/sysroot.rs b/crates/ra_project_model/src/sysroot.rs
index 10ca391b6..34d066b1e 100644
--- a/crates/ra_project_model/src/sysroot.rs
+++ b/crates/ra_project_model/src/sysroot.rs
@@ -53,9 +53,10 @@ impl Sysroot {
53 if !src.exists() { 53 if !src.exists() {
54 Err(format!( 54 Err(format!(
55 "can't load standard library from sysroot\n\ 55 "can't load standard library from sysroot\n\
56 {:?}\n\ 56 {}\n\
57 (discovered via `rustc --print sysroot`)\n\
57 try running `rustup component add rust-src` or set `RUST_SRC_PATH`", 58 try running `rustup component add rust-src` or set `RUST_SRC_PATH`",
58 src, 59 src.display(),
59 ))?; 60 ))?;
60 } 61 }
61 62
diff --git a/crates/ra_syntax/src/ast/expr_extensions.rs b/crates/ra_syntax/src/ast/expr_extensions.rs
index 2fd039837..23b6aa901 100644
--- a/crates/ra_syntax/src/ast/expr_extensions.rs
+++ b/crates/ra_syntax/src/ast/expr_extensions.rs
@@ -126,6 +126,24 @@ pub enum BinOp {
126 BitXorAssign, 126 BitXorAssign,
127} 127}
128 128
129impl BinOp {
130 pub fn is_assignment(&self) -> bool {
131 match *self {
132 BinOp::Assignment
133 | BinOp::AddAssign
134 | BinOp::DivAssign
135 | BinOp::MulAssign
136 | BinOp::RemAssign
137 | BinOp::ShrAssign
138 | BinOp::ShlAssign
139 | BinOp::SubAssign
140 | BinOp::BitOrAssign
141 | BinOp::BitAndAssign
142 | BinOp::BitXorAssign => true,
143 _ => false,
144 }
145 }
146}
129impl ast::BinExpr { 147impl ast::BinExpr {
130 pub fn op_details(&self) -> Option<(SyntaxToken, BinOp)> { 148 pub fn op_details(&self) -> Option<(SyntaxToken, BinOp)> {
131 self.syntax().children_with_tokens().filter_map(|it| it.into_token()).find_map(|c| { 149 self.syntax().children_with_tokens().filter_map(|it| it.into_token()).find_map(|c| {
diff --git a/crates/ra_syntax/src/ast/generated.rs b/crates/ra_syntax/src/ast/generated.rs
index e64c83d33..33d5578e7 100644
--- a/crates/ra_syntax/src/ast/generated.rs
+++ b/crates/ra_syntax/src/ast/generated.rs
@@ -6,13 +6,13 @@ use crate::{
6 SyntaxNode, 6 SyntaxNode,
7}; 7};
8#[derive(Debug, Clone, PartialEq, Eq, Hash)] 8#[derive(Debug, Clone, PartialEq, Eq, Hash)]
9pub struct Alias { 9pub struct SourceFile {
10 pub(crate) syntax: SyntaxNode, 10 pub(crate) syntax: SyntaxNode,
11} 11}
12impl AstNode for Alias { 12impl AstNode for SourceFile {
13 fn can_cast(kind: SyntaxKind) -> bool { 13 fn can_cast(kind: SyntaxKind) -> bool {
14 match kind { 14 match kind {
15 ALIAS => true, 15 SOURCE_FILE => true,
16 _ => false, 16 _ => false,
17 } 17 }
18 } 18 }
@@ -27,16 +27,21 @@ impl AstNode for Alias {
27 &self.syntax 27 &self.syntax
28 } 28 }
29} 29}
30impl ast::NameOwner for Alias {} 30impl ast::ModuleItemOwner for SourceFile {}
31impl Alias {} 31impl ast::FnDefOwner for SourceFile {}
32impl SourceFile {
33 pub fn modules(&self) -> AstChildren<Module> {
34 AstChildren::new(&self.syntax)
35 }
36}
32#[derive(Debug, Clone, PartialEq, Eq, Hash)] 37#[derive(Debug, Clone, PartialEq, Eq, Hash)]
33pub struct ArgList { 38pub struct FnDef {
34 pub(crate) syntax: SyntaxNode, 39 pub(crate) syntax: SyntaxNode,
35} 40}
36impl AstNode for ArgList { 41impl AstNode for FnDef {
37 fn can_cast(kind: SyntaxKind) -> bool { 42 fn can_cast(kind: SyntaxKind) -> bool {
38 match kind { 43 match kind {
39 ARG_LIST => true, 44 FN_DEF => true,
40 _ => false, 45 _ => false,
41 } 46 }
42 } 47 }
@@ -51,19 +56,30 @@ impl AstNode for ArgList {
51 &self.syntax 56 &self.syntax
52 } 57 }
53} 58}
54impl ArgList { 59impl ast::VisibilityOwner for FnDef {}
55 pub fn args(&self) -> AstChildren<Expr> { 60impl ast::NameOwner for FnDef {}
56 AstChildren::new(&self.syntax) 61impl ast::TypeParamsOwner for FnDef {}
62impl ast::DocCommentsOwner for FnDef {}
63impl ast::AttrsOwner for FnDef {}
64impl FnDef {
65 pub fn param_list(&self) -> Option<ParamList> {
66 AstChildren::new(&self.syntax).next()
67 }
68 pub fn ret_type(&self) -> Option<RetType> {
69 AstChildren::new(&self.syntax).next()
70 }
71 pub fn body(&self) -> Option<BlockExpr> {
72 AstChildren::new(&self.syntax).next()
57 } 73 }
58} 74}
59#[derive(Debug, Clone, PartialEq, Eq, Hash)] 75#[derive(Debug, Clone, PartialEq, Eq, Hash)]
60pub struct ArrayExpr { 76pub struct RetType {
61 pub(crate) syntax: SyntaxNode, 77 pub(crate) syntax: SyntaxNode,
62} 78}
63impl AstNode for ArrayExpr { 79impl AstNode for RetType {
64 fn can_cast(kind: SyntaxKind) -> bool { 80 fn can_cast(kind: SyntaxKind) -> bool {
65 match kind { 81 match kind {
66 ARRAY_EXPR => true, 82 RET_TYPE => true,
67 _ => false, 83 _ => false,
68 } 84 }
69 } 85 }
@@ -78,19 +94,19 @@ impl AstNode for ArrayExpr {
78 &self.syntax 94 &self.syntax
79 } 95 }
80} 96}
81impl ArrayExpr { 97impl RetType {
82 pub fn exprs(&self) -> AstChildren<Expr> { 98 pub fn type_ref(&self) -> Option<TypeRef> {
83 AstChildren::new(&self.syntax) 99 AstChildren::new(&self.syntax).next()
84 } 100 }
85} 101}
86#[derive(Debug, Clone, PartialEq, Eq, Hash)] 102#[derive(Debug, Clone, PartialEq, Eq, Hash)]
87pub struct ArrayType { 103pub struct StructDef {
88 pub(crate) syntax: SyntaxNode, 104 pub(crate) syntax: SyntaxNode,
89} 105}
90impl AstNode for ArrayType { 106impl AstNode for StructDef {
91 fn can_cast(kind: SyntaxKind) -> bool { 107 fn can_cast(kind: SyntaxKind) -> bool {
92 match kind { 108 match kind {
93 ARRAY_TYPE => true, 109 STRUCT_DEF => true,
94 _ => false, 110 _ => false,
95 } 111 }
96 } 112 }
@@ -105,22 +121,20 @@ impl AstNode for ArrayType {
105 &self.syntax 121 &self.syntax
106 } 122 }
107} 123}
108impl ArrayType { 124impl ast::VisibilityOwner for StructDef {}
109 pub fn type_ref(&self) -> Option<TypeRef> { 125impl ast::NameOwner for StructDef {}
110 AstChildren::new(&self.syntax).next() 126impl ast::TypeParamsOwner for StructDef {}
111 } 127impl ast::AttrsOwner for StructDef {}
112 pub fn expr(&self) -> Option<Expr> { 128impl ast::DocCommentsOwner for StructDef {}
113 AstChildren::new(&self.syntax).next() 129impl StructDef {}
114 }
115}
116#[derive(Debug, Clone, PartialEq, Eq, Hash)] 130#[derive(Debug, Clone, PartialEq, Eq, Hash)]
117pub struct AssocTypeArg { 131pub struct UnionDef {
118 pub(crate) syntax: SyntaxNode, 132 pub(crate) syntax: SyntaxNode,
119} 133}
120impl AstNode for AssocTypeArg { 134impl AstNode for UnionDef {
121 fn can_cast(kind: SyntaxKind) -> bool { 135 fn can_cast(kind: SyntaxKind) -> bool {
122 match kind { 136 match kind {
123 ASSOC_TYPE_ARG => true, 137 UNION_DEF => true,
124 _ => false, 138 _ => false,
125 } 139 }
126 } 140 }
@@ -135,22 +149,24 @@ impl AstNode for AssocTypeArg {
135 &self.syntax 149 &self.syntax
136 } 150 }
137} 151}
138impl AssocTypeArg { 152impl ast::VisibilityOwner for UnionDef {}
139 pub fn name_ref(&self) -> Option<NameRef> { 153impl ast::NameOwner for UnionDef {}
140 AstChildren::new(&self.syntax).next() 154impl ast::TypeParamsOwner for UnionDef {}
141 } 155impl ast::AttrsOwner for UnionDef {}
142 pub fn type_ref(&self) -> Option<TypeRef> { 156impl ast::DocCommentsOwner for UnionDef {}
157impl UnionDef {
158 pub fn record_field_def_list(&self) -> Option<RecordFieldDefList> {
143 AstChildren::new(&self.syntax).next() 159 AstChildren::new(&self.syntax).next()
144 } 160 }
145} 161}
146#[derive(Debug, Clone, PartialEq, Eq, Hash)] 162#[derive(Debug, Clone, PartialEq, Eq, Hash)]
147pub struct Attr { 163pub struct RecordFieldDefList {
148 pub(crate) syntax: SyntaxNode, 164 pub(crate) syntax: SyntaxNode,
149} 165}
150impl AstNode for Attr { 166impl AstNode for RecordFieldDefList {
151 fn can_cast(kind: SyntaxKind) -> bool { 167 fn can_cast(kind: SyntaxKind) -> bool {
152 match kind { 168 match kind {
153 ATTR => true, 169 RECORD_FIELD_DEF_LIST => true,
154 _ => false, 170 _ => false,
155 } 171 }
156 } 172 }
@@ -165,60 +181,47 @@ impl AstNode for Attr {
165 &self.syntax 181 &self.syntax
166 } 182 }
167} 183}
168impl Attr { 184impl RecordFieldDefList {
169 pub fn path(&self) -> Option<Path> { 185 pub fn fields(&self) -> AstChildren<RecordFieldDef> {
170 AstChildren::new(&self.syntax).next() 186 AstChildren::new(&self.syntax)
171 }
172 pub fn input(&self) -> Option<AttrInput> {
173 AstChildren::new(&self.syntax).next()
174 } 187 }
175} 188}
176#[derive(Debug, Clone, PartialEq, Eq, Hash)] 189#[derive(Debug, Clone, PartialEq, Eq, Hash)]
177pub enum AttrInput { 190pub struct RecordFieldDef {
178 Literal(Literal), 191 pub(crate) syntax: SyntaxNode,
179 TokenTree(TokenTree),
180}
181impl From<Literal> for AttrInput {
182 fn from(node: Literal) -> AttrInput {
183 AttrInput::Literal(node)
184 }
185}
186impl From<TokenTree> for AttrInput {
187 fn from(node: TokenTree) -> AttrInput {
188 AttrInput::TokenTree(node)
189 }
190} 192}
191impl AstNode for AttrInput { 193impl AstNode for RecordFieldDef {
192 fn can_cast(kind: SyntaxKind) -> bool { 194 fn can_cast(kind: SyntaxKind) -> bool {
193 match kind { 195 match kind {
194 LITERAL | TOKEN_TREE => true, 196 RECORD_FIELD_DEF => true,
195 _ => false, 197 _ => false,
196 } 198 }
197 } 199 }
198 fn cast(syntax: SyntaxNode) -> Option<Self> { 200 fn cast(syntax: SyntaxNode) -> Option<Self> {
199 let res = match syntax.kind() { 201 if Self::can_cast(syntax.kind()) {
200 LITERAL => AttrInput::Literal(Literal { syntax }), 202 Some(Self { syntax })
201 TOKEN_TREE => AttrInput::TokenTree(TokenTree { syntax }), 203 } else {
202 _ => return None, 204 None
203 }; 205 }
204 Some(res)
205 } 206 }
206 fn syntax(&self) -> &SyntaxNode { 207 fn syntax(&self) -> &SyntaxNode {
207 match self { 208 &self.syntax
208 AttrInput::Literal(it) => &it.syntax,
209 AttrInput::TokenTree(it) => &it.syntax,
210 }
211 } 209 }
212} 210}
213impl AttrInput {} 211impl ast::VisibilityOwner for RecordFieldDef {}
212impl ast::NameOwner for RecordFieldDef {}
213impl ast::AttrsOwner for RecordFieldDef {}
214impl ast::DocCommentsOwner for RecordFieldDef {}
215impl ast::TypeAscriptionOwner for RecordFieldDef {}
216impl RecordFieldDef {}
214#[derive(Debug, Clone, PartialEq, Eq, Hash)] 217#[derive(Debug, Clone, PartialEq, Eq, Hash)]
215pub struct AwaitExpr { 218pub struct TupleFieldDefList {
216 pub(crate) syntax: SyntaxNode, 219 pub(crate) syntax: SyntaxNode,
217} 220}
218impl AstNode for AwaitExpr { 221impl AstNode for TupleFieldDefList {
219 fn can_cast(kind: SyntaxKind) -> bool { 222 fn can_cast(kind: SyntaxKind) -> bool {
220 match kind { 223 match kind {
221 AWAIT_EXPR => true, 224 TUPLE_FIELD_DEF_LIST => true,
222 _ => false, 225 _ => false,
223 } 226 }
224 } 227 }
@@ -233,19 +236,19 @@ impl AstNode for AwaitExpr {
233 &self.syntax 236 &self.syntax
234 } 237 }
235} 238}
236impl AwaitExpr { 239impl TupleFieldDefList {
237 pub fn expr(&self) -> Option<Expr> { 240 pub fn fields(&self) -> AstChildren<TupleFieldDef> {
238 AstChildren::new(&self.syntax).next() 241 AstChildren::new(&self.syntax)
239 } 242 }
240} 243}
241#[derive(Debug, Clone, PartialEq, Eq, Hash)] 244#[derive(Debug, Clone, PartialEq, Eq, Hash)]
242pub struct BinExpr { 245pub struct TupleFieldDef {
243 pub(crate) syntax: SyntaxNode, 246 pub(crate) syntax: SyntaxNode,
244} 247}
245impl AstNode for BinExpr { 248impl AstNode for TupleFieldDef {
246 fn can_cast(kind: SyntaxKind) -> bool { 249 fn can_cast(kind: SyntaxKind) -> bool {
247 match kind { 250 match kind {
248 BIN_EXPR => true, 251 TUPLE_FIELD_DEF => true,
249 _ => false, 252 _ => false,
250 } 253 }
251 } 254 }
@@ -260,15 +263,21 @@ impl AstNode for BinExpr {
260 &self.syntax 263 &self.syntax
261 } 264 }
262} 265}
263impl BinExpr {} 266impl ast::VisibilityOwner for TupleFieldDef {}
267impl ast::AttrsOwner for TupleFieldDef {}
268impl TupleFieldDef {
269 pub fn type_ref(&self) -> Option<TypeRef> {
270 AstChildren::new(&self.syntax).next()
271 }
272}
264#[derive(Debug, Clone, PartialEq, Eq, Hash)] 273#[derive(Debug, Clone, PartialEq, Eq, Hash)]
265pub struct BindPat { 274pub struct EnumDef {
266 pub(crate) syntax: SyntaxNode, 275 pub(crate) syntax: SyntaxNode,
267} 276}
268impl AstNode for BindPat { 277impl AstNode for EnumDef {
269 fn can_cast(kind: SyntaxKind) -> bool { 278 fn can_cast(kind: SyntaxKind) -> bool {
270 match kind { 279 match kind {
271 BIND_PAT => true, 280 ENUM_DEF => true,
272 _ => false, 281 _ => false,
273 } 282 }
274 } 283 }
@@ -283,20 +292,24 @@ impl AstNode for BindPat {
283 &self.syntax 292 &self.syntax
284 } 293 }
285} 294}
286impl ast::NameOwner for BindPat {} 295impl ast::VisibilityOwner for EnumDef {}
287impl BindPat { 296impl ast::NameOwner for EnumDef {}
288 pub fn pat(&self) -> Option<Pat> { 297impl ast::TypeParamsOwner for EnumDef {}
298impl ast::AttrsOwner for EnumDef {}
299impl ast::DocCommentsOwner for EnumDef {}
300impl EnumDef {
301 pub fn variant_list(&self) -> Option<EnumVariantList> {
289 AstChildren::new(&self.syntax).next() 302 AstChildren::new(&self.syntax).next()
290 } 303 }
291} 304}
292#[derive(Debug, Clone, PartialEq, Eq, Hash)] 305#[derive(Debug, Clone, PartialEq, Eq, Hash)]
293pub struct Block { 306pub struct EnumVariantList {
294 pub(crate) syntax: SyntaxNode, 307 pub(crate) syntax: SyntaxNode,
295} 308}
296impl AstNode for Block { 309impl AstNode for EnumVariantList {
297 fn can_cast(kind: SyntaxKind) -> bool { 310 fn can_cast(kind: SyntaxKind) -> bool {
298 match kind { 311 match kind {
299 BLOCK => true, 312 ENUM_VARIANT_LIST => true,
300 _ => false, 313 _ => false,
301 } 314 }
302 } 315 }
@@ -311,24 +324,19 @@ impl AstNode for Block {
311 &self.syntax 324 &self.syntax
312 } 325 }
313} 326}
314impl ast::AttrsOwner for Block {} 327impl EnumVariantList {
315impl ast::ModuleItemOwner for Block {} 328 pub fn variants(&self) -> AstChildren<EnumVariant> {
316impl Block {
317 pub fn statements(&self) -> AstChildren<Stmt> {
318 AstChildren::new(&self.syntax) 329 AstChildren::new(&self.syntax)
319 } 330 }
320 pub fn expr(&self) -> Option<Expr> {
321 AstChildren::new(&self.syntax).next()
322 }
323} 331}
324#[derive(Debug, Clone, PartialEq, Eq, Hash)] 332#[derive(Debug, Clone, PartialEq, Eq, Hash)]
325pub struct BlockExpr { 333pub struct EnumVariant {
326 pub(crate) syntax: SyntaxNode, 334 pub(crate) syntax: SyntaxNode,
327} 335}
328impl AstNode for BlockExpr { 336impl AstNode for EnumVariant {
329 fn can_cast(kind: SyntaxKind) -> bool { 337 fn can_cast(kind: SyntaxKind) -> bool {
330 match kind { 338 match kind {
331 BLOCK_EXPR => true, 339 ENUM_VARIANT => true,
332 _ => false, 340 _ => false,
333 } 341 }
334 } 342 }
@@ -343,19 +351,22 @@ impl AstNode for BlockExpr {
343 &self.syntax 351 &self.syntax
344 } 352 }
345} 353}
346impl BlockExpr { 354impl ast::NameOwner for EnumVariant {}
347 pub fn block(&self) -> Option<Block> { 355impl ast::DocCommentsOwner for EnumVariant {}
356impl ast::AttrsOwner for EnumVariant {}
357impl EnumVariant {
358 pub fn expr(&self) -> Option<Expr> {
348 AstChildren::new(&self.syntax).next() 359 AstChildren::new(&self.syntax).next()
349 } 360 }
350} 361}
351#[derive(Debug, Clone, PartialEq, Eq, Hash)] 362#[derive(Debug, Clone, PartialEq, Eq, Hash)]
352pub struct BoxExpr { 363pub struct TraitDef {
353 pub(crate) syntax: SyntaxNode, 364 pub(crate) syntax: SyntaxNode,
354} 365}
355impl AstNode for BoxExpr { 366impl AstNode for TraitDef {
356 fn can_cast(kind: SyntaxKind) -> bool { 367 fn can_cast(kind: SyntaxKind) -> bool {
357 match kind { 368 match kind {
358 BOX_EXPR => true, 369 TRAIT_DEF => true,
359 _ => false, 370 _ => false,
360 } 371 }
361 } 372 }
@@ -370,19 +381,25 @@ impl AstNode for BoxExpr {
370 &self.syntax 381 &self.syntax
371 } 382 }
372} 383}
373impl BoxExpr { 384impl ast::VisibilityOwner for TraitDef {}
374 pub fn expr(&self) -> Option<Expr> { 385impl ast::NameOwner for TraitDef {}
386impl ast::AttrsOwner for TraitDef {}
387impl ast::DocCommentsOwner for TraitDef {}
388impl ast::TypeParamsOwner for TraitDef {}
389impl ast::TypeBoundsOwner for TraitDef {}
390impl TraitDef {
391 pub fn item_list(&self) -> Option<ItemList> {
375 AstChildren::new(&self.syntax).next() 392 AstChildren::new(&self.syntax).next()
376 } 393 }
377} 394}
378#[derive(Debug, Clone, PartialEq, Eq, Hash)] 395#[derive(Debug, Clone, PartialEq, Eq, Hash)]
379pub struct BoxPat { 396pub struct Module {
380 pub(crate) syntax: SyntaxNode, 397 pub(crate) syntax: SyntaxNode,
381} 398}
382impl AstNode for BoxPat { 399impl AstNode for Module {
383 fn can_cast(kind: SyntaxKind) -> bool { 400 fn can_cast(kind: SyntaxKind) -> bool {
384 match kind { 401 match kind {
385 BOX_PAT => true, 402 MODULE => true,
386 _ => false, 403 _ => false,
387 } 404 }
388 } 405 }
@@ -397,19 +414,23 @@ impl AstNode for BoxPat {
397 &self.syntax 414 &self.syntax
398 } 415 }
399} 416}
400impl BoxPat { 417impl ast::VisibilityOwner for Module {}
401 pub fn pat(&self) -> Option<Pat> { 418impl ast::NameOwner for Module {}
419impl ast::AttrsOwner for Module {}
420impl ast::DocCommentsOwner for Module {}
421impl Module {
422 pub fn item_list(&self) -> Option<ItemList> {
402 AstChildren::new(&self.syntax).next() 423 AstChildren::new(&self.syntax).next()
403 } 424 }
404} 425}
405#[derive(Debug, Clone, PartialEq, Eq, Hash)] 426#[derive(Debug, Clone, PartialEq, Eq, Hash)]
406pub struct BreakExpr { 427pub struct ItemList {
407 pub(crate) syntax: SyntaxNode, 428 pub(crate) syntax: SyntaxNode,
408} 429}
409impl AstNode for BreakExpr { 430impl AstNode for ItemList {
410 fn can_cast(kind: SyntaxKind) -> bool { 431 fn can_cast(kind: SyntaxKind) -> bool {
411 match kind { 432 match kind {
412 BREAK_EXPR => true, 433 ITEM_LIST => true,
413 _ => false, 434 _ => false,
414 } 435 }
415 } 436 }
@@ -424,19 +445,21 @@ impl AstNode for BreakExpr {
424 &self.syntax 445 &self.syntax
425 } 446 }
426} 447}
427impl BreakExpr { 448impl ast::FnDefOwner for ItemList {}
428 pub fn expr(&self) -> Option<Expr> { 449impl ast::ModuleItemOwner for ItemList {}
429 AstChildren::new(&self.syntax).next() 450impl ItemList {
451 pub fn impl_items(&self) -> AstChildren<ImplItem> {
452 AstChildren::new(&self.syntax)
430 } 453 }
431} 454}
432#[derive(Debug, Clone, PartialEq, Eq, Hash)] 455#[derive(Debug, Clone, PartialEq, Eq, Hash)]
433pub struct CallExpr { 456pub struct ConstDef {
434 pub(crate) syntax: SyntaxNode, 457 pub(crate) syntax: SyntaxNode,
435} 458}
436impl AstNode for CallExpr { 459impl AstNode for ConstDef {
437 fn can_cast(kind: SyntaxKind) -> bool { 460 fn can_cast(kind: SyntaxKind) -> bool {
438 match kind { 461 match kind {
439 CALL_EXPR => true, 462 CONST_DEF => true,
440 _ => false, 463 _ => false,
441 } 464 }
442 } 465 }
@@ -451,20 +474,25 @@ impl AstNode for CallExpr {
451 &self.syntax 474 &self.syntax
452 } 475 }
453} 476}
454impl ast::ArgListOwner for CallExpr {} 477impl ast::VisibilityOwner for ConstDef {}
455impl CallExpr { 478impl ast::NameOwner for ConstDef {}
456 pub fn expr(&self) -> Option<Expr> { 479impl ast::TypeParamsOwner for ConstDef {}
480impl ast::AttrsOwner for ConstDef {}
481impl ast::DocCommentsOwner for ConstDef {}
482impl ast::TypeAscriptionOwner for ConstDef {}
483impl ConstDef {
484 pub fn body(&self) -> Option<Expr> {
457 AstChildren::new(&self.syntax).next() 485 AstChildren::new(&self.syntax).next()
458 } 486 }
459} 487}
460#[derive(Debug, Clone, PartialEq, Eq, Hash)] 488#[derive(Debug, Clone, PartialEq, Eq, Hash)]
461pub struct CastExpr { 489pub struct StaticDef {
462 pub(crate) syntax: SyntaxNode, 490 pub(crate) syntax: SyntaxNode,
463} 491}
464impl AstNode for CastExpr { 492impl AstNode for StaticDef {
465 fn can_cast(kind: SyntaxKind) -> bool { 493 fn can_cast(kind: SyntaxKind) -> bool {
466 match kind { 494 match kind {
467 CAST_EXPR => true, 495 STATIC_DEF => true,
468 _ => false, 496 _ => false,
469 } 497 }
470 } 498 }
@@ -479,22 +507,25 @@ impl AstNode for CastExpr {
479 &self.syntax 507 &self.syntax
480 } 508 }
481} 509}
482impl CastExpr { 510impl ast::VisibilityOwner for StaticDef {}
483 pub fn expr(&self) -> Option<Expr> { 511impl ast::NameOwner for StaticDef {}
484 AstChildren::new(&self.syntax).next() 512impl ast::TypeParamsOwner for StaticDef {}
485 } 513impl ast::AttrsOwner for StaticDef {}
486 pub fn type_ref(&self) -> Option<TypeRef> { 514impl ast::DocCommentsOwner for StaticDef {}
515impl ast::TypeAscriptionOwner for StaticDef {}
516impl StaticDef {
517 pub fn body(&self) -> Option<Expr> {
487 AstChildren::new(&self.syntax).next() 518 AstChildren::new(&self.syntax).next()
488 } 519 }
489} 520}
490#[derive(Debug, Clone, PartialEq, Eq, Hash)] 521#[derive(Debug, Clone, PartialEq, Eq, Hash)]
491pub struct Condition { 522pub struct TypeAliasDef {
492 pub(crate) syntax: SyntaxNode, 523 pub(crate) syntax: SyntaxNode,
493} 524}
494impl AstNode for Condition { 525impl AstNode for TypeAliasDef {
495 fn can_cast(kind: SyntaxKind) -> bool { 526 fn can_cast(kind: SyntaxKind) -> bool {
496 match kind { 527 match kind {
497 CONDITION => true, 528 TYPE_ALIAS_DEF => true,
498 _ => false, 529 _ => false,
499 } 530 }
500 } 531 }
@@ -509,22 +540,25 @@ impl AstNode for Condition {
509 &self.syntax 540 &self.syntax
510 } 541 }
511} 542}
512impl Condition { 543impl ast::VisibilityOwner for TypeAliasDef {}
513 pub fn pat(&self) -> Option<Pat> { 544impl ast::NameOwner for TypeAliasDef {}
514 AstChildren::new(&self.syntax).next() 545impl ast::TypeParamsOwner for TypeAliasDef {}
515 } 546impl ast::AttrsOwner for TypeAliasDef {}
516 pub fn expr(&self) -> Option<Expr> { 547impl ast::DocCommentsOwner for TypeAliasDef {}
548impl ast::TypeBoundsOwner for TypeAliasDef {}
549impl TypeAliasDef {
550 pub fn type_ref(&self) -> Option<TypeRef> {
517 AstChildren::new(&self.syntax).next() 551 AstChildren::new(&self.syntax).next()
518 } 552 }
519} 553}
520#[derive(Debug, Clone, PartialEq, Eq, Hash)] 554#[derive(Debug, Clone, PartialEq, Eq, Hash)]
521pub struct ConstDef { 555pub struct ImplBlock {
522 pub(crate) syntax: SyntaxNode, 556 pub(crate) syntax: SyntaxNode,
523} 557}
524impl AstNode for ConstDef { 558impl AstNode for ImplBlock {
525 fn can_cast(kind: SyntaxKind) -> bool { 559 fn can_cast(kind: SyntaxKind) -> bool {
526 match kind { 560 match kind {
527 CONST_DEF => true, 561 IMPL_BLOCK => true,
528 _ => false, 562 _ => false,
529 } 563 }
530 } 564 }
@@ -539,25 +573,21 @@ impl AstNode for ConstDef {
539 &self.syntax 573 &self.syntax
540 } 574 }
541} 575}
542impl ast::VisibilityOwner for ConstDef {} 576impl ast::TypeParamsOwner for ImplBlock {}
543impl ast::NameOwner for ConstDef {} 577impl ast::AttrsOwner for ImplBlock {}
544impl ast::TypeParamsOwner for ConstDef {} 578impl ImplBlock {
545impl ast::AttrsOwner for ConstDef {} 579 pub fn item_list(&self) -> Option<ItemList> {
546impl ast::DocCommentsOwner for ConstDef {}
547impl ast::TypeAscriptionOwner for ConstDef {}
548impl ConstDef {
549 pub fn body(&self) -> Option<Expr> {
550 AstChildren::new(&self.syntax).next() 580 AstChildren::new(&self.syntax).next()
551 } 581 }
552} 582}
553#[derive(Debug, Clone, PartialEq, Eq, Hash)] 583#[derive(Debug, Clone, PartialEq, Eq, Hash)]
554pub struct ConstParam { 584pub struct ParenType {
555 pub(crate) syntax: SyntaxNode, 585 pub(crate) syntax: SyntaxNode,
556} 586}
557impl AstNode for ConstParam { 587impl AstNode for ParenType {
558 fn can_cast(kind: SyntaxKind) -> bool { 588 fn can_cast(kind: SyntaxKind) -> bool {
559 match kind { 589 match kind {
560 CONST_PARAM => true, 590 PAREN_TYPE => true,
561 _ => false, 591 _ => false,
562 } 592 }
563 } 593 }
@@ -572,22 +602,19 @@ impl AstNode for ConstParam {
572 &self.syntax 602 &self.syntax
573 } 603 }
574} 604}
575impl ast::NameOwner for ConstParam {} 605impl ParenType {
576impl ast::AttrsOwner for ConstParam {} 606 pub fn type_ref(&self) -> Option<TypeRef> {
577impl ast::TypeAscriptionOwner for ConstParam {}
578impl ConstParam {
579 pub fn default_val(&self) -> Option<Expr> {
580 AstChildren::new(&self.syntax).next() 607 AstChildren::new(&self.syntax).next()
581 } 608 }
582} 609}
583#[derive(Debug, Clone, PartialEq, Eq, Hash)] 610#[derive(Debug, Clone, PartialEq, Eq, Hash)]
584pub struct ContinueExpr { 611pub struct TupleType {
585 pub(crate) syntax: SyntaxNode, 612 pub(crate) syntax: SyntaxNode,
586} 613}
587impl AstNode for ContinueExpr { 614impl AstNode for TupleType {
588 fn can_cast(kind: SyntaxKind) -> bool { 615 fn can_cast(kind: SyntaxKind) -> bool {
589 match kind { 616 match kind {
590 CONTINUE_EXPR => true, 617 TUPLE_TYPE => true,
591 _ => false, 618 _ => false,
592 } 619 }
593 } 620 }
@@ -602,15 +629,19 @@ impl AstNode for ContinueExpr {
602 &self.syntax 629 &self.syntax
603 } 630 }
604} 631}
605impl ContinueExpr {} 632impl TupleType {
633 pub fn fields(&self) -> AstChildren<TypeRef> {
634 AstChildren::new(&self.syntax)
635 }
636}
606#[derive(Debug, Clone, PartialEq, Eq, Hash)] 637#[derive(Debug, Clone, PartialEq, Eq, Hash)]
607pub struct DotDotPat { 638pub struct NeverType {
608 pub(crate) syntax: SyntaxNode, 639 pub(crate) syntax: SyntaxNode,
609} 640}
610impl AstNode for DotDotPat { 641impl AstNode for NeverType {
611 fn can_cast(kind: SyntaxKind) -> bool { 642 fn can_cast(kind: SyntaxKind) -> bool {
612 match kind { 643 match kind {
613 DOT_DOT_PAT => true, 644 NEVER_TYPE => true,
614 _ => false, 645 _ => false,
615 } 646 }
616 } 647 }
@@ -625,15 +656,15 @@ impl AstNode for DotDotPat {
625 &self.syntax 656 &self.syntax
626 } 657 }
627} 658}
628impl DotDotPat {} 659impl NeverType {}
629#[derive(Debug, Clone, PartialEq, Eq, Hash)] 660#[derive(Debug, Clone, PartialEq, Eq, Hash)]
630pub struct DynTraitType { 661pub struct PathType {
631 pub(crate) syntax: SyntaxNode, 662 pub(crate) syntax: SyntaxNode,
632} 663}
633impl AstNode for DynTraitType { 664impl AstNode for PathType {
634 fn can_cast(kind: SyntaxKind) -> bool { 665 fn can_cast(kind: SyntaxKind) -> bool {
635 match kind { 666 match kind {
636 DYN_TRAIT_TYPE => true, 667 PATH_TYPE => true,
637 _ => false, 668 _ => false,
638 } 669 }
639 } 670 }
@@ -648,16 +679,19 @@ impl AstNode for DynTraitType {
648 &self.syntax 679 &self.syntax
649 } 680 }
650} 681}
651impl ast::TypeBoundsOwner for DynTraitType {} 682impl PathType {
652impl DynTraitType {} 683 pub fn path(&self) -> Option<Path> {
684 AstChildren::new(&self.syntax).next()
685 }
686}
653#[derive(Debug, Clone, PartialEq, Eq, Hash)] 687#[derive(Debug, Clone, PartialEq, Eq, Hash)]
654pub struct EnumDef { 688pub struct PointerType {
655 pub(crate) syntax: SyntaxNode, 689 pub(crate) syntax: SyntaxNode,
656} 690}
657impl AstNode for EnumDef { 691impl AstNode for PointerType {
658 fn can_cast(kind: SyntaxKind) -> bool { 692 fn can_cast(kind: SyntaxKind) -> bool {
659 match kind { 693 match kind {
660 ENUM_DEF => true, 694 POINTER_TYPE => true,
661 _ => false, 695 _ => false,
662 } 696 }
663 } 697 }
@@ -672,24 +706,19 @@ impl AstNode for EnumDef {
672 &self.syntax 706 &self.syntax
673 } 707 }
674} 708}
675impl ast::VisibilityOwner for EnumDef {} 709impl PointerType {
676impl ast::NameOwner for EnumDef {} 710 pub fn type_ref(&self) -> Option<TypeRef> {
677impl ast::TypeParamsOwner for EnumDef {}
678impl ast::AttrsOwner for EnumDef {}
679impl ast::DocCommentsOwner for EnumDef {}
680impl EnumDef {
681 pub fn variant_list(&self) -> Option<EnumVariantList> {
682 AstChildren::new(&self.syntax).next() 711 AstChildren::new(&self.syntax).next()
683 } 712 }
684} 713}
685#[derive(Debug, Clone, PartialEq, Eq, Hash)] 714#[derive(Debug, Clone, PartialEq, Eq, Hash)]
686pub struct EnumVariant { 715pub struct ArrayType {
687 pub(crate) syntax: SyntaxNode, 716 pub(crate) syntax: SyntaxNode,
688} 717}
689impl AstNode for EnumVariant { 718impl AstNode for ArrayType {
690 fn can_cast(kind: SyntaxKind) -> bool { 719 fn can_cast(kind: SyntaxKind) -> bool {
691 match kind { 720 match kind {
692 ENUM_VARIANT => true, 721 ARRAY_TYPE => true,
693 _ => false, 722 _ => false,
694 } 723 }
695 } 724 }
@@ -704,22 +733,22 @@ impl AstNode for EnumVariant {
704 &self.syntax 733 &self.syntax
705 } 734 }
706} 735}
707impl ast::NameOwner for EnumVariant {} 736impl ArrayType {
708impl ast::DocCommentsOwner for EnumVariant {} 737 pub fn type_ref(&self) -> Option<TypeRef> {
709impl ast::AttrsOwner for EnumVariant {} 738 AstChildren::new(&self.syntax).next()
710impl EnumVariant { 739 }
711 pub fn expr(&self) -> Option<Expr> { 740 pub fn expr(&self) -> Option<Expr> {
712 AstChildren::new(&self.syntax).next() 741 AstChildren::new(&self.syntax).next()
713 } 742 }
714} 743}
715#[derive(Debug, Clone, PartialEq, Eq, Hash)] 744#[derive(Debug, Clone, PartialEq, Eq, Hash)]
716pub struct EnumVariantList { 745pub struct SliceType {
717 pub(crate) syntax: SyntaxNode, 746 pub(crate) syntax: SyntaxNode,
718} 747}
719impl AstNode for EnumVariantList { 748impl AstNode for SliceType {
720 fn can_cast(kind: SyntaxKind) -> bool { 749 fn can_cast(kind: SyntaxKind) -> bool {
721 match kind { 750 match kind {
722 ENUM_VARIANT_LIST => true, 751 SLICE_TYPE => true,
723 _ => false, 752 _ => false,
724 } 753 }
725 } 754 }
@@ -734,294 +763,46 @@ impl AstNode for EnumVariantList {
734 &self.syntax 763 &self.syntax
735 } 764 }
736} 765}
737impl EnumVariantList { 766impl SliceType {
738 pub fn variants(&self) -> AstChildren<EnumVariant> { 767 pub fn type_ref(&self) -> Option<TypeRef> {
739 AstChildren::new(&self.syntax) 768 AstChildren::new(&self.syntax).next()
740 } 769 }
741} 770}
742#[derive(Debug, Clone, PartialEq, Eq, Hash)] 771#[derive(Debug, Clone, PartialEq, Eq, Hash)]
743pub enum Expr { 772pub struct ReferenceType {
744 TupleExpr(TupleExpr), 773 pub(crate) syntax: SyntaxNode,
745 ArrayExpr(ArrayExpr),
746 ParenExpr(ParenExpr),
747 PathExpr(PathExpr),
748 LambdaExpr(LambdaExpr),
749 IfExpr(IfExpr),
750 LoopExpr(LoopExpr),
751 ForExpr(ForExpr),
752 WhileExpr(WhileExpr),
753 ContinueExpr(ContinueExpr),
754 BreakExpr(BreakExpr),
755 Label(Label),
756 BlockExpr(BlockExpr),
757 ReturnExpr(ReturnExpr),
758 MatchExpr(MatchExpr),
759 RecordLit(RecordLit),
760 CallExpr(CallExpr),
761 IndexExpr(IndexExpr),
762 MethodCallExpr(MethodCallExpr),
763 FieldExpr(FieldExpr),
764 AwaitExpr(AwaitExpr),
765 TryExpr(TryExpr),
766 TryBlockExpr(TryBlockExpr),
767 CastExpr(CastExpr),
768 RefExpr(RefExpr),
769 PrefixExpr(PrefixExpr),
770 RangeExpr(RangeExpr),
771 BinExpr(BinExpr),
772 Literal(Literal),
773 MacroCall(MacroCall),
774 BoxExpr(BoxExpr),
775}
776impl From<TupleExpr> for Expr {
777 fn from(node: TupleExpr) -> Expr {
778 Expr::TupleExpr(node)
779 }
780}
781impl From<ArrayExpr> for Expr {
782 fn from(node: ArrayExpr) -> Expr {
783 Expr::ArrayExpr(node)
784 }
785}
786impl From<ParenExpr> for Expr {
787 fn from(node: ParenExpr) -> Expr {
788 Expr::ParenExpr(node)
789 }
790}
791impl From<PathExpr> for Expr {
792 fn from(node: PathExpr) -> Expr {
793 Expr::PathExpr(node)
794 }
795}
796impl From<LambdaExpr> for Expr {
797 fn from(node: LambdaExpr) -> Expr {
798 Expr::LambdaExpr(node)
799 }
800}
801impl From<IfExpr> for Expr {
802 fn from(node: IfExpr) -> Expr {
803 Expr::IfExpr(node)
804 }
805}
806impl From<LoopExpr> for Expr {
807 fn from(node: LoopExpr) -> Expr {
808 Expr::LoopExpr(node)
809 }
810}
811impl From<ForExpr> for Expr {
812 fn from(node: ForExpr) -> Expr {
813 Expr::ForExpr(node)
814 }
815}
816impl From<WhileExpr> for Expr {
817 fn from(node: WhileExpr) -> Expr {
818 Expr::WhileExpr(node)
819 }
820}
821impl From<ContinueExpr> for Expr {
822 fn from(node: ContinueExpr) -> Expr {
823 Expr::ContinueExpr(node)
824 }
825}
826impl From<BreakExpr> for Expr {
827 fn from(node: BreakExpr) -> Expr {
828 Expr::BreakExpr(node)
829 }
830}
831impl From<Label> for Expr {
832 fn from(node: Label) -> Expr {
833 Expr::Label(node)
834 }
835}
836impl From<BlockExpr> for Expr {
837 fn from(node: BlockExpr) -> Expr {
838 Expr::BlockExpr(node)
839 }
840}
841impl From<ReturnExpr> for Expr {
842 fn from(node: ReturnExpr) -> Expr {
843 Expr::ReturnExpr(node)
844 }
845}
846impl From<MatchExpr> for Expr {
847 fn from(node: MatchExpr) -> Expr {
848 Expr::MatchExpr(node)
849 }
850}
851impl From<RecordLit> for Expr {
852 fn from(node: RecordLit) -> Expr {
853 Expr::RecordLit(node)
854 }
855}
856impl From<CallExpr> for Expr {
857 fn from(node: CallExpr) -> Expr {
858 Expr::CallExpr(node)
859 }
860}
861impl From<IndexExpr> for Expr {
862 fn from(node: IndexExpr) -> Expr {
863 Expr::IndexExpr(node)
864 }
865}
866impl From<MethodCallExpr> for Expr {
867 fn from(node: MethodCallExpr) -> Expr {
868 Expr::MethodCallExpr(node)
869 }
870}
871impl From<FieldExpr> for Expr {
872 fn from(node: FieldExpr) -> Expr {
873 Expr::FieldExpr(node)
874 }
875}
876impl From<AwaitExpr> for Expr {
877 fn from(node: AwaitExpr) -> Expr {
878 Expr::AwaitExpr(node)
879 }
880}
881impl From<TryExpr> for Expr {
882 fn from(node: TryExpr) -> Expr {
883 Expr::TryExpr(node)
884 }
885}
886impl From<TryBlockExpr> for Expr {
887 fn from(node: TryBlockExpr) -> Expr {
888 Expr::TryBlockExpr(node)
889 }
890}
891impl From<CastExpr> for Expr {
892 fn from(node: CastExpr) -> Expr {
893 Expr::CastExpr(node)
894 }
895}
896impl From<RefExpr> for Expr {
897 fn from(node: RefExpr) -> Expr {
898 Expr::RefExpr(node)
899 }
900}
901impl From<PrefixExpr> for Expr {
902 fn from(node: PrefixExpr) -> Expr {
903 Expr::PrefixExpr(node)
904 }
905}
906impl From<RangeExpr> for Expr {
907 fn from(node: RangeExpr) -> Expr {
908 Expr::RangeExpr(node)
909 }
910}
911impl From<BinExpr> for Expr {
912 fn from(node: BinExpr) -> Expr {
913 Expr::BinExpr(node)
914 }
915}
916impl From<Literal> for Expr {
917 fn from(node: Literal) -> Expr {
918 Expr::Literal(node)
919 }
920}
921impl From<MacroCall> for Expr {
922 fn from(node: MacroCall) -> Expr {
923 Expr::MacroCall(node)
924 }
925}
926impl From<BoxExpr> for Expr {
927 fn from(node: BoxExpr) -> Expr {
928 Expr::BoxExpr(node)
929 }
930} 774}
931impl AstNode for Expr { 775impl AstNode for ReferenceType {
932 fn can_cast(kind: SyntaxKind) -> bool { 776 fn can_cast(kind: SyntaxKind) -> bool {
933 match kind { 777 match kind {
934 TUPLE_EXPR | ARRAY_EXPR | PAREN_EXPR | PATH_EXPR | LAMBDA_EXPR | IF_EXPR 778 REFERENCE_TYPE => true,
935 | LOOP_EXPR | FOR_EXPR | WHILE_EXPR | CONTINUE_EXPR | BREAK_EXPR | LABEL
936 | BLOCK_EXPR | RETURN_EXPR | MATCH_EXPR | RECORD_LIT | CALL_EXPR | INDEX_EXPR
937 | METHOD_CALL_EXPR | FIELD_EXPR | AWAIT_EXPR | TRY_EXPR | TRY_BLOCK_EXPR
938 | CAST_EXPR | REF_EXPR | PREFIX_EXPR | RANGE_EXPR | BIN_EXPR | LITERAL | MACRO_CALL
939 | BOX_EXPR => true,
940 _ => false, 779 _ => false,
941 } 780 }
942 } 781 }
943 fn cast(syntax: SyntaxNode) -> Option<Self> { 782 fn cast(syntax: SyntaxNode) -> Option<Self> {
944 let res = match syntax.kind() { 783 if Self::can_cast(syntax.kind()) {
945 TUPLE_EXPR => Expr::TupleExpr(TupleExpr { syntax }), 784 Some(Self { syntax })
946 ARRAY_EXPR => Expr::ArrayExpr(ArrayExpr { syntax }), 785 } else {
947 PAREN_EXPR => Expr::ParenExpr(ParenExpr { syntax }), 786 None
948 PATH_EXPR => Expr::PathExpr(PathExpr { syntax }), 787 }
949 LAMBDA_EXPR => Expr::LambdaExpr(LambdaExpr { syntax }),
950 IF_EXPR => Expr::IfExpr(IfExpr { syntax }),
951 LOOP_EXPR => Expr::LoopExpr(LoopExpr { syntax }),
952 FOR_EXPR => Expr::ForExpr(ForExpr { syntax }),
953 WHILE_EXPR => Expr::WhileExpr(WhileExpr { syntax }),
954 CONTINUE_EXPR => Expr::ContinueExpr(ContinueExpr { syntax }),
955 BREAK_EXPR => Expr::BreakExpr(BreakExpr { syntax }),
956 LABEL => Expr::Label(Label { syntax }),
957 BLOCK_EXPR => Expr::BlockExpr(BlockExpr { syntax }),
958 RETURN_EXPR => Expr::ReturnExpr(ReturnExpr { syntax }),
959 MATCH_EXPR => Expr::MatchExpr(MatchExpr { syntax }),
960 RECORD_LIT => Expr::RecordLit(RecordLit { syntax }),
961 CALL_EXPR => Expr::CallExpr(CallExpr { syntax }),
962 INDEX_EXPR => Expr::IndexExpr(IndexExpr { syntax }),
963 METHOD_CALL_EXPR => Expr::MethodCallExpr(MethodCallExpr { syntax }),
964 FIELD_EXPR => Expr::FieldExpr(FieldExpr { syntax }),
965 AWAIT_EXPR => Expr::AwaitExpr(AwaitExpr { syntax }),
966 TRY_EXPR => Expr::TryExpr(TryExpr { syntax }),
967 TRY_BLOCK_EXPR => Expr::TryBlockExpr(TryBlockExpr { syntax }),
968 CAST_EXPR => Expr::CastExpr(CastExpr { syntax }),
969 REF_EXPR => Expr::RefExpr(RefExpr { syntax }),
970 PREFIX_EXPR => Expr::PrefixExpr(PrefixExpr { syntax }),
971 RANGE_EXPR => Expr::RangeExpr(RangeExpr { syntax }),
972 BIN_EXPR => Expr::BinExpr(BinExpr { syntax }),
973 LITERAL => Expr::Literal(Literal { syntax }),
974 MACRO_CALL => Expr::MacroCall(MacroCall { syntax }),
975 BOX_EXPR => Expr::BoxExpr(BoxExpr { syntax }),
976 _ => return None,
977 };
978 Some(res)
979 } 788 }
980 fn syntax(&self) -> &SyntaxNode { 789 fn syntax(&self) -> &SyntaxNode {
981 match self { 790 &self.syntax
982 Expr::TupleExpr(it) => &it.syntax, 791 }
983 Expr::ArrayExpr(it) => &it.syntax, 792}
984 Expr::ParenExpr(it) => &it.syntax, 793impl ReferenceType {
985 Expr::PathExpr(it) => &it.syntax, 794 pub fn type_ref(&self) -> Option<TypeRef> {
986 Expr::LambdaExpr(it) => &it.syntax, 795 AstChildren::new(&self.syntax).next()
987 Expr::IfExpr(it) => &it.syntax,
988 Expr::LoopExpr(it) => &it.syntax,
989 Expr::ForExpr(it) => &it.syntax,
990 Expr::WhileExpr(it) => &it.syntax,
991 Expr::ContinueExpr(it) => &it.syntax,
992 Expr::BreakExpr(it) => &it.syntax,
993 Expr::Label(it) => &it.syntax,
994 Expr::BlockExpr(it) => &it.syntax,
995 Expr::ReturnExpr(it) => &it.syntax,
996 Expr::MatchExpr(it) => &it.syntax,
997 Expr::RecordLit(it) => &it.syntax,
998 Expr::CallExpr(it) => &it.syntax,
999 Expr::IndexExpr(it) => &it.syntax,
1000 Expr::MethodCallExpr(it) => &it.syntax,
1001 Expr::FieldExpr(it) => &it.syntax,
1002 Expr::AwaitExpr(it) => &it.syntax,
1003 Expr::TryExpr(it) => &it.syntax,
1004 Expr::TryBlockExpr(it) => &it.syntax,
1005 Expr::CastExpr(it) => &it.syntax,
1006 Expr::RefExpr(it) => &it.syntax,
1007 Expr::PrefixExpr(it) => &it.syntax,
1008 Expr::RangeExpr(it) => &it.syntax,
1009 Expr::BinExpr(it) => &it.syntax,
1010 Expr::Literal(it) => &it.syntax,
1011 Expr::MacroCall(it) => &it.syntax,
1012 Expr::BoxExpr(it) => &it.syntax,
1013 }
1014 } 796 }
1015} 797}
1016impl Expr {}
1017#[derive(Debug, Clone, PartialEq, Eq, Hash)] 798#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1018pub struct ExprStmt { 799pub struct PlaceholderType {
1019 pub(crate) syntax: SyntaxNode, 800 pub(crate) syntax: SyntaxNode,
1020} 801}
1021impl AstNode for ExprStmt { 802impl AstNode for PlaceholderType {
1022 fn can_cast(kind: SyntaxKind) -> bool { 803 fn can_cast(kind: SyntaxKind) -> bool {
1023 match kind { 804 match kind {
1024 EXPR_STMT => true, 805 PLACEHOLDER_TYPE => true,
1025 _ => false, 806 _ => false,
1026 } 807 }
1027 } 808 }
@@ -1036,19 +817,15 @@ impl AstNode for ExprStmt {
1036 &self.syntax 817 &self.syntax
1037 } 818 }
1038} 819}
1039impl ExprStmt { 820impl PlaceholderType {}
1040 pub fn expr(&self) -> Option<Expr> {
1041 AstChildren::new(&self.syntax).next()
1042 }
1043}
1044#[derive(Debug, Clone, PartialEq, Eq, Hash)] 821#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1045pub struct ExternCrateItem { 822pub struct FnPointerType {
1046 pub(crate) syntax: SyntaxNode, 823 pub(crate) syntax: SyntaxNode,
1047} 824}
1048impl AstNode for ExternCrateItem { 825impl AstNode for FnPointerType {
1049 fn can_cast(kind: SyntaxKind) -> bool { 826 fn can_cast(kind: SyntaxKind) -> bool {
1050 match kind { 827 match kind {
1051 EXTERN_CRATE_ITEM => true, 828 FN_POINTER_TYPE => true,
1052 _ => false, 829 _ => false,
1053 } 830 }
1054 } 831 }
@@ -1063,24 +840,22 @@ impl AstNode for ExternCrateItem {
1063 &self.syntax 840 &self.syntax
1064 } 841 }
1065} 842}
1066impl ast::AttrsOwner for ExternCrateItem {} 843impl FnPointerType {
1067impl ast::VisibilityOwner for ExternCrateItem {} 844 pub fn param_list(&self) -> Option<ParamList> {
1068impl ExternCrateItem {
1069 pub fn name_ref(&self) -> Option<NameRef> {
1070 AstChildren::new(&self.syntax).next() 845 AstChildren::new(&self.syntax).next()
1071 } 846 }
1072 pub fn alias(&self) -> Option<Alias> { 847 pub fn ret_type(&self) -> Option<RetType> {
1073 AstChildren::new(&self.syntax).next() 848 AstChildren::new(&self.syntax).next()
1074 } 849 }
1075} 850}
1076#[derive(Debug, Clone, PartialEq, Eq, Hash)] 851#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1077pub struct FieldExpr { 852pub struct ForType {
1078 pub(crate) syntax: SyntaxNode, 853 pub(crate) syntax: SyntaxNode,
1079} 854}
1080impl AstNode for FieldExpr { 855impl AstNode for ForType {
1081 fn can_cast(kind: SyntaxKind) -> bool { 856 fn can_cast(kind: SyntaxKind) -> bool {
1082 match kind { 857 match kind {
1083 FIELD_EXPR => true, 858 FOR_TYPE => true,
1084 _ => false, 859 _ => false,
1085 } 860 }
1086 } 861 }
@@ -1095,22 +870,19 @@ impl AstNode for FieldExpr {
1095 &self.syntax 870 &self.syntax
1096 } 871 }
1097} 872}
1098impl FieldExpr { 873impl ForType {
1099 pub fn expr(&self) -> Option<Expr> { 874 pub fn type_ref(&self) -> Option<TypeRef> {
1100 AstChildren::new(&self.syntax).next()
1101 }
1102 pub fn name_ref(&self) -> Option<NameRef> {
1103 AstChildren::new(&self.syntax).next() 875 AstChildren::new(&self.syntax).next()
1104 } 876 }
1105} 877}
1106#[derive(Debug, Clone, PartialEq, Eq, Hash)] 878#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1107pub struct FnDef { 879pub struct ImplTraitType {
1108 pub(crate) syntax: SyntaxNode, 880 pub(crate) syntax: SyntaxNode,
1109} 881}
1110impl AstNode for FnDef { 882impl AstNode for ImplTraitType {
1111 fn can_cast(kind: SyntaxKind) -> bool { 883 fn can_cast(kind: SyntaxKind) -> bool {
1112 match kind { 884 match kind {
1113 FN_DEF => true, 885 IMPL_TRAIT_TYPE => true,
1114 _ => false, 886 _ => false,
1115 } 887 }
1116 } 888 }
@@ -1125,30 +897,16 @@ impl AstNode for FnDef {
1125 &self.syntax 897 &self.syntax
1126 } 898 }
1127} 899}
1128impl ast::VisibilityOwner for FnDef {} 900impl ast::TypeBoundsOwner for ImplTraitType {}
1129impl ast::NameOwner for FnDef {} 901impl ImplTraitType {}
1130impl ast::TypeParamsOwner for FnDef {}
1131impl ast::AttrsOwner for FnDef {}
1132impl ast::DocCommentsOwner for FnDef {}
1133impl FnDef {
1134 pub fn param_list(&self) -> Option<ParamList> {
1135 AstChildren::new(&self.syntax).next()
1136 }
1137 pub fn body(&self) -> Option<BlockExpr> {
1138 AstChildren::new(&self.syntax).next()
1139 }
1140 pub fn ret_type(&self) -> Option<RetType> {
1141 AstChildren::new(&self.syntax).next()
1142 }
1143}
1144#[derive(Debug, Clone, PartialEq, Eq, Hash)] 902#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1145pub struct FnPointerType { 903pub struct DynTraitType {
1146 pub(crate) syntax: SyntaxNode, 904 pub(crate) syntax: SyntaxNode,
1147} 905}
1148impl AstNode for FnPointerType { 906impl AstNode for DynTraitType {
1149 fn can_cast(kind: SyntaxKind) -> bool { 907 fn can_cast(kind: SyntaxKind) -> bool {
1150 match kind { 908 match kind {
1151 FN_POINTER_TYPE => true, 909 DYN_TRAIT_TYPE => true,
1152 _ => false, 910 _ => false,
1153 } 911 }
1154 } 912 }
@@ -1163,22 +921,16 @@ impl AstNode for FnPointerType {
1163 &self.syntax 921 &self.syntax
1164 } 922 }
1165} 923}
1166impl FnPointerType { 924impl ast::TypeBoundsOwner for DynTraitType {}
1167 pub fn param_list(&self) -> Option<ParamList> { 925impl DynTraitType {}
1168 AstChildren::new(&self.syntax).next()
1169 }
1170 pub fn ret_type(&self) -> Option<RetType> {
1171 AstChildren::new(&self.syntax).next()
1172 }
1173}
1174#[derive(Debug, Clone, PartialEq, Eq, Hash)] 926#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1175pub struct ForExpr { 927pub struct TupleExpr {
1176 pub(crate) syntax: SyntaxNode, 928 pub(crate) syntax: SyntaxNode,
1177} 929}
1178impl AstNode for ForExpr { 930impl AstNode for TupleExpr {
1179 fn can_cast(kind: SyntaxKind) -> bool { 931 fn can_cast(kind: SyntaxKind) -> bool {
1180 match kind { 932 match kind {
1181 FOR_EXPR => true, 933 TUPLE_EXPR => true,
1182 _ => false, 934 _ => false,
1183 } 935 }
1184 } 936 }
@@ -1193,23 +945,19 @@ impl AstNode for ForExpr {
1193 &self.syntax 945 &self.syntax
1194 } 946 }
1195} 947}
1196impl ast::LoopBodyOwner for ForExpr {} 948impl TupleExpr {
1197impl ForExpr { 949 pub fn exprs(&self) -> AstChildren<Expr> {
1198 pub fn pat(&self) -> Option<Pat> { 950 AstChildren::new(&self.syntax)
1199 AstChildren::new(&self.syntax).next()
1200 }
1201 pub fn iterable(&self) -> Option<Expr> {
1202 AstChildren::new(&self.syntax).next()
1203 } 951 }
1204} 952}
1205#[derive(Debug, Clone, PartialEq, Eq, Hash)] 953#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1206pub struct ForType { 954pub struct ArrayExpr {
1207 pub(crate) syntax: SyntaxNode, 955 pub(crate) syntax: SyntaxNode,
1208} 956}
1209impl AstNode for ForType { 957impl AstNode for ArrayExpr {
1210 fn can_cast(kind: SyntaxKind) -> bool { 958 fn can_cast(kind: SyntaxKind) -> bool {
1211 match kind { 959 match kind {
1212 FOR_TYPE => true, 960 ARRAY_EXPR => true,
1213 _ => false, 961 _ => false,
1214 } 962 }
1215 } 963 }
@@ -1224,19 +972,19 @@ impl AstNode for ForType {
1224 &self.syntax 972 &self.syntax
1225 } 973 }
1226} 974}
1227impl ForType { 975impl ArrayExpr {
1228 pub fn type_ref(&self) -> Option<TypeRef> { 976 pub fn exprs(&self) -> AstChildren<Expr> {
1229 AstChildren::new(&self.syntax).next() 977 AstChildren::new(&self.syntax)
1230 } 978 }
1231} 979}
1232#[derive(Debug, Clone, PartialEq, Eq, Hash)] 980#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1233pub struct IfExpr { 981pub struct ParenExpr {
1234 pub(crate) syntax: SyntaxNode, 982 pub(crate) syntax: SyntaxNode,
1235} 983}
1236impl AstNode for IfExpr { 984impl AstNode for ParenExpr {
1237 fn can_cast(kind: SyntaxKind) -> bool { 985 fn can_cast(kind: SyntaxKind) -> bool {
1238 match kind { 986 match kind {
1239 IF_EXPR => true, 987 PAREN_EXPR => true,
1240 _ => false, 988 _ => false,
1241 } 989 }
1242 } 990 }
@@ -1251,19 +999,19 @@ impl AstNode for IfExpr {
1251 &self.syntax 999 &self.syntax
1252 } 1000 }
1253} 1001}
1254impl IfExpr { 1002impl ParenExpr {
1255 pub fn condition(&self) -> Option<Condition> { 1003 pub fn expr(&self) -> Option<Expr> {
1256 AstChildren::new(&self.syntax).next() 1004 AstChildren::new(&self.syntax).next()
1257 } 1005 }
1258} 1006}
1259#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1007#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1260pub struct ImplBlock { 1008pub struct PathExpr {
1261 pub(crate) syntax: SyntaxNode, 1009 pub(crate) syntax: SyntaxNode,
1262} 1010}
1263impl AstNode for ImplBlock { 1011impl AstNode for PathExpr {
1264 fn can_cast(kind: SyntaxKind) -> bool { 1012 fn can_cast(kind: SyntaxKind) -> bool {
1265 match kind { 1013 match kind {
1266 IMPL_BLOCK => true, 1014 PATH_EXPR => true,
1267 _ => false, 1015 _ => false,
1268 } 1016 }
1269 } 1017 }
@@ -1278,68 +1026,52 @@ impl AstNode for ImplBlock {
1278 &self.syntax 1026 &self.syntax
1279 } 1027 }
1280} 1028}
1281impl ast::TypeParamsOwner for ImplBlock {} 1029impl PathExpr {
1282impl ast::AttrsOwner for ImplBlock {} 1030 pub fn path(&self) -> Option<Path> {
1283impl ImplBlock {
1284 pub fn item_list(&self) -> Option<ItemList> {
1285 AstChildren::new(&self.syntax).next() 1031 AstChildren::new(&self.syntax).next()
1286 } 1032 }
1287} 1033}
1288#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1034#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1289pub enum ImplItem { 1035pub struct LambdaExpr {
1290 FnDef(FnDef), 1036 pub(crate) syntax: SyntaxNode,
1291 TypeAliasDef(TypeAliasDef),
1292 ConstDef(ConstDef),
1293}
1294impl From<FnDef> for ImplItem {
1295 fn from(node: FnDef) -> ImplItem {
1296 ImplItem::FnDef(node)
1297 }
1298}
1299impl From<TypeAliasDef> for ImplItem {
1300 fn from(node: TypeAliasDef) -> ImplItem {
1301 ImplItem::TypeAliasDef(node)
1302 }
1303}
1304impl From<ConstDef> for ImplItem {
1305 fn from(node: ConstDef) -> ImplItem {
1306 ImplItem::ConstDef(node)
1307 }
1308} 1037}
1309impl AstNode for ImplItem { 1038impl AstNode for LambdaExpr {
1310 fn can_cast(kind: SyntaxKind) -> bool { 1039 fn can_cast(kind: SyntaxKind) -> bool {
1311 match kind { 1040 match kind {
1312 FN_DEF | TYPE_ALIAS_DEF | CONST_DEF => true, 1041 LAMBDA_EXPR => true,
1313 _ => false, 1042 _ => false,
1314 } 1043 }
1315 } 1044 }
1316 fn cast(syntax: SyntaxNode) -> Option<Self> { 1045 fn cast(syntax: SyntaxNode) -> Option<Self> {
1317 let res = match syntax.kind() { 1046 if Self::can_cast(syntax.kind()) {
1318 FN_DEF => ImplItem::FnDef(FnDef { syntax }), 1047 Some(Self { syntax })
1319 TYPE_ALIAS_DEF => ImplItem::TypeAliasDef(TypeAliasDef { syntax }), 1048 } else {
1320 CONST_DEF => ImplItem::ConstDef(ConstDef { syntax }), 1049 None
1321 _ => return None, 1050 }
1322 };
1323 Some(res)
1324 } 1051 }
1325 fn syntax(&self) -> &SyntaxNode { 1052 fn syntax(&self) -> &SyntaxNode {
1326 match self { 1053 &self.syntax
1327 ImplItem::FnDef(it) => &it.syntax, 1054 }
1328 ImplItem::TypeAliasDef(it) => &it.syntax, 1055}
1329 ImplItem::ConstDef(it) => &it.syntax, 1056impl LambdaExpr {
1330 } 1057 pub fn param_list(&self) -> Option<ParamList> {
1058 AstChildren::new(&self.syntax).next()
1059 }
1060 pub fn ret_type(&self) -> Option<RetType> {
1061 AstChildren::new(&self.syntax).next()
1062 }
1063 pub fn body(&self) -> Option<Expr> {
1064 AstChildren::new(&self.syntax).next()
1331 } 1065 }
1332} 1066}
1333impl ast::AttrsOwner for ImplItem {}
1334impl ImplItem {}
1335#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1067#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1336pub struct ImplTraitType { 1068pub struct IfExpr {
1337 pub(crate) syntax: SyntaxNode, 1069 pub(crate) syntax: SyntaxNode,
1338} 1070}
1339impl AstNode for ImplTraitType { 1071impl AstNode for IfExpr {
1340 fn can_cast(kind: SyntaxKind) -> bool { 1072 fn can_cast(kind: SyntaxKind) -> bool {
1341 match kind { 1073 match kind {
1342 IMPL_TRAIT_TYPE => true, 1074 IF_EXPR => true,
1343 _ => false, 1075 _ => false,
1344 } 1076 }
1345 } 1077 }
@@ -1354,16 +1086,19 @@ impl AstNode for ImplTraitType {
1354 &self.syntax 1086 &self.syntax
1355 } 1087 }
1356} 1088}
1357impl ast::TypeBoundsOwner for ImplTraitType {} 1089impl IfExpr {
1358impl ImplTraitType {} 1090 pub fn condition(&self) -> Option<Condition> {
1091 AstChildren::new(&self.syntax).next()
1092 }
1093}
1359#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1094#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1360pub struct IndexExpr { 1095pub struct LoopExpr {
1361 pub(crate) syntax: SyntaxNode, 1096 pub(crate) syntax: SyntaxNode,
1362} 1097}
1363impl AstNode for IndexExpr { 1098impl AstNode for LoopExpr {
1364 fn can_cast(kind: SyntaxKind) -> bool { 1099 fn can_cast(kind: SyntaxKind) -> bool {
1365 match kind { 1100 match kind {
1366 INDEX_EXPR => true, 1101 LOOP_EXPR => true,
1367 _ => false, 1102 _ => false,
1368 } 1103 }
1369 } 1104 }
@@ -1378,15 +1113,16 @@ impl AstNode for IndexExpr {
1378 &self.syntax 1113 &self.syntax
1379 } 1114 }
1380} 1115}
1381impl IndexExpr {} 1116impl ast::LoopBodyOwner for LoopExpr {}
1117impl LoopExpr {}
1382#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1118#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1383pub struct ItemList { 1119pub struct TryBlockExpr {
1384 pub(crate) syntax: SyntaxNode, 1120 pub(crate) syntax: SyntaxNode,
1385} 1121}
1386impl AstNode for ItemList { 1122impl AstNode for TryBlockExpr {
1387 fn can_cast(kind: SyntaxKind) -> bool { 1123 fn can_cast(kind: SyntaxKind) -> bool {
1388 match kind { 1124 match kind {
1389 ITEM_LIST => true, 1125 TRY_BLOCK_EXPR => true,
1390 _ => false, 1126 _ => false,
1391 } 1127 }
1392 } 1128 }
@@ -1401,21 +1137,19 @@ impl AstNode for ItemList {
1401 &self.syntax 1137 &self.syntax
1402 } 1138 }
1403} 1139}
1404impl ast::FnDefOwner for ItemList {} 1140impl TryBlockExpr {
1405impl ast::ModuleItemOwner for ItemList {} 1141 pub fn body(&self) -> Option<BlockExpr> {
1406impl ItemList { 1142 AstChildren::new(&self.syntax).next()
1407 pub fn impl_items(&self) -> AstChildren<ImplItem> {
1408 AstChildren::new(&self.syntax)
1409 } 1143 }
1410} 1144}
1411#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1145#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1412pub struct Label { 1146pub struct ForExpr {
1413 pub(crate) syntax: SyntaxNode, 1147 pub(crate) syntax: SyntaxNode,
1414} 1148}
1415impl AstNode for Label { 1149impl AstNode for ForExpr {
1416 fn can_cast(kind: SyntaxKind) -> bool { 1150 fn can_cast(kind: SyntaxKind) -> bool {
1417 match kind { 1151 match kind {
1418 LABEL => true, 1152 FOR_EXPR => true,
1419 _ => false, 1153 _ => false,
1420 } 1154 }
1421 } 1155 }
@@ -1430,15 +1164,23 @@ impl AstNode for Label {
1430 &self.syntax 1164 &self.syntax
1431 } 1165 }
1432} 1166}
1433impl Label {} 1167impl ast::LoopBodyOwner for ForExpr {}
1168impl ForExpr {
1169 pub fn pat(&self) -> Option<Pat> {
1170 AstChildren::new(&self.syntax).next()
1171 }
1172 pub fn iterable(&self) -> Option<Expr> {
1173 AstChildren::new(&self.syntax).next()
1174 }
1175}
1434#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1176#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1435pub struct LambdaExpr { 1177pub struct WhileExpr {
1436 pub(crate) syntax: SyntaxNode, 1178 pub(crate) syntax: SyntaxNode,
1437} 1179}
1438impl AstNode for LambdaExpr { 1180impl AstNode for WhileExpr {
1439 fn can_cast(kind: SyntaxKind) -> bool { 1181 fn can_cast(kind: SyntaxKind) -> bool {
1440 match kind { 1182 match kind {
1441 LAMBDA_EXPR => true, 1183 WHILE_EXPR => true,
1442 _ => false, 1184 _ => false,
1443 } 1185 }
1444 } 1186 }
@@ -1453,25 +1195,20 @@ impl AstNode for LambdaExpr {
1453 &self.syntax 1195 &self.syntax
1454 } 1196 }
1455} 1197}
1456impl LambdaExpr { 1198impl ast::LoopBodyOwner for WhileExpr {}
1457 pub fn param_list(&self) -> Option<ParamList> { 1199impl WhileExpr {
1458 AstChildren::new(&self.syntax).next() 1200 pub fn condition(&self) -> Option<Condition> {
1459 }
1460 pub fn ret_type(&self) -> Option<RetType> {
1461 AstChildren::new(&self.syntax).next()
1462 }
1463 pub fn body(&self) -> Option<Expr> {
1464 AstChildren::new(&self.syntax).next() 1201 AstChildren::new(&self.syntax).next()
1465 } 1202 }
1466} 1203}
1467#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1204#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1468pub struct LetStmt { 1205pub struct ContinueExpr {
1469 pub(crate) syntax: SyntaxNode, 1206 pub(crate) syntax: SyntaxNode,
1470} 1207}
1471impl AstNode for LetStmt { 1208impl AstNode for ContinueExpr {
1472 fn can_cast(kind: SyntaxKind) -> bool { 1209 fn can_cast(kind: SyntaxKind) -> bool {
1473 match kind { 1210 match kind {
1474 LET_STMT => true, 1211 CONTINUE_EXPR => true,
1475 _ => false, 1212 _ => false,
1476 } 1213 }
1477 } 1214 }
@@ -1486,23 +1223,15 @@ impl AstNode for LetStmt {
1486 &self.syntax 1223 &self.syntax
1487 } 1224 }
1488} 1225}
1489impl ast::TypeAscriptionOwner for LetStmt {} 1226impl ContinueExpr {}
1490impl LetStmt {
1491 pub fn pat(&self) -> Option<Pat> {
1492 AstChildren::new(&self.syntax).next()
1493 }
1494 pub fn initializer(&self) -> Option<Expr> {
1495 AstChildren::new(&self.syntax).next()
1496 }
1497}
1498#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1227#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1499pub struct LifetimeArg { 1228pub struct BreakExpr {
1500 pub(crate) syntax: SyntaxNode, 1229 pub(crate) syntax: SyntaxNode,
1501} 1230}
1502impl AstNode for LifetimeArg { 1231impl AstNode for BreakExpr {
1503 fn can_cast(kind: SyntaxKind) -> bool { 1232 fn can_cast(kind: SyntaxKind) -> bool {
1504 match kind { 1233 match kind {
1505 LIFETIME_ARG => true, 1234 BREAK_EXPR => true,
1506 _ => false, 1235 _ => false,
1507 } 1236 }
1508 } 1237 }
@@ -1517,15 +1246,19 @@ impl AstNode for LifetimeArg {
1517 &self.syntax 1246 &self.syntax
1518 } 1247 }
1519} 1248}
1520impl LifetimeArg {} 1249impl BreakExpr {
1250 pub fn expr(&self) -> Option<Expr> {
1251 AstChildren::new(&self.syntax).next()
1252 }
1253}
1521#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1254#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1522pub struct LifetimeParam { 1255pub struct Label {
1523 pub(crate) syntax: SyntaxNode, 1256 pub(crate) syntax: SyntaxNode,
1524} 1257}
1525impl AstNode for LifetimeParam { 1258impl AstNode for Label {
1526 fn can_cast(kind: SyntaxKind) -> bool { 1259 fn can_cast(kind: SyntaxKind) -> bool {
1527 match kind { 1260 match kind {
1528 LIFETIME_PARAM => true, 1261 LABEL => true,
1529 _ => false, 1262 _ => false,
1530 } 1263 }
1531 } 1264 }
@@ -1540,16 +1273,15 @@ impl AstNode for LifetimeParam {
1540 &self.syntax 1273 &self.syntax
1541 } 1274 }
1542} 1275}
1543impl ast::AttrsOwner for LifetimeParam {} 1276impl Label {}
1544impl LifetimeParam {}
1545#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1277#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1546pub struct Literal { 1278pub struct BlockExpr {
1547 pub(crate) syntax: SyntaxNode, 1279 pub(crate) syntax: SyntaxNode,
1548} 1280}
1549impl AstNode for Literal { 1281impl AstNode for BlockExpr {
1550 fn can_cast(kind: SyntaxKind) -> bool { 1282 fn can_cast(kind: SyntaxKind) -> bool {
1551 match kind { 1283 match kind {
1552 LITERAL => true, 1284 BLOCK_EXPR => true,
1553 _ => false, 1285 _ => false,
1554 } 1286 }
1555 } 1287 }
@@ -1564,15 +1296,19 @@ impl AstNode for Literal {
1564 &self.syntax 1296 &self.syntax
1565 } 1297 }
1566} 1298}
1567impl Literal {} 1299impl BlockExpr {
1300 pub fn block(&self) -> Option<Block> {
1301 AstChildren::new(&self.syntax).next()
1302 }
1303}
1568#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1304#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1569pub struct LiteralPat { 1305pub struct ReturnExpr {
1570 pub(crate) syntax: SyntaxNode, 1306 pub(crate) syntax: SyntaxNode,
1571} 1307}
1572impl AstNode for LiteralPat { 1308impl AstNode for ReturnExpr {
1573 fn can_cast(kind: SyntaxKind) -> bool { 1309 fn can_cast(kind: SyntaxKind) -> bool {
1574 match kind { 1310 match kind {
1575 LITERAL_PAT => true, 1311 RETURN_EXPR => true,
1576 _ => false, 1312 _ => false,
1577 } 1313 }
1578 } 1314 }
@@ -1587,19 +1323,19 @@ impl AstNode for LiteralPat {
1587 &self.syntax 1323 &self.syntax
1588 } 1324 }
1589} 1325}
1590impl LiteralPat { 1326impl ReturnExpr {
1591 pub fn literal(&self) -> Option<Literal> { 1327 pub fn expr(&self) -> Option<Expr> {
1592 AstChildren::new(&self.syntax).next() 1328 AstChildren::new(&self.syntax).next()
1593 } 1329 }
1594} 1330}
1595#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1331#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1596pub struct LoopExpr { 1332pub struct CallExpr {
1597 pub(crate) syntax: SyntaxNode, 1333 pub(crate) syntax: SyntaxNode,
1598} 1334}
1599impl AstNode for LoopExpr { 1335impl AstNode for CallExpr {
1600 fn can_cast(kind: SyntaxKind) -> bool { 1336 fn can_cast(kind: SyntaxKind) -> bool {
1601 match kind { 1337 match kind {
1602 LOOP_EXPR => true, 1338 CALL_EXPR => true,
1603 _ => false, 1339 _ => false,
1604 } 1340 }
1605 } 1341 }
@@ -1614,16 +1350,20 @@ impl AstNode for LoopExpr {
1614 &self.syntax 1350 &self.syntax
1615 } 1351 }
1616} 1352}
1617impl ast::LoopBodyOwner for LoopExpr {} 1353impl ast::ArgListOwner for CallExpr {}
1618impl LoopExpr {} 1354impl CallExpr {
1355 pub fn expr(&self) -> Option<Expr> {
1356 AstChildren::new(&self.syntax).next()
1357 }
1358}
1619#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1359#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1620pub struct MacroCall { 1360pub struct MethodCallExpr {
1621 pub(crate) syntax: SyntaxNode, 1361 pub(crate) syntax: SyntaxNode,
1622} 1362}
1623impl AstNode for MacroCall { 1363impl AstNode for MethodCallExpr {
1624 fn can_cast(kind: SyntaxKind) -> bool { 1364 fn can_cast(kind: SyntaxKind) -> bool {
1625 match kind { 1365 match kind {
1626 MACRO_CALL => true, 1366 METHOD_CALL_EXPR => true,
1627 _ => false, 1367 _ => false,
1628 } 1368 }
1629 } 1369 }
@@ -1638,25 +1378,26 @@ impl AstNode for MacroCall {
1638 &self.syntax 1378 &self.syntax
1639 } 1379 }
1640} 1380}
1641impl ast::NameOwner for MacroCall {} 1381impl ast::ArgListOwner for MethodCallExpr {}
1642impl ast::AttrsOwner for MacroCall {} 1382impl MethodCallExpr {
1643impl ast::DocCommentsOwner for MacroCall {} 1383 pub fn expr(&self) -> Option<Expr> {
1644impl MacroCall {
1645 pub fn token_tree(&self) -> Option<TokenTree> {
1646 AstChildren::new(&self.syntax).next() 1384 AstChildren::new(&self.syntax).next()
1647 } 1385 }
1648 pub fn path(&self) -> Option<Path> { 1386 pub fn name_ref(&self) -> Option<NameRef> {
1387 AstChildren::new(&self.syntax).next()
1388 }
1389 pub fn type_arg_list(&self) -> Option<TypeArgList> {
1649 AstChildren::new(&self.syntax).next() 1390 AstChildren::new(&self.syntax).next()
1650 } 1391 }
1651} 1392}
1652#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1393#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1653pub struct MacroItems { 1394pub struct IndexExpr {
1654 pub(crate) syntax: SyntaxNode, 1395 pub(crate) syntax: SyntaxNode,
1655} 1396}
1656impl AstNode for MacroItems { 1397impl AstNode for IndexExpr {
1657 fn can_cast(kind: SyntaxKind) -> bool { 1398 fn can_cast(kind: SyntaxKind) -> bool {
1658 match kind { 1399 match kind {
1659 MACRO_ITEMS => true, 1400 INDEX_EXPR => true,
1660 _ => false, 1401 _ => false,
1661 } 1402 }
1662 } 1403 }
@@ -1671,17 +1412,15 @@ impl AstNode for MacroItems {
1671 &self.syntax 1412 &self.syntax
1672 } 1413 }
1673} 1414}
1674impl ast::ModuleItemOwner for MacroItems {} 1415impl IndexExpr {}
1675impl ast::FnDefOwner for MacroItems {}
1676impl MacroItems {}
1677#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1416#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1678pub struct MacroStmts { 1417pub struct FieldExpr {
1679 pub(crate) syntax: SyntaxNode, 1418 pub(crate) syntax: SyntaxNode,
1680} 1419}
1681impl AstNode for MacroStmts { 1420impl AstNode for FieldExpr {
1682 fn can_cast(kind: SyntaxKind) -> bool { 1421 fn can_cast(kind: SyntaxKind) -> bool {
1683 match kind { 1422 match kind {
1684 MACRO_STMTS => true, 1423 FIELD_EXPR => true,
1685 _ => false, 1424 _ => false,
1686 } 1425 }
1687 } 1426 }
@@ -1696,22 +1435,22 @@ impl AstNode for MacroStmts {
1696 &self.syntax 1435 &self.syntax
1697 } 1436 }
1698} 1437}
1699impl MacroStmts { 1438impl FieldExpr {
1700 pub fn statements(&self) -> AstChildren<Stmt> {
1701 AstChildren::new(&self.syntax)
1702 }
1703 pub fn expr(&self) -> Option<Expr> { 1439 pub fn expr(&self) -> Option<Expr> {
1704 AstChildren::new(&self.syntax).next() 1440 AstChildren::new(&self.syntax).next()
1705 } 1441 }
1442 pub fn name_ref(&self) -> Option<NameRef> {
1443 AstChildren::new(&self.syntax).next()
1444 }
1706} 1445}
1707#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1446#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1708pub struct MatchArm { 1447pub struct AwaitExpr {
1709 pub(crate) syntax: SyntaxNode, 1448 pub(crate) syntax: SyntaxNode,
1710} 1449}
1711impl AstNode for MatchArm { 1450impl AstNode for AwaitExpr {
1712 fn can_cast(kind: SyntaxKind) -> bool { 1451 fn can_cast(kind: SyntaxKind) -> bool {
1713 match kind { 1452 match kind {
1714 MATCH_ARM => true, 1453 AWAIT_EXPR => true,
1715 _ => false, 1454 _ => false,
1716 } 1455 }
1717 } 1456 }
@@ -1726,26 +1465,19 @@ impl AstNode for MatchArm {
1726 &self.syntax 1465 &self.syntax
1727 } 1466 }
1728} 1467}
1729impl ast::AttrsOwner for MatchArm {} 1468impl AwaitExpr {
1730impl MatchArm {
1731 pub fn pats(&self) -> AstChildren<Pat> {
1732 AstChildren::new(&self.syntax)
1733 }
1734 pub fn guard(&self) -> Option<MatchGuard> {
1735 AstChildren::new(&self.syntax).next()
1736 }
1737 pub fn expr(&self) -> Option<Expr> { 1469 pub fn expr(&self) -> Option<Expr> {
1738 AstChildren::new(&self.syntax).next() 1470 AstChildren::new(&self.syntax).next()
1739 } 1471 }
1740} 1472}
1741#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1473#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1742pub struct MatchArmList { 1474pub struct TryExpr {
1743 pub(crate) syntax: SyntaxNode, 1475 pub(crate) syntax: SyntaxNode,
1744} 1476}
1745impl AstNode for MatchArmList { 1477impl AstNode for TryExpr {
1746 fn can_cast(kind: SyntaxKind) -> bool { 1478 fn can_cast(kind: SyntaxKind) -> bool {
1747 match kind { 1479 match kind {
1748 MATCH_ARM_LIST => true, 1480 TRY_EXPR => true,
1749 _ => false, 1481 _ => false,
1750 } 1482 }
1751 } 1483 }
@@ -1760,20 +1492,19 @@ impl AstNode for MatchArmList {
1760 &self.syntax 1492 &self.syntax
1761 } 1493 }
1762} 1494}
1763impl ast::AttrsOwner for MatchArmList {} 1495impl TryExpr {
1764impl MatchArmList { 1496 pub fn expr(&self) -> Option<Expr> {
1765 pub fn arms(&self) -> AstChildren<MatchArm> { 1497 AstChildren::new(&self.syntax).next()
1766 AstChildren::new(&self.syntax)
1767 } 1498 }
1768} 1499}
1769#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1500#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1770pub struct MatchExpr { 1501pub struct CastExpr {
1771 pub(crate) syntax: SyntaxNode, 1502 pub(crate) syntax: SyntaxNode,
1772} 1503}
1773impl AstNode for MatchExpr { 1504impl AstNode for CastExpr {
1774 fn can_cast(kind: SyntaxKind) -> bool { 1505 fn can_cast(kind: SyntaxKind) -> bool {
1775 match kind { 1506 match kind {
1776 MATCH_EXPR => true, 1507 CAST_EXPR => true,
1777 _ => false, 1508 _ => false,
1778 } 1509 }
1779 } 1510 }
@@ -1788,22 +1519,22 @@ impl AstNode for MatchExpr {
1788 &self.syntax 1519 &self.syntax
1789 } 1520 }
1790} 1521}
1791impl MatchExpr { 1522impl CastExpr {
1792 pub fn expr(&self) -> Option<Expr> { 1523 pub fn expr(&self) -> Option<Expr> {
1793 AstChildren::new(&self.syntax).next() 1524 AstChildren::new(&self.syntax).next()
1794 } 1525 }
1795 pub fn match_arm_list(&self) -> Option<MatchArmList> { 1526 pub fn type_ref(&self) -> Option<TypeRef> {
1796 AstChildren::new(&self.syntax).next() 1527 AstChildren::new(&self.syntax).next()
1797 } 1528 }
1798} 1529}
1799#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1530#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1800pub struct MatchGuard { 1531pub struct RefExpr {
1801 pub(crate) syntax: SyntaxNode, 1532 pub(crate) syntax: SyntaxNode,
1802} 1533}
1803impl AstNode for MatchGuard { 1534impl AstNode for RefExpr {
1804 fn can_cast(kind: SyntaxKind) -> bool { 1535 fn can_cast(kind: SyntaxKind) -> bool {
1805 match kind { 1536 match kind {
1806 MATCH_GUARD => true, 1537 REF_EXPR => true,
1807 _ => false, 1538 _ => false,
1808 } 1539 }
1809 } 1540 }
@@ -1818,19 +1549,19 @@ impl AstNode for MatchGuard {
1818 &self.syntax 1549 &self.syntax
1819 } 1550 }
1820} 1551}
1821impl MatchGuard { 1552impl RefExpr {
1822 pub fn expr(&self) -> Option<Expr> { 1553 pub fn expr(&self) -> Option<Expr> {
1823 AstChildren::new(&self.syntax).next() 1554 AstChildren::new(&self.syntax).next()
1824 } 1555 }
1825} 1556}
1826#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1557#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1827pub struct MethodCallExpr { 1558pub struct PrefixExpr {
1828 pub(crate) syntax: SyntaxNode, 1559 pub(crate) syntax: SyntaxNode,
1829} 1560}
1830impl AstNode for MethodCallExpr { 1561impl AstNode for PrefixExpr {
1831 fn can_cast(kind: SyntaxKind) -> bool { 1562 fn can_cast(kind: SyntaxKind) -> bool {
1832 match kind { 1563 match kind {
1833 METHOD_CALL_EXPR => true, 1564 PREFIX_EXPR => true,
1834 _ => false, 1565 _ => false,
1835 } 1566 }
1836 } 1567 }
@@ -1845,26 +1576,19 @@ impl AstNode for MethodCallExpr {
1845 &self.syntax 1576 &self.syntax
1846 } 1577 }
1847} 1578}
1848impl ast::ArgListOwner for MethodCallExpr {} 1579impl PrefixExpr {
1849impl MethodCallExpr {
1850 pub fn expr(&self) -> Option<Expr> { 1580 pub fn expr(&self) -> Option<Expr> {
1851 AstChildren::new(&self.syntax).next() 1581 AstChildren::new(&self.syntax).next()
1852 } 1582 }
1853 pub fn name_ref(&self) -> Option<NameRef> {
1854 AstChildren::new(&self.syntax).next()
1855 }
1856 pub fn type_arg_list(&self) -> Option<TypeArgList> {
1857 AstChildren::new(&self.syntax).next()
1858 }
1859} 1583}
1860#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1584#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1861pub struct Module { 1585pub struct BoxExpr {
1862 pub(crate) syntax: SyntaxNode, 1586 pub(crate) syntax: SyntaxNode,
1863} 1587}
1864impl AstNode for Module { 1588impl AstNode for BoxExpr {
1865 fn can_cast(kind: SyntaxKind) -> bool { 1589 fn can_cast(kind: SyntaxKind) -> bool {
1866 match kind { 1590 match kind {
1867 MODULE => true, 1591 BOX_EXPR => true,
1868 _ => false, 1592 _ => false,
1869 } 1593 }
1870 } 1594 }
@@ -1879,144 +1603,42 @@ impl AstNode for Module {
1879 &self.syntax 1603 &self.syntax
1880 } 1604 }
1881} 1605}
1882impl ast::VisibilityOwner for Module {} 1606impl BoxExpr {
1883impl ast::NameOwner for Module {} 1607 pub fn expr(&self) -> Option<Expr> {
1884impl ast::AttrsOwner for Module {}
1885impl ast::DocCommentsOwner for Module {}
1886impl Module {
1887 pub fn item_list(&self) -> Option<ItemList> {
1888 AstChildren::new(&self.syntax).next() 1608 AstChildren::new(&self.syntax).next()
1889 } 1609 }
1890} 1610}
1891#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1611#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1892pub enum ModuleItem { 1612pub struct RangeExpr {
1893 StructDef(StructDef), 1613 pub(crate) syntax: SyntaxNode,
1894 UnionDef(UnionDef),
1895 EnumDef(EnumDef),
1896 FnDef(FnDef),
1897 TraitDef(TraitDef),
1898 TypeAliasDef(TypeAliasDef),
1899 ImplBlock(ImplBlock),
1900 UseItem(UseItem),
1901 ExternCrateItem(ExternCrateItem),
1902 ConstDef(ConstDef),
1903 StaticDef(StaticDef),
1904 Module(Module),
1905}
1906impl From<StructDef> for ModuleItem {
1907 fn from(node: StructDef) -> ModuleItem {
1908 ModuleItem::StructDef(node)
1909 }
1910}
1911impl From<UnionDef> for ModuleItem {
1912 fn from(node: UnionDef) -> ModuleItem {
1913 ModuleItem::UnionDef(node)
1914 }
1915}
1916impl From<EnumDef> for ModuleItem {
1917 fn from(node: EnumDef) -> ModuleItem {
1918 ModuleItem::EnumDef(node)
1919 }
1920}
1921impl From<FnDef> for ModuleItem {
1922 fn from(node: FnDef) -> ModuleItem {
1923 ModuleItem::FnDef(node)
1924 }
1925}
1926impl From<TraitDef> for ModuleItem {
1927 fn from(node: TraitDef) -> ModuleItem {
1928 ModuleItem::TraitDef(node)
1929 }
1930}
1931impl From<TypeAliasDef> for ModuleItem {
1932 fn from(node: TypeAliasDef) -> ModuleItem {
1933 ModuleItem::TypeAliasDef(node)
1934 }
1935}
1936impl From<ImplBlock> for ModuleItem {
1937 fn from(node: ImplBlock) -> ModuleItem {
1938 ModuleItem::ImplBlock(node)
1939 }
1940}
1941impl From<UseItem> for ModuleItem {
1942 fn from(node: UseItem) -> ModuleItem {
1943 ModuleItem::UseItem(node)
1944 }
1945}
1946impl From<ExternCrateItem> for ModuleItem {
1947 fn from(node: ExternCrateItem) -> ModuleItem {
1948 ModuleItem::ExternCrateItem(node)
1949 }
1950}
1951impl From<ConstDef> for ModuleItem {
1952 fn from(node: ConstDef) -> ModuleItem {
1953 ModuleItem::ConstDef(node)
1954 }
1955}
1956impl From<StaticDef> for ModuleItem {
1957 fn from(node: StaticDef) -> ModuleItem {
1958 ModuleItem::StaticDef(node)
1959 }
1960}
1961impl From<Module> for ModuleItem {
1962 fn from(node: Module) -> ModuleItem {
1963 ModuleItem::Module(node)
1964 }
1965} 1614}
1966impl AstNode for ModuleItem { 1615impl AstNode for RangeExpr {
1967 fn can_cast(kind: SyntaxKind) -> bool { 1616 fn can_cast(kind: SyntaxKind) -> bool {
1968 match kind { 1617 match kind {
1969 STRUCT_DEF | UNION_DEF | ENUM_DEF | FN_DEF | TRAIT_DEF | TYPE_ALIAS_DEF 1618 RANGE_EXPR => true,
1970 | IMPL_BLOCK | USE_ITEM | EXTERN_CRATE_ITEM | CONST_DEF | STATIC_DEF | MODULE => true,
1971 _ => false, 1619 _ => false,
1972 } 1620 }
1973 } 1621 }
1974 fn cast(syntax: SyntaxNode) -> Option<Self> { 1622 fn cast(syntax: SyntaxNode) -> Option<Self> {
1975 let res = match syntax.kind() { 1623 if Self::can_cast(syntax.kind()) {
1976 STRUCT_DEF => ModuleItem::StructDef(StructDef { syntax }), 1624 Some(Self { syntax })
1977 UNION_DEF => ModuleItem::UnionDef(UnionDef { syntax }), 1625 } else {
1978 ENUM_DEF => ModuleItem::EnumDef(EnumDef { syntax }), 1626 None
1979 FN_DEF => ModuleItem::FnDef(FnDef { syntax }), 1627 }
1980 TRAIT_DEF => ModuleItem::TraitDef(TraitDef { syntax }),
1981 TYPE_ALIAS_DEF => ModuleItem::TypeAliasDef(TypeAliasDef { syntax }),
1982 IMPL_BLOCK => ModuleItem::ImplBlock(ImplBlock { syntax }),
1983 USE_ITEM => ModuleItem::UseItem(UseItem { syntax }),
1984 EXTERN_CRATE_ITEM => ModuleItem::ExternCrateItem(ExternCrateItem { syntax }),
1985 CONST_DEF => ModuleItem::ConstDef(ConstDef { syntax }),
1986 STATIC_DEF => ModuleItem::StaticDef(StaticDef { syntax }),
1987 MODULE => ModuleItem::Module(Module { syntax }),
1988 _ => return None,
1989 };
1990 Some(res)
1991 } 1628 }
1992 fn syntax(&self) -> &SyntaxNode { 1629 fn syntax(&self) -> &SyntaxNode {
1993 match self { 1630 &self.syntax
1994 ModuleItem::StructDef(it) => &it.syntax,
1995 ModuleItem::UnionDef(it) => &it.syntax,
1996 ModuleItem::EnumDef(it) => &it.syntax,
1997 ModuleItem::FnDef(it) => &it.syntax,
1998 ModuleItem::TraitDef(it) => &it.syntax,
1999 ModuleItem::TypeAliasDef(it) => &it.syntax,
2000 ModuleItem::ImplBlock(it) => &it.syntax,
2001 ModuleItem::UseItem(it) => &it.syntax,
2002 ModuleItem::ExternCrateItem(it) => &it.syntax,
2003 ModuleItem::ConstDef(it) => &it.syntax,
2004 ModuleItem::StaticDef(it) => &it.syntax,
2005 ModuleItem::Module(it) => &it.syntax,
2006 }
2007 } 1631 }
2008} 1632}
2009impl ast::AttrsOwner for ModuleItem {} 1633impl RangeExpr {}
2010impl ast::VisibilityOwner for ModuleItem {}
2011impl ModuleItem {}
2012#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1634#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2013pub struct Name { 1635pub struct BinExpr {
2014 pub(crate) syntax: SyntaxNode, 1636 pub(crate) syntax: SyntaxNode,
2015} 1637}
2016impl AstNode for Name { 1638impl AstNode for BinExpr {
2017 fn can_cast(kind: SyntaxKind) -> bool { 1639 fn can_cast(kind: SyntaxKind) -> bool {
2018 match kind { 1640 match kind {
2019 NAME => true, 1641 BIN_EXPR => true,
2020 _ => false, 1642 _ => false,
2021 } 1643 }
2022 } 1644 }
@@ -2031,15 +1653,15 @@ impl AstNode for Name {
2031 &self.syntax 1653 &self.syntax
2032 } 1654 }
2033} 1655}
2034impl Name {} 1656impl BinExpr {}
2035#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1657#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2036pub struct NameRef { 1658pub struct Literal {
2037 pub(crate) syntax: SyntaxNode, 1659 pub(crate) syntax: SyntaxNode,
2038} 1660}
2039impl AstNode for NameRef { 1661impl AstNode for Literal {
2040 fn can_cast(kind: SyntaxKind) -> bool { 1662 fn can_cast(kind: SyntaxKind) -> bool {
2041 match kind { 1663 match kind {
2042 NAME_REF => true, 1664 LITERAL => true,
2043 _ => false, 1665 _ => false,
2044 } 1666 }
2045 } 1667 }
@@ -2054,15 +1676,15 @@ impl AstNode for NameRef {
2054 &self.syntax 1676 &self.syntax
2055 } 1677 }
2056} 1678}
2057impl NameRef {} 1679impl Literal {}
2058#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1680#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2059pub struct NeverType { 1681pub struct MatchExpr {
2060 pub(crate) syntax: SyntaxNode, 1682 pub(crate) syntax: SyntaxNode,
2061} 1683}
2062impl AstNode for NeverType { 1684impl AstNode for MatchExpr {
2063 fn can_cast(kind: SyntaxKind) -> bool { 1685 fn can_cast(kind: SyntaxKind) -> bool {
2064 match kind { 1686 match kind {
2065 NEVER_TYPE => true, 1687 MATCH_EXPR => true,
2066 _ => false, 1688 _ => false,
2067 } 1689 }
2068 } 1690 }
@@ -2077,64 +1699,50 @@ impl AstNode for NeverType {
2077 &self.syntax 1699 &self.syntax
2078 } 1700 }
2079} 1701}
2080impl NeverType {} 1702impl MatchExpr {
2081#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1703 pub fn expr(&self) -> Option<Expr> {
2082pub enum NominalDef { 1704 AstChildren::new(&self.syntax).next()
2083 StructDef(StructDef),
2084 EnumDef(EnumDef),
2085 UnionDef(UnionDef),
2086}
2087impl From<StructDef> for NominalDef {
2088 fn from(node: StructDef) -> NominalDef {
2089 NominalDef::StructDef(node)
2090 } 1705 }
2091} 1706 pub fn match_arm_list(&self) -> Option<MatchArmList> {
2092impl From<EnumDef> for NominalDef { 1707 AstChildren::new(&self.syntax).next()
2093 fn from(node: EnumDef) -> NominalDef {
2094 NominalDef::EnumDef(node)
2095 } 1708 }
2096} 1709}
2097impl From<UnionDef> for NominalDef { 1710#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2098 fn from(node: UnionDef) -> NominalDef { 1711pub struct MatchArmList {
2099 NominalDef::UnionDef(node) 1712 pub(crate) syntax: SyntaxNode,
2100 }
2101} 1713}
2102impl AstNode for NominalDef { 1714impl AstNode for MatchArmList {
2103 fn can_cast(kind: SyntaxKind) -> bool { 1715 fn can_cast(kind: SyntaxKind) -> bool {
2104 match kind { 1716 match kind {
2105 STRUCT_DEF | ENUM_DEF | UNION_DEF => true, 1717 MATCH_ARM_LIST => true,
2106 _ => false, 1718 _ => false,
2107 } 1719 }
2108 } 1720 }
2109 fn cast(syntax: SyntaxNode) -> Option<Self> { 1721 fn cast(syntax: SyntaxNode) -> Option<Self> {
2110 let res = match syntax.kind() { 1722 if Self::can_cast(syntax.kind()) {
2111 STRUCT_DEF => NominalDef::StructDef(StructDef { syntax }), 1723 Some(Self { syntax })
2112 ENUM_DEF => NominalDef::EnumDef(EnumDef { syntax }), 1724 } else {
2113 UNION_DEF => NominalDef::UnionDef(UnionDef { syntax }), 1725 None
2114 _ => return None, 1726 }
2115 };
2116 Some(res)
2117 } 1727 }
2118 fn syntax(&self) -> &SyntaxNode { 1728 fn syntax(&self) -> &SyntaxNode {
2119 match self { 1729 &self.syntax
2120 NominalDef::StructDef(it) => &it.syntax, 1730 }
2121 NominalDef::EnumDef(it) => &it.syntax, 1731}
2122 NominalDef::UnionDef(it) => &it.syntax, 1732impl ast::AttrsOwner for MatchArmList {}
2123 } 1733impl MatchArmList {
1734 pub fn arms(&self) -> AstChildren<MatchArm> {
1735 AstChildren::new(&self.syntax)
2124 } 1736 }
2125} 1737}
2126impl ast::NameOwner for NominalDef {}
2127impl ast::TypeParamsOwner for NominalDef {}
2128impl ast::AttrsOwner for NominalDef {}
2129impl NominalDef {}
2130#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1738#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2131pub struct Param { 1739pub struct MatchArm {
2132 pub(crate) syntax: SyntaxNode, 1740 pub(crate) syntax: SyntaxNode,
2133} 1741}
2134impl AstNode for Param { 1742impl AstNode for MatchArm {
2135 fn can_cast(kind: SyntaxKind) -> bool { 1743 fn can_cast(kind: SyntaxKind) -> bool {
2136 match kind { 1744 match kind {
2137 PARAM => true, 1745 MATCH_ARM => true,
2138 _ => false, 1746 _ => false,
2139 } 1747 }
2140 } 1748 }
@@ -2149,21 +1757,26 @@ impl AstNode for Param {
2149 &self.syntax 1757 &self.syntax
2150 } 1758 }
2151} 1759}
2152impl ast::TypeAscriptionOwner for Param {} 1760impl ast::AttrsOwner for MatchArm {}
2153impl ast::AttrsOwner for Param {} 1761impl MatchArm {
2154impl Param { 1762 pub fn pats(&self) -> AstChildren<Pat> {
2155 pub fn pat(&self) -> Option<Pat> { 1763 AstChildren::new(&self.syntax)
1764 }
1765 pub fn guard(&self) -> Option<MatchGuard> {
1766 AstChildren::new(&self.syntax).next()
1767 }
1768 pub fn expr(&self) -> Option<Expr> {
2156 AstChildren::new(&self.syntax).next() 1769 AstChildren::new(&self.syntax).next()
2157 } 1770 }
2158} 1771}
2159#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1772#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2160pub struct ParamList { 1773pub struct MatchGuard {
2161 pub(crate) syntax: SyntaxNode, 1774 pub(crate) syntax: SyntaxNode,
2162} 1775}
2163impl AstNode for ParamList { 1776impl AstNode for MatchGuard {
2164 fn can_cast(kind: SyntaxKind) -> bool { 1777 fn can_cast(kind: SyntaxKind) -> bool {
2165 match kind { 1778 match kind {
2166 PARAM_LIST => true, 1779 MATCH_GUARD => true,
2167 _ => false, 1780 _ => false,
2168 } 1781 }
2169 } 1782 }
@@ -2178,22 +1791,19 @@ impl AstNode for ParamList {
2178 &self.syntax 1791 &self.syntax
2179 } 1792 }
2180} 1793}
2181impl ParamList { 1794impl MatchGuard {
2182 pub fn params(&self) -> AstChildren<Param> { 1795 pub fn expr(&self) -> Option<Expr> {
2183 AstChildren::new(&self.syntax)
2184 }
2185 pub fn self_param(&self) -> Option<SelfParam> {
2186 AstChildren::new(&self.syntax).next() 1796 AstChildren::new(&self.syntax).next()
2187 } 1797 }
2188} 1798}
2189#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1799#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2190pub struct ParenExpr { 1800pub struct RecordLit {
2191 pub(crate) syntax: SyntaxNode, 1801 pub(crate) syntax: SyntaxNode,
2192} 1802}
2193impl AstNode for ParenExpr { 1803impl AstNode for RecordLit {
2194 fn can_cast(kind: SyntaxKind) -> bool { 1804 fn can_cast(kind: SyntaxKind) -> bool {
2195 match kind { 1805 match kind {
2196 PAREN_EXPR => true, 1806 RECORD_LIT => true,
2197 _ => false, 1807 _ => false,
2198 } 1808 }
2199 } 1809 }
@@ -2208,19 +1818,22 @@ impl AstNode for ParenExpr {
2208 &self.syntax 1818 &self.syntax
2209 } 1819 }
2210} 1820}
2211impl ParenExpr { 1821impl RecordLit {
2212 pub fn expr(&self) -> Option<Expr> { 1822 pub fn path(&self) -> Option<Path> {
1823 AstChildren::new(&self.syntax).next()
1824 }
1825 pub fn record_field_list(&self) -> Option<RecordFieldList> {
2213 AstChildren::new(&self.syntax).next() 1826 AstChildren::new(&self.syntax).next()
2214 } 1827 }
2215} 1828}
2216#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1829#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2217pub struct ParenType { 1830pub struct RecordFieldList {
2218 pub(crate) syntax: SyntaxNode, 1831 pub(crate) syntax: SyntaxNode,
2219} 1832}
2220impl AstNode for ParenType { 1833impl AstNode for RecordFieldList {
2221 fn can_cast(kind: SyntaxKind) -> bool { 1834 fn can_cast(kind: SyntaxKind) -> bool {
2222 match kind { 1835 match kind {
2223 PAREN_TYPE => true, 1836 RECORD_FIELD_LIST => true,
2224 _ => false, 1837 _ => false,
2225 } 1838 }
2226 } 1839 }
@@ -2235,140 +1848,79 @@ impl AstNode for ParenType {
2235 &self.syntax 1848 &self.syntax
2236 } 1849 }
2237} 1850}
2238impl ParenType { 1851impl RecordFieldList {
2239 pub fn type_ref(&self) -> Option<TypeRef> { 1852 pub fn fields(&self) -> AstChildren<RecordField> {
1853 AstChildren::new(&self.syntax)
1854 }
1855 pub fn spread(&self) -> Option<Expr> {
2240 AstChildren::new(&self.syntax).next() 1856 AstChildren::new(&self.syntax).next()
2241 } 1857 }
2242} 1858}
2243#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1859#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2244pub enum Pat { 1860pub struct RecordField {
2245 RefPat(RefPat), 1861 pub(crate) syntax: SyntaxNode,
2246 BoxPat(BoxPat),
2247 BindPat(BindPat),
2248 PlaceholderPat(PlaceholderPat),
2249 DotDotPat(DotDotPat),
2250 PathPat(PathPat),
2251 RecordPat(RecordPat),
2252 TupleStructPat(TupleStructPat),
2253 TuplePat(TuplePat),
2254 SlicePat(SlicePat),
2255 RangePat(RangePat),
2256 LiteralPat(LiteralPat),
2257}
2258impl From<RefPat> for Pat {
2259 fn from(node: RefPat) -> Pat {
2260 Pat::RefPat(node)
2261 }
2262}
2263impl From<BoxPat> for Pat {
2264 fn from(node: BoxPat) -> Pat {
2265 Pat::BoxPat(node)
2266 }
2267}
2268impl From<BindPat> for Pat {
2269 fn from(node: BindPat) -> Pat {
2270 Pat::BindPat(node)
2271 }
2272}
2273impl From<PlaceholderPat> for Pat {
2274 fn from(node: PlaceholderPat) -> Pat {
2275 Pat::PlaceholderPat(node)
2276 }
2277}
2278impl From<DotDotPat> for Pat {
2279 fn from(node: DotDotPat) -> Pat {
2280 Pat::DotDotPat(node)
2281 }
2282}
2283impl From<PathPat> for Pat {
2284 fn from(node: PathPat) -> Pat {
2285 Pat::PathPat(node)
2286 }
2287} 1862}
2288impl From<RecordPat> for Pat { 1863impl AstNode for RecordField {
2289 fn from(node: RecordPat) -> Pat { 1864 fn can_cast(kind: SyntaxKind) -> bool {
2290 Pat::RecordPat(node) 1865 match kind {
1866 RECORD_FIELD => true,
1867 _ => false,
1868 }
2291 } 1869 }
2292} 1870 fn cast(syntax: SyntaxNode) -> Option<Self> {
2293impl From<TupleStructPat> for Pat { 1871 if Self::can_cast(syntax.kind()) {
2294 fn from(node: TupleStructPat) -> Pat { 1872 Some(Self { syntax })
2295 Pat::TupleStructPat(node) 1873 } else {
1874 None
1875 }
2296 } 1876 }
2297} 1877 fn syntax(&self) -> &SyntaxNode {
2298impl From<TuplePat> for Pat { 1878 &self.syntax
2299 fn from(node: TuplePat) -> Pat {
2300 Pat::TuplePat(node)
2301 } 1879 }
2302} 1880}
2303impl From<SlicePat> for Pat { 1881impl RecordField {
2304 fn from(node: SlicePat) -> Pat { 1882 pub fn name_ref(&self) -> Option<NameRef> {
2305 Pat::SlicePat(node) 1883 AstChildren::new(&self.syntax).next()
2306 } 1884 }
2307} 1885 pub fn expr(&self) -> Option<Expr> {
2308impl From<RangePat> for Pat { 1886 AstChildren::new(&self.syntax).next()
2309 fn from(node: RangePat) -> Pat {
2310 Pat::RangePat(node)
2311 } 1887 }
2312} 1888}
2313impl From<LiteralPat> for Pat { 1889#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2314 fn from(node: LiteralPat) -> Pat { 1890pub struct RefPat {
2315 Pat::LiteralPat(node) 1891 pub(crate) syntax: SyntaxNode,
2316 }
2317} 1892}
2318impl AstNode for Pat { 1893impl AstNode for RefPat {
2319 fn can_cast(kind: SyntaxKind) -> bool { 1894 fn can_cast(kind: SyntaxKind) -> bool {
2320 match kind { 1895 match kind {
2321 REF_PAT | BOX_PAT | BIND_PAT | PLACEHOLDER_PAT | DOT_DOT_PAT | PATH_PAT 1896 REF_PAT => true,
2322 | RECORD_PAT | TUPLE_STRUCT_PAT | TUPLE_PAT | SLICE_PAT | RANGE_PAT | LITERAL_PAT => {
2323 true
2324 }
2325 _ => false, 1897 _ => false,
2326 } 1898 }
2327 } 1899 }
2328 fn cast(syntax: SyntaxNode) -> Option<Self> { 1900 fn cast(syntax: SyntaxNode) -> Option<Self> {
2329 let res = match syntax.kind() { 1901 if Self::can_cast(syntax.kind()) {
2330 REF_PAT => Pat::RefPat(RefPat { syntax }), 1902 Some(Self { syntax })
2331 BOX_PAT => Pat::BoxPat(BoxPat { syntax }), 1903 } else {
2332 BIND_PAT => Pat::BindPat(BindPat { syntax }), 1904 None
2333 PLACEHOLDER_PAT => Pat::PlaceholderPat(PlaceholderPat { syntax }), 1905 }
2334 DOT_DOT_PAT => Pat::DotDotPat(DotDotPat { syntax }),
2335 PATH_PAT => Pat::PathPat(PathPat { syntax }),
2336 RECORD_PAT => Pat::RecordPat(RecordPat { syntax }),
2337 TUPLE_STRUCT_PAT => Pat::TupleStructPat(TupleStructPat { syntax }),
2338 TUPLE_PAT => Pat::TuplePat(TuplePat { syntax }),
2339 SLICE_PAT => Pat::SlicePat(SlicePat { syntax }),
2340 RANGE_PAT => Pat::RangePat(RangePat { syntax }),
2341 LITERAL_PAT => Pat::LiteralPat(LiteralPat { syntax }),
2342 _ => return None,
2343 };
2344 Some(res)
2345 } 1906 }
2346 fn syntax(&self) -> &SyntaxNode { 1907 fn syntax(&self) -> &SyntaxNode {
2347 match self { 1908 &self.syntax
2348 Pat::RefPat(it) => &it.syntax, 1909 }
2349 Pat::BoxPat(it) => &it.syntax, 1910}
2350 Pat::BindPat(it) => &it.syntax, 1911impl RefPat {
2351 Pat::PlaceholderPat(it) => &it.syntax, 1912 pub fn pat(&self) -> Option<Pat> {
2352 Pat::DotDotPat(it) => &it.syntax, 1913 AstChildren::new(&self.syntax).next()
2353 Pat::PathPat(it) => &it.syntax,
2354 Pat::RecordPat(it) => &it.syntax,
2355 Pat::TupleStructPat(it) => &it.syntax,
2356 Pat::TuplePat(it) => &it.syntax,
2357 Pat::SlicePat(it) => &it.syntax,
2358 Pat::RangePat(it) => &it.syntax,
2359 Pat::LiteralPat(it) => &it.syntax,
2360 }
2361 } 1914 }
2362} 1915}
2363impl Pat {}
2364#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1916#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2365pub struct Path { 1917pub struct BoxPat {
2366 pub(crate) syntax: SyntaxNode, 1918 pub(crate) syntax: SyntaxNode,
2367} 1919}
2368impl AstNode for Path { 1920impl AstNode for BoxPat {
2369 fn can_cast(kind: SyntaxKind) -> bool { 1921 fn can_cast(kind: SyntaxKind) -> bool {
2370 match kind { 1922 match kind {
2371 PATH => true, 1923 BOX_PAT => true,
2372 _ => false, 1924 _ => false,
2373 } 1925 }
2374 } 1926 }
@@ -2383,22 +1935,19 @@ impl AstNode for Path {
2383 &self.syntax 1935 &self.syntax
2384 } 1936 }
2385} 1937}
2386impl Path { 1938impl BoxPat {
2387 pub fn segment(&self) -> Option<PathSegment> { 1939 pub fn pat(&self) -> Option<Pat> {
2388 AstChildren::new(&self.syntax).next()
2389 }
2390 pub fn qualifier(&self) -> Option<Path> {
2391 AstChildren::new(&self.syntax).next() 1940 AstChildren::new(&self.syntax).next()
2392 } 1941 }
2393} 1942}
2394#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1943#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2395pub struct PathExpr { 1944pub struct BindPat {
2396 pub(crate) syntax: SyntaxNode, 1945 pub(crate) syntax: SyntaxNode,
2397} 1946}
2398impl AstNode for PathExpr { 1947impl AstNode for BindPat {
2399 fn can_cast(kind: SyntaxKind) -> bool { 1948 fn can_cast(kind: SyntaxKind) -> bool {
2400 match kind { 1949 match kind {
2401 PATH_EXPR => true, 1950 BIND_PAT => true,
2402 _ => false, 1951 _ => false,
2403 } 1952 }
2404 } 1953 }
@@ -2413,19 +1962,20 @@ impl AstNode for PathExpr {
2413 &self.syntax 1962 &self.syntax
2414 } 1963 }
2415} 1964}
2416impl PathExpr { 1965impl ast::NameOwner for BindPat {}
2417 pub fn path(&self) -> Option<Path> { 1966impl BindPat {
1967 pub fn pat(&self) -> Option<Pat> {
2418 AstChildren::new(&self.syntax).next() 1968 AstChildren::new(&self.syntax).next()
2419 } 1969 }
2420} 1970}
2421#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1971#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2422pub struct PathPat { 1972pub struct PlaceholderPat {
2423 pub(crate) syntax: SyntaxNode, 1973 pub(crate) syntax: SyntaxNode,
2424} 1974}
2425impl AstNode for PathPat { 1975impl AstNode for PlaceholderPat {
2426 fn can_cast(kind: SyntaxKind) -> bool { 1976 fn can_cast(kind: SyntaxKind) -> bool {
2427 match kind { 1977 match kind {
2428 PATH_PAT => true, 1978 PLACEHOLDER_PAT => true,
2429 _ => false, 1979 _ => false,
2430 } 1980 }
2431 } 1981 }
@@ -2440,19 +1990,15 @@ impl AstNode for PathPat {
2440 &self.syntax 1990 &self.syntax
2441 } 1991 }
2442} 1992}
2443impl PathPat { 1993impl PlaceholderPat {}
2444 pub fn path(&self) -> Option<Path> {
2445 AstChildren::new(&self.syntax).next()
2446 }
2447}
2448#[derive(Debug, Clone, PartialEq, Eq, Hash)] 1994#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2449pub struct PathSegment { 1995pub struct DotDotPat {
2450 pub(crate) syntax: SyntaxNode, 1996 pub(crate) syntax: SyntaxNode,
2451} 1997}
2452impl AstNode for PathSegment { 1998impl AstNode for DotDotPat {
2453 fn can_cast(kind: SyntaxKind) -> bool { 1999 fn can_cast(kind: SyntaxKind) -> bool {
2454 match kind { 2000 match kind {
2455 PATH_SEGMENT => true, 2001 DOT_DOT_PAT => true,
2456 _ => false, 2002 _ => false,
2457 } 2003 }
2458 } 2004 }
@@ -2467,31 +2013,15 @@ impl AstNode for PathSegment {
2467 &self.syntax 2013 &self.syntax
2468 } 2014 }
2469} 2015}
2470impl PathSegment { 2016impl DotDotPat {}
2471 pub fn name_ref(&self) -> Option<NameRef> {
2472 AstChildren::new(&self.syntax).next()
2473 }
2474 pub fn type_arg_list(&self) -> Option<TypeArgList> {
2475 AstChildren::new(&self.syntax).next()
2476 }
2477 pub fn param_list(&self) -> Option<ParamList> {
2478 AstChildren::new(&self.syntax).next()
2479 }
2480 pub fn ret_type(&self) -> Option<RetType> {
2481 AstChildren::new(&self.syntax).next()
2482 }
2483 pub fn path_type(&self) -> Option<PathType> {
2484 AstChildren::new(&self.syntax).next()
2485 }
2486}
2487#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2017#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2488pub struct PathType { 2018pub struct PathPat {
2489 pub(crate) syntax: SyntaxNode, 2019 pub(crate) syntax: SyntaxNode,
2490} 2020}
2491impl AstNode for PathType { 2021impl AstNode for PathPat {
2492 fn can_cast(kind: SyntaxKind) -> bool { 2022 fn can_cast(kind: SyntaxKind) -> bool {
2493 match kind { 2023 match kind {
2494 PATH_TYPE => true, 2024 PATH_PAT => true,
2495 _ => false, 2025 _ => false,
2496 } 2026 }
2497 } 2027 }
@@ -2506,19 +2036,19 @@ impl AstNode for PathType {
2506 &self.syntax 2036 &self.syntax
2507 } 2037 }
2508} 2038}
2509impl PathType { 2039impl PathPat {
2510 pub fn path(&self) -> Option<Path> { 2040 pub fn path(&self) -> Option<Path> {
2511 AstChildren::new(&self.syntax).next() 2041 AstChildren::new(&self.syntax).next()
2512 } 2042 }
2513} 2043}
2514#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2044#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2515pub struct PlaceholderPat { 2045pub struct SlicePat {
2516 pub(crate) syntax: SyntaxNode, 2046 pub(crate) syntax: SyntaxNode,
2517} 2047}
2518impl AstNode for PlaceholderPat { 2048impl AstNode for SlicePat {
2519 fn can_cast(kind: SyntaxKind) -> bool { 2049 fn can_cast(kind: SyntaxKind) -> bool {
2520 match kind { 2050 match kind {
2521 PLACEHOLDER_PAT => true, 2051 SLICE_PAT => true,
2522 _ => false, 2052 _ => false,
2523 } 2053 }
2524 } 2054 }
@@ -2533,15 +2063,15 @@ impl AstNode for PlaceholderPat {
2533 &self.syntax 2063 &self.syntax
2534 } 2064 }
2535} 2065}
2536impl PlaceholderPat {} 2066impl SlicePat {}
2537#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2067#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2538pub struct PlaceholderType { 2068pub struct RangePat {
2539 pub(crate) syntax: SyntaxNode, 2069 pub(crate) syntax: SyntaxNode,
2540} 2070}
2541impl AstNode for PlaceholderType { 2071impl AstNode for RangePat {
2542 fn can_cast(kind: SyntaxKind) -> bool { 2072 fn can_cast(kind: SyntaxKind) -> bool {
2543 match kind { 2073 match kind {
2544 PLACEHOLDER_TYPE => true, 2074 RANGE_PAT => true,
2545 _ => false, 2075 _ => false,
2546 } 2076 }
2547 } 2077 }
@@ -2556,15 +2086,15 @@ impl AstNode for PlaceholderType {
2556 &self.syntax 2086 &self.syntax
2557 } 2087 }
2558} 2088}
2559impl PlaceholderType {} 2089impl RangePat {}
2560#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2090#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2561pub struct PointerType { 2091pub struct LiteralPat {
2562 pub(crate) syntax: SyntaxNode, 2092 pub(crate) syntax: SyntaxNode,
2563} 2093}
2564impl AstNode for PointerType { 2094impl AstNode for LiteralPat {
2565 fn can_cast(kind: SyntaxKind) -> bool { 2095 fn can_cast(kind: SyntaxKind) -> bool {
2566 match kind { 2096 match kind {
2567 POINTER_TYPE => true, 2097 LITERAL_PAT => true,
2568 _ => false, 2098 _ => false,
2569 } 2099 }
2570 } 2100 }
@@ -2579,19 +2109,19 @@ impl AstNode for PointerType {
2579 &self.syntax 2109 &self.syntax
2580 } 2110 }
2581} 2111}
2582impl PointerType { 2112impl LiteralPat {
2583 pub fn type_ref(&self) -> Option<TypeRef> { 2113 pub fn literal(&self) -> Option<Literal> {
2584 AstChildren::new(&self.syntax).next() 2114 AstChildren::new(&self.syntax).next()
2585 } 2115 }
2586} 2116}
2587#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2117#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2588pub struct PrefixExpr { 2118pub struct RecordPat {
2589 pub(crate) syntax: SyntaxNode, 2119 pub(crate) syntax: SyntaxNode,
2590} 2120}
2591impl AstNode for PrefixExpr { 2121impl AstNode for RecordPat {
2592 fn can_cast(kind: SyntaxKind) -> bool { 2122 fn can_cast(kind: SyntaxKind) -> bool {
2593 match kind { 2123 match kind {
2594 PREFIX_EXPR => true, 2124 RECORD_PAT => true,
2595 _ => false, 2125 _ => false,
2596 } 2126 }
2597 } 2127 }
@@ -2606,19 +2136,22 @@ impl AstNode for PrefixExpr {
2606 &self.syntax 2136 &self.syntax
2607 } 2137 }
2608} 2138}
2609impl PrefixExpr { 2139impl RecordPat {
2610 pub fn expr(&self) -> Option<Expr> { 2140 pub fn record_field_pat_list(&self) -> Option<RecordFieldPatList> {
2141 AstChildren::new(&self.syntax).next()
2142 }
2143 pub fn path(&self) -> Option<Path> {
2611 AstChildren::new(&self.syntax).next() 2144 AstChildren::new(&self.syntax).next()
2612 } 2145 }
2613} 2146}
2614#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2147#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2615pub struct RangeExpr { 2148pub struct RecordFieldPatList {
2616 pub(crate) syntax: SyntaxNode, 2149 pub(crate) syntax: SyntaxNode,
2617} 2150}
2618impl AstNode for RangeExpr { 2151impl AstNode for RecordFieldPatList {
2619 fn can_cast(kind: SyntaxKind) -> bool { 2152 fn can_cast(kind: SyntaxKind) -> bool {
2620 match kind { 2153 match kind {
2621 RANGE_EXPR => true, 2154 RECORD_FIELD_PAT_LIST => true,
2622 _ => false, 2155 _ => false,
2623 } 2156 }
2624 } 2157 }
@@ -2633,15 +2166,22 @@ impl AstNode for RangeExpr {
2633 &self.syntax 2166 &self.syntax
2634 } 2167 }
2635} 2168}
2636impl RangeExpr {} 2169impl RecordFieldPatList {
2170 pub fn record_field_pats(&self) -> AstChildren<RecordFieldPat> {
2171 AstChildren::new(&self.syntax)
2172 }
2173 pub fn bind_pats(&self) -> AstChildren<BindPat> {
2174 AstChildren::new(&self.syntax)
2175 }
2176}
2637#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2177#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2638pub struct RangePat { 2178pub struct RecordFieldPat {
2639 pub(crate) syntax: SyntaxNode, 2179 pub(crate) syntax: SyntaxNode,
2640} 2180}
2641impl AstNode for RangePat { 2181impl AstNode for RecordFieldPat {
2642 fn can_cast(kind: SyntaxKind) -> bool { 2182 fn can_cast(kind: SyntaxKind) -> bool {
2643 match kind { 2183 match kind {
2644 RANGE_PAT => true, 2184 RECORD_FIELD_PAT => true,
2645 _ => false, 2185 _ => false,
2646 } 2186 }
2647 } 2187 }
@@ -2656,15 +2196,20 @@ impl AstNode for RangePat {
2656 &self.syntax 2196 &self.syntax
2657 } 2197 }
2658} 2198}
2659impl RangePat {} 2199impl ast::NameOwner for RecordFieldPat {}
2200impl RecordFieldPat {
2201 pub fn pat(&self) -> Option<Pat> {
2202 AstChildren::new(&self.syntax).next()
2203 }
2204}
2660#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2205#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2661pub struct RecordField { 2206pub struct TupleStructPat {
2662 pub(crate) syntax: SyntaxNode, 2207 pub(crate) syntax: SyntaxNode,
2663} 2208}
2664impl AstNode for RecordField { 2209impl AstNode for TupleStructPat {
2665 fn can_cast(kind: SyntaxKind) -> bool { 2210 fn can_cast(kind: SyntaxKind) -> bool {
2666 match kind { 2211 match kind {
2667 RECORD_FIELD => true, 2212 TUPLE_STRUCT_PAT => true,
2668 _ => false, 2213 _ => false,
2669 } 2214 }
2670 } 2215 }
@@ -2679,22 +2224,22 @@ impl AstNode for RecordField {
2679 &self.syntax 2224 &self.syntax
2680 } 2225 }
2681} 2226}
2682impl RecordField { 2227impl TupleStructPat {
2683 pub fn name_ref(&self) -> Option<NameRef> { 2228 pub fn path(&self) -> Option<Path> {
2684 AstChildren::new(&self.syntax).next() 2229 AstChildren::new(&self.syntax).next()
2685 } 2230 }
2686 pub fn expr(&self) -> Option<Expr> { 2231 pub fn args(&self) -> AstChildren<Pat> {
2687 AstChildren::new(&self.syntax).next() 2232 AstChildren::new(&self.syntax)
2688 } 2233 }
2689} 2234}
2690#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2235#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2691pub struct RecordFieldDef { 2236pub struct TuplePat {
2692 pub(crate) syntax: SyntaxNode, 2237 pub(crate) syntax: SyntaxNode,
2693} 2238}
2694impl AstNode for RecordFieldDef { 2239impl AstNode for TuplePat {
2695 fn can_cast(kind: SyntaxKind) -> bool { 2240 fn can_cast(kind: SyntaxKind) -> bool {
2696 match kind { 2241 match kind {
2697 RECORD_FIELD_DEF => true, 2242 TUPLE_PAT => true,
2698 _ => false, 2243 _ => false,
2699 } 2244 }
2700 } 2245 }
@@ -2709,20 +2254,19 @@ impl AstNode for RecordFieldDef {
2709 &self.syntax 2254 &self.syntax
2710 } 2255 }
2711} 2256}
2712impl ast::VisibilityOwner for RecordFieldDef {} 2257impl TuplePat {
2713impl ast::NameOwner for RecordFieldDef {} 2258 pub fn args(&self) -> AstChildren<Pat> {
2714impl ast::AttrsOwner for RecordFieldDef {} 2259 AstChildren::new(&self.syntax)
2715impl ast::DocCommentsOwner for RecordFieldDef {} 2260 }
2716impl ast::TypeAscriptionOwner for RecordFieldDef {} 2261}
2717impl RecordFieldDef {}
2718#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2262#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2719pub struct RecordFieldDefList { 2263pub struct Visibility {
2720 pub(crate) syntax: SyntaxNode, 2264 pub(crate) syntax: SyntaxNode,
2721} 2265}
2722impl AstNode for RecordFieldDefList { 2266impl AstNode for Visibility {
2723 fn can_cast(kind: SyntaxKind) -> bool { 2267 fn can_cast(kind: SyntaxKind) -> bool {
2724 match kind { 2268 match kind {
2725 RECORD_FIELD_DEF_LIST => true, 2269 VISIBILITY => true,
2726 _ => false, 2270 _ => false,
2727 } 2271 }
2728 } 2272 }
@@ -2737,19 +2281,15 @@ impl AstNode for RecordFieldDefList {
2737 &self.syntax 2281 &self.syntax
2738 } 2282 }
2739} 2283}
2740impl RecordFieldDefList { 2284impl Visibility {}
2741 pub fn fields(&self) -> AstChildren<RecordFieldDef> {
2742 AstChildren::new(&self.syntax)
2743 }
2744}
2745#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2285#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2746pub struct RecordFieldList { 2286pub struct Name {
2747 pub(crate) syntax: SyntaxNode, 2287 pub(crate) syntax: SyntaxNode,
2748} 2288}
2749impl AstNode for RecordFieldList { 2289impl AstNode for Name {
2750 fn can_cast(kind: SyntaxKind) -> bool { 2290 fn can_cast(kind: SyntaxKind) -> bool {
2751 match kind { 2291 match kind {
2752 RECORD_FIELD_LIST => true, 2292 NAME => true,
2753 _ => false, 2293 _ => false,
2754 } 2294 }
2755 } 2295 }
@@ -2764,22 +2304,15 @@ impl AstNode for RecordFieldList {
2764 &self.syntax 2304 &self.syntax
2765 } 2305 }
2766} 2306}
2767impl RecordFieldList { 2307impl Name {}
2768 pub fn fields(&self) -> AstChildren<RecordField> {
2769 AstChildren::new(&self.syntax)
2770 }
2771 pub fn spread(&self) -> Option<Expr> {
2772 AstChildren::new(&self.syntax).next()
2773 }
2774}
2775#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2308#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2776pub struct RecordFieldPat { 2309pub struct NameRef {
2777 pub(crate) syntax: SyntaxNode, 2310 pub(crate) syntax: SyntaxNode,
2778} 2311}
2779impl AstNode for RecordFieldPat { 2312impl AstNode for NameRef {
2780 fn can_cast(kind: SyntaxKind) -> bool { 2313 fn can_cast(kind: SyntaxKind) -> bool {
2781 match kind { 2314 match kind {
2782 RECORD_FIELD_PAT => true, 2315 NAME_REF => true,
2783 _ => false, 2316 _ => false,
2784 } 2317 }
2785 } 2318 }
@@ -2794,20 +2327,15 @@ impl AstNode for RecordFieldPat {
2794 &self.syntax 2327 &self.syntax
2795 } 2328 }
2796} 2329}
2797impl ast::NameOwner for RecordFieldPat {} 2330impl NameRef {}
2798impl RecordFieldPat {
2799 pub fn pat(&self) -> Option<Pat> {
2800 AstChildren::new(&self.syntax).next()
2801 }
2802}
2803#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2331#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2804pub struct RecordFieldPatList { 2332pub struct MacroCall {
2805 pub(crate) syntax: SyntaxNode, 2333 pub(crate) syntax: SyntaxNode,
2806} 2334}
2807impl AstNode for RecordFieldPatList { 2335impl AstNode for MacroCall {
2808 fn can_cast(kind: SyntaxKind) -> bool { 2336 fn can_cast(kind: SyntaxKind) -> bool {
2809 match kind { 2337 match kind {
2810 RECORD_FIELD_PAT_LIST => true, 2338 MACRO_CALL => true,
2811 _ => false, 2339 _ => false,
2812 } 2340 }
2813 } 2341 }
@@ -2822,22 +2350,25 @@ impl AstNode for RecordFieldPatList {
2822 &self.syntax 2350 &self.syntax
2823 } 2351 }
2824} 2352}
2825impl RecordFieldPatList { 2353impl ast::NameOwner for MacroCall {}
2826 pub fn record_field_pats(&self) -> AstChildren<RecordFieldPat> { 2354impl ast::AttrsOwner for MacroCall {}
2827 AstChildren::new(&self.syntax) 2355impl ast::DocCommentsOwner for MacroCall {}
2356impl MacroCall {
2357 pub fn token_tree(&self) -> Option<TokenTree> {
2358 AstChildren::new(&self.syntax).next()
2828 } 2359 }
2829 pub fn bind_pats(&self) -> AstChildren<BindPat> { 2360 pub fn path(&self) -> Option<Path> {
2830 AstChildren::new(&self.syntax) 2361 AstChildren::new(&self.syntax).next()
2831 } 2362 }
2832} 2363}
2833#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2364#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2834pub struct RecordLit { 2365pub struct Attr {
2835 pub(crate) syntax: SyntaxNode, 2366 pub(crate) syntax: SyntaxNode,
2836} 2367}
2837impl AstNode for RecordLit { 2368impl AstNode for Attr {
2838 fn can_cast(kind: SyntaxKind) -> bool { 2369 fn can_cast(kind: SyntaxKind) -> bool {
2839 match kind { 2370 match kind {
2840 RECORD_LIT => true, 2371 ATTR => true,
2841 _ => false, 2372 _ => false,
2842 } 2373 }
2843 } 2374 }
@@ -2852,22 +2383,22 @@ impl AstNode for RecordLit {
2852 &self.syntax 2383 &self.syntax
2853 } 2384 }
2854} 2385}
2855impl RecordLit { 2386impl Attr {
2856 pub fn path(&self) -> Option<Path> { 2387 pub fn path(&self) -> Option<Path> {
2857 AstChildren::new(&self.syntax).next() 2388 AstChildren::new(&self.syntax).next()
2858 } 2389 }
2859 pub fn record_field_list(&self) -> Option<RecordFieldList> { 2390 pub fn input(&self) -> Option<AttrInput> {
2860 AstChildren::new(&self.syntax).next() 2391 AstChildren::new(&self.syntax).next()
2861 } 2392 }
2862} 2393}
2863#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2394#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2864pub struct RecordPat { 2395pub struct TokenTree {
2865 pub(crate) syntax: SyntaxNode, 2396 pub(crate) syntax: SyntaxNode,
2866} 2397}
2867impl AstNode for RecordPat { 2398impl AstNode for TokenTree {
2868 fn can_cast(kind: SyntaxKind) -> bool { 2399 fn can_cast(kind: SyntaxKind) -> bool {
2869 match kind { 2400 match kind {
2870 RECORD_PAT => true, 2401 TOKEN_TREE => true,
2871 _ => false, 2402 _ => false,
2872 } 2403 }
2873 } 2404 }
@@ -2882,22 +2413,45 @@ impl AstNode for RecordPat {
2882 &self.syntax 2413 &self.syntax
2883 } 2414 }
2884} 2415}
2885impl RecordPat { 2416impl TokenTree {}
2886 pub fn record_field_pat_list(&self) -> Option<RecordFieldPatList> { 2417#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2887 AstChildren::new(&self.syntax).next() 2418pub struct TypeParamList {
2419 pub(crate) syntax: SyntaxNode,
2420}
2421impl AstNode for TypeParamList {
2422 fn can_cast(kind: SyntaxKind) -> bool {
2423 match kind {
2424 TYPE_PARAM_LIST => true,
2425 _ => false,
2426 }
2888 } 2427 }
2889 pub fn path(&self) -> Option<Path> { 2428 fn cast(syntax: SyntaxNode) -> Option<Self> {
2890 AstChildren::new(&self.syntax).next() 2429 if Self::can_cast(syntax.kind()) {
2430 Some(Self { syntax })
2431 } else {
2432 None
2433 }
2434 }
2435 fn syntax(&self) -> &SyntaxNode {
2436 &self.syntax
2437 }
2438}
2439impl TypeParamList {
2440 pub fn type_params(&self) -> AstChildren<TypeParam> {
2441 AstChildren::new(&self.syntax)
2442 }
2443 pub fn lifetime_params(&self) -> AstChildren<LifetimeParam> {
2444 AstChildren::new(&self.syntax)
2891 } 2445 }
2892} 2446}
2893#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2447#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2894pub struct RefExpr { 2448pub struct TypeParam {
2895 pub(crate) syntax: SyntaxNode, 2449 pub(crate) syntax: SyntaxNode,
2896} 2450}
2897impl AstNode for RefExpr { 2451impl AstNode for TypeParam {
2898 fn can_cast(kind: SyntaxKind) -> bool { 2452 fn can_cast(kind: SyntaxKind) -> bool {
2899 match kind { 2453 match kind {
2900 REF_EXPR => true, 2454 TYPE_PARAM => true,
2901 _ => false, 2455 _ => false,
2902 } 2456 }
2903 } 2457 }
@@ -2912,19 +2466,22 @@ impl AstNode for RefExpr {
2912 &self.syntax 2466 &self.syntax
2913 } 2467 }
2914} 2468}
2915impl RefExpr { 2469impl ast::NameOwner for TypeParam {}
2916 pub fn expr(&self) -> Option<Expr> { 2470impl ast::AttrsOwner for TypeParam {}
2471impl ast::TypeBoundsOwner for TypeParam {}
2472impl TypeParam {
2473 pub fn default_type(&self) -> Option<TypeRef> {
2917 AstChildren::new(&self.syntax).next() 2474 AstChildren::new(&self.syntax).next()
2918 } 2475 }
2919} 2476}
2920#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2477#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2921pub struct RefPat { 2478pub struct ConstParam {
2922 pub(crate) syntax: SyntaxNode, 2479 pub(crate) syntax: SyntaxNode,
2923} 2480}
2924impl AstNode for RefPat { 2481impl AstNode for ConstParam {
2925 fn can_cast(kind: SyntaxKind) -> bool { 2482 fn can_cast(kind: SyntaxKind) -> bool {
2926 match kind { 2483 match kind {
2927 REF_PAT => true, 2484 CONST_PARAM => true,
2928 _ => false, 2485 _ => false,
2929 } 2486 }
2930 } 2487 }
@@ -2939,19 +2496,22 @@ impl AstNode for RefPat {
2939 &self.syntax 2496 &self.syntax
2940 } 2497 }
2941} 2498}
2942impl RefPat { 2499impl ast::NameOwner for ConstParam {}
2943 pub fn pat(&self) -> Option<Pat> { 2500impl ast::AttrsOwner for ConstParam {}
2501impl ast::TypeAscriptionOwner for ConstParam {}
2502impl ConstParam {
2503 pub fn default_val(&self) -> Option<Expr> {
2944 AstChildren::new(&self.syntax).next() 2504 AstChildren::new(&self.syntax).next()
2945 } 2505 }
2946} 2506}
2947#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2507#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2948pub struct ReferenceType { 2508pub struct LifetimeParam {
2949 pub(crate) syntax: SyntaxNode, 2509 pub(crate) syntax: SyntaxNode,
2950} 2510}
2951impl AstNode for ReferenceType { 2511impl AstNode for LifetimeParam {
2952 fn can_cast(kind: SyntaxKind) -> bool { 2512 fn can_cast(kind: SyntaxKind) -> bool {
2953 match kind { 2513 match kind {
2954 REFERENCE_TYPE => true, 2514 LIFETIME_PARAM => true,
2955 _ => false, 2515 _ => false,
2956 } 2516 }
2957 } 2517 }
@@ -2966,19 +2526,16 @@ impl AstNode for ReferenceType {
2966 &self.syntax 2526 &self.syntax
2967 } 2527 }
2968} 2528}
2969impl ReferenceType { 2529impl ast::AttrsOwner for LifetimeParam {}
2970 pub fn type_ref(&self) -> Option<TypeRef> { 2530impl LifetimeParam {}
2971 AstChildren::new(&self.syntax).next()
2972 }
2973}
2974#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2531#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2975pub struct RetType { 2532pub struct TypeBound {
2976 pub(crate) syntax: SyntaxNode, 2533 pub(crate) syntax: SyntaxNode,
2977} 2534}
2978impl AstNode for RetType { 2535impl AstNode for TypeBound {
2979 fn can_cast(kind: SyntaxKind) -> bool { 2536 fn can_cast(kind: SyntaxKind) -> bool {
2980 match kind { 2537 match kind {
2981 RET_TYPE => true, 2538 TYPE_BOUND => true,
2982 _ => false, 2539 _ => false,
2983 } 2540 }
2984 } 2541 }
@@ -2993,19 +2550,19 @@ impl AstNode for RetType {
2993 &self.syntax 2550 &self.syntax
2994 } 2551 }
2995} 2552}
2996impl RetType { 2553impl TypeBound {
2997 pub fn type_ref(&self) -> Option<TypeRef> { 2554 pub fn type_ref(&self) -> Option<TypeRef> {
2998 AstChildren::new(&self.syntax).next() 2555 AstChildren::new(&self.syntax).next()
2999 } 2556 }
3000} 2557}
3001#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2558#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3002pub struct ReturnExpr { 2559pub struct TypeBoundList {
3003 pub(crate) syntax: SyntaxNode, 2560 pub(crate) syntax: SyntaxNode,
3004} 2561}
3005impl AstNode for ReturnExpr { 2562impl AstNode for TypeBoundList {
3006 fn can_cast(kind: SyntaxKind) -> bool { 2563 fn can_cast(kind: SyntaxKind) -> bool {
3007 match kind { 2564 match kind {
3008 RETURN_EXPR => true, 2565 TYPE_BOUND_LIST => true,
3009 _ => false, 2566 _ => false,
3010 } 2567 }
3011 } 2568 }
@@ -3020,19 +2577,19 @@ impl AstNode for ReturnExpr {
3020 &self.syntax 2577 &self.syntax
3021 } 2578 }
3022} 2579}
3023impl ReturnExpr { 2580impl TypeBoundList {
3024 pub fn expr(&self) -> Option<Expr> { 2581 pub fn bounds(&self) -> AstChildren<TypeBound> {
3025 AstChildren::new(&self.syntax).next() 2582 AstChildren::new(&self.syntax)
3026 } 2583 }
3027} 2584}
3028#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2585#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3029pub struct SelfParam { 2586pub struct WherePred {
3030 pub(crate) syntax: SyntaxNode, 2587 pub(crate) syntax: SyntaxNode,
3031} 2588}
3032impl AstNode for SelfParam { 2589impl AstNode for WherePred {
3033 fn can_cast(kind: SyntaxKind) -> bool { 2590 fn can_cast(kind: SyntaxKind) -> bool {
3034 match kind { 2591 match kind {
3035 SELF_PARAM => true, 2592 WHERE_PRED => true,
3036 _ => false, 2593 _ => false,
3037 } 2594 }
3038 } 2595 }
@@ -3047,17 +2604,20 @@ impl AstNode for SelfParam {
3047 &self.syntax 2604 &self.syntax
3048 } 2605 }
3049} 2606}
3050impl ast::TypeAscriptionOwner for SelfParam {} 2607impl ast::TypeBoundsOwner for WherePred {}
3051impl ast::AttrsOwner for SelfParam {} 2608impl WherePred {
3052impl SelfParam {} 2609 pub fn type_ref(&self) -> Option<TypeRef> {
2610 AstChildren::new(&self.syntax).next()
2611 }
2612}
3053#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2613#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3054pub struct SlicePat { 2614pub struct WhereClause {
3055 pub(crate) syntax: SyntaxNode, 2615 pub(crate) syntax: SyntaxNode,
3056} 2616}
3057impl AstNode for SlicePat { 2617impl AstNode for WhereClause {
3058 fn can_cast(kind: SyntaxKind) -> bool { 2618 fn can_cast(kind: SyntaxKind) -> bool {
3059 match kind { 2619 match kind {
3060 SLICE_PAT => true, 2620 WHERE_CLAUSE => true,
3061 _ => false, 2621 _ => false,
3062 } 2622 }
3063 } 2623 }
@@ -3072,15 +2632,19 @@ impl AstNode for SlicePat {
3072 &self.syntax 2632 &self.syntax
3073 } 2633 }
3074} 2634}
3075impl SlicePat {} 2635impl WhereClause {
2636 pub fn predicates(&self) -> AstChildren<WherePred> {
2637 AstChildren::new(&self.syntax)
2638 }
2639}
3076#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2640#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3077pub struct SliceType { 2641pub struct ExprStmt {
3078 pub(crate) syntax: SyntaxNode, 2642 pub(crate) syntax: SyntaxNode,
3079} 2643}
3080impl AstNode for SliceType { 2644impl AstNode for ExprStmt {
3081 fn can_cast(kind: SyntaxKind) -> bool { 2645 fn can_cast(kind: SyntaxKind) -> bool {
3082 match kind { 2646 match kind {
3083 SLICE_TYPE => true, 2647 EXPR_STMT => true,
3084 _ => false, 2648 _ => false,
3085 } 2649 }
3086 } 2650 }
@@ -3095,19 +2659,19 @@ impl AstNode for SliceType {
3095 &self.syntax 2659 &self.syntax
3096 } 2660 }
3097} 2661}
3098impl SliceType { 2662impl ExprStmt {
3099 pub fn type_ref(&self) -> Option<TypeRef> { 2663 pub fn expr(&self) -> Option<Expr> {
3100 AstChildren::new(&self.syntax).next() 2664 AstChildren::new(&self.syntax).next()
3101 } 2665 }
3102} 2666}
3103#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2667#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3104pub struct SourceFile { 2668pub struct LetStmt {
3105 pub(crate) syntax: SyntaxNode, 2669 pub(crate) syntax: SyntaxNode,
3106} 2670}
3107impl AstNode for SourceFile { 2671impl AstNode for LetStmt {
3108 fn can_cast(kind: SyntaxKind) -> bool { 2672 fn can_cast(kind: SyntaxKind) -> bool {
3109 match kind { 2673 match kind {
3110 SOURCE_FILE => true, 2674 LET_STMT => true,
3111 _ => false, 2675 _ => false,
3112 } 2676 }
3113 } 2677 }
@@ -3122,21 +2686,23 @@ impl AstNode for SourceFile {
3122 &self.syntax 2686 &self.syntax
3123 } 2687 }
3124} 2688}
3125impl ast::ModuleItemOwner for SourceFile {} 2689impl ast::TypeAscriptionOwner for LetStmt {}
3126impl ast::FnDefOwner for SourceFile {} 2690impl LetStmt {
3127impl SourceFile { 2691 pub fn pat(&self) -> Option<Pat> {
3128 pub fn modules(&self) -> AstChildren<Module> { 2692 AstChildren::new(&self.syntax).next()
3129 AstChildren::new(&self.syntax) 2693 }
2694 pub fn initializer(&self) -> Option<Expr> {
2695 AstChildren::new(&self.syntax).next()
3130 } 2696 }
3131} 2697}
3132#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2698#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3133pub struct StaticDef { 2699pub struct Condition {
3134 pub(crate) syntax: SyntaxNode, 2700 pub(crate) syntax: SyntaxNode,
3135} 2701}
3136impl AstNode for StaticDef { 2702impl AstNode for Condition {
3137 fn can_cast(kind: SyntaxKind) -> bool { 2703 fn can_cast(kind: SyntaxKind) -> bool {
3138 match kind { 2704 match kind {
3139 STATIC_DEF => true, 2705 CONDITION => true,
3140 _ => false, 2706 _ => false,
3141 } 2707 }
3142 } 2708 }
@@ -3151,63 +2717,54 @@ impl AstNode for StaticDef {
3151 &self.syntax 2717 &self.syntax
3152 } 2718 }
3153} 2719}
3154impl ast::VisibilityOwner for StaticDef {} 2720impl Condition {
3155impl ast::NameOwner for StaticDef {} 2721 pub fn pat(&self) -> Option<Pat> {
3156impl ast::TypeParamsOwner for StaticDef {}
3157impl ast::AttrsOwner for StaticDef {}
3158impl ast::DocCommentsOwner for StaticDef {}
3159impl ast::TypeAscriptionOwner for StaticDef {}
3160impl StaticDef {
3161 pub fn body(&self) -> Option<Expr> {
3162 AstChildren::new(&self.syntax).next() 2722 AstChildren::new(&self.syntax).next()
3163 } 2723 }
3164} 2724 pub fn expr(&self) -> Option<Expr> {
3165#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2725 AstChildren::new(&self.syntax).next()
3166pub enum Stmt {
3167 ExprStmt(ExprStmt),
3168 LetStmt(LetStmt),
3169}
3170impl From<ExprStmt> for Stmt {
3171 fn from(node: ExprStmt) -> Stmt {
3172 Stmt::ExprStmt(node)
3173 } 2726 }
3174} 2727}
3175impl From<LetStmt> for Stmt { 2728#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3176 fn from(node: LetStmt) -> Stmt { 2729pub struct Block {
3177 Stmt::LetStmt(node) 2730 pub(crate) syntax: SyntaxNode,
3178 }
3179} 2731}
3180impl AstNode for Stmt { 2732impl AstNode for Block {
3181 fn can_cast(kind: SyntaxKind) -> bool { 2733 fn can_cast(kind: SyntaxKind) -> bool {
3182 match kind { 2734 match kind {
3183 EXPR_STMT | LET_STMT => true, 2735 BLOCK => true,
3184 _ => false, 2736 _ => false,
3185 } 2737 }
3186 } 2738 }
3187 fn cast(syntax: SyntaxNode) -> Option<Self> { 2739 fn cast(syntax: SyntaxNode) -> Option<Self> {
3188 let res = match syntax.kind() { 2740 if Self::can_cast(syntax.kind()) {
3189 EXPR_STMT => Stmt::ExprStmt(ExprStmt { syntax }), 2741 Some(Self { syntax })
3190 LET_STMT => Stmt::LetStmt(LetStmt { syntax }), 2742 } else {
3191 _ => return None, 2743 None
3192 }; 2744 }
3193 Some(res)
3194 } 2745 }
3195 fn syntax(&self) -> &SyntaxNode { 2746 fn syntax(&self) -> &SyntaxNode {
3196 match self { 2747 &self.syntax
3197 Stmt::ExprStmt(it) => &it.syntax, 2748 }
3198 Stmt::LetStmt(it) => &it.syntax, 2749}
3199 } 2750impl ast::AttrsOwner for Block {}
2751impl ast::ModuleItemOwner for Block {}
2752impl Block {
2753 pub fn statements(&self) -> AstChildren<Stmt> {
2754 AstChildren::new(&self.syntax)
2755 }
2756 pub fn expr(&self) -> Option<Expr> {
2757 AstChildren::new(&self.syntax).next()
3200 } 2758 }
3201} 2759}
3202impl Stmt {}
3203#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2760#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3204pub struct StructDef { 2761pub struct ParamList {
3205 pub(crate) syntax: SyntaxNode, 2762 pub(crate) syntax: SyntaxNode,
3206} 2763}
3207impl AstNode for StructDef { 2764impl AstNode for ParamList {
3208 fn can_cast(kind: SyntaxKind) -> bool { 2765 fn can_cast(kind: SyntaxKind) -> bool {
3209 match kind { 2766 match kind {
3210 STRUCT_DEF => true, 2767 PARAM_LIST => true,
3211 _ => false, 2768 _ => false,
3212 } 2769 }
3213 } 2770 }
@@ -3222,20 +2779,22 @@ impl AstNode for StructDef {
3222 &self.syntax 2779 &self.syntax
3223 } 2780 }
3224} 2781}
3225impl ast::VisibilityOwner for StructDef {} 2782impl ParamList {
3226impl ast::NameOwner for StructDef {} 2783 pub fn self_param(&self) -> Option<SelfParam> {
3227impl ast::TypeParamsOwner for StructDef {} 2784 AstChildren::new(&self.syntax).next()
3228impl ast::AttrsOwner for StructDef {} 2785 }
3229impl ast::DocCommentsOwner for StructDef {} 2786 pub fn params(&self) -> AstChildren<Param> {
3230impl StructDef {} 2787 AstChildren::new(&self.syntax)
2788 }
2789}
3231#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2790#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3232pub struct TokenTree { 2791pub struct SelfParam {
3233 pub(crate) syntax: SyntaxNode, 2792 pub(crate) syntax: SyntaxNode,
3234} 2793}
3235impl AstNode for TokenTree { 2794impl AstNode for SelfParam {
3236 fn can_cast(kind: SyntaxKind) -> bool { 2795 fn can_cast(kind: SyntaxKind) -> bool {
3237 match kind { 2796 match kind {
3238 TOKEN_TREE => true, 2797 SELF_PARAM => true,
3239 _ => false, 2798 _ => false,
3240 } 2799 }
3241 } 2800 }
@@ -3250,15 +2809,17 @@ impl AstNode for TokenTree {
3250 &self.syntax 2809 &self.syntax
3251 } 2810 }
3252} 2811}
3253impl TokenTree {} 2812impl ast::TypeAscriptionOwner for SelfParam {}
2813impl ast::AttrsOwner for SelfParam {}
2814impl SelfParam {}
3254#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2815#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3255pub struct TraitDef { 2816pub struct Param {
3256 pub(crate) syntax: SyntaxNode, 2817 pub(crate) syntax: SyntaxNode,
3257} 2818}
3258impl AstNode for TraitDef { 2819impl AstNode for Param {
3259 fn can_cast(kind: SyntaxKind) -> bool { 2820 fn can_cast(kind: SyntaxKind) -> bool {
3260 match kind { 2821 match kind {
3261 TRAIT_DEF => true, 2822 PARAM => true,
3262 _ => false, 2823 _ => false,
3263 } 2824 }
3264 } 2825 }
@@ -3273,25 +2834,21 @@ impl AstNode for TraitDef {
3273 &self.syntax 2834 &self.syntax
3274 } 2835 }
3275} 2836}
3276impl ast::VisibilityOwner for TraitDef {} 2837impl ast::TypeAscriptionOwner for Param {}
3277impl ast::NameOwner for TraitDef {} 2838impl ast::AttrsOwner for Param {}
3278impl ast::AttrsOwner for TraitDef {} 2839impl Param {
3279impl ast::DocCommentsOwner for TraitDef {} 2840 pub fn pat(&self) -> Option<Pat> {
3280impl ast::TypeParamsOwner for TraitDef {}
3281impl ast::TypeBoundsOwner for TraitDef {}
3282impl TraitDef {
3283 pub fn item_list(&self) -> Option<ItemList> {
3284 AstChildren::new(&self.syntax).next() 2841 AstChildren::new(&self.syntax).next()
3285 } 2842 }
3286} 2843}
3287#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2844#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3288pub struct TryBlockExpr { 2845pub struct UseItem {
3289 pub(crate) syntax: SyntaxNode, 2846 pub(crate) syntax: SyntaxNode,
3290} 2847}
3291impl AstNode for TryBlockExpr { 2848impl AstNode for UseItem {
3292 fn can_cast(kind: SyntaxKind) -> bool { 2849 fn can_cast(kind: SyntaxKind) -> bool {
3293 match kind { 2850 match kind {
3294 TRY_BLOCK_EXPR => true, 2851 USE_ITEM => true,
3295 _ => false, 2852 _ => false,
3296 } 2853 }
3297 } 2854 }
@@ -3306,19 +2863,21 @@ impl AstNode for TryBlockExpr {
3306 &self.syntax 2863 &self.syntax
3307 } 2864 }
3308} 2865}
3309impl TryBlockExpr { 2866impl ast::AttrsOwner for UseItem {}
3310 pub fn body(&self) -> Option<BlockExpr> { 2867impl ast::VisibilityOwner for UseItem {}
2868impl UseItem {
2869 pub fn use_tree(&self) -> Option<UseTree> {
3311 AstChildren::new(&self.syntax).next() 2870 AstChildren::new(&self.syntax).next()
3312 } 2871 }
3313} 2872}
3314#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2873#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3315pub struct TryExpr { 2874pub struct UseTree {
3316 pub(crate) syntax: SyntaxNode, 2875 pub(crate) syntax: SyntaxNode,
3317} 2876}
3318impl AstNode for TryExpr { 2877impl AstNode for UseTree {
3319 fn can_cast(kind: SyntaxKind) -> bool { 2878 fn can_cast(kind: SyntaxKind) -> bool {
3320 match kind { 2879 match kind {
3321 TRY_EXPR => true, 2880 USE_TREE => true,
3322 _ => false, 2881 _ => false,
3323 } 2882 }
3324 } 2883 }
@@ -3333,19 +2892,25 @@ impl AstNode for TryExpr {
3333 &self.syntax 2892 &self.syntax
3334 } 2893 }
3335} 2894}
3336impl TryExpr { 2895impl UseTree {
3337 pub fn expr(&self) -> Option<Expr> { 2896 pub fn path(&self) -> Option<Path> {
2897 AstChildren::new(&self.syntax).next()
2898 }
2899 pub fn use_tree_list(&self) -> Option<UseTreeList> {
2900 AstChildren::new(&self.syntax).next()
2901 }
2902 pub fn alias(&self) -> Option<Alias> {
3338 AstChildren::new(&self.syntax).next() 2903 AstChildren::new(&self.syntax).next()
3339 } 2904 }
3340} 2905}
3341#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2906#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3342pub struct TupleExpr { 2907pub struct Alias {
3343 pub(crate) syntax: SyntaxNode, 2908 pub(crate) syntax: SyntaxNode,
3344} 2909}
3345impl AstNode for TupleExpr { 2910impl AstNode for Alias {
3346 fn can_cast(kind: SyntaxKind) -> bool { 2911 fn can_cast(kind: SyntaxKind) -> bool {
3347 match kind { 2912 match kind {
3348 TUPLE_EXPR => true, 2913 ALIAS => true,
3349 _ => false, 2914 _ => false,
3350 } 2915 }
3351 } 2916 }
@@ -3360,19 +2925,16 @@ impl AstNode for TupleExpr {
3360 &self.syntax 2925 &self.syntax
3361 } 2926 }
3362} 2927}
3363impl TupleExpr { 2928impl ast::NameOwner for Alias {}
3364 pub fn exprs(&self) -> AstChildren<Expr> { 2929impl Alias {}
3365 AstChildren::new(&self.syntax)
3366 }
3367}
3368#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2930#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3369pub struct TupleFieldDef { 2931pub struct UseTreeList {
3370 pub(crate) syntax: SyntaxNode, 2932 pub(crate) syntax: SyntaxNode,
3371} 2933}
3372impl AstNode for TupleFieldDef { 2934impl AstNode for UseTreeList {
3373 fn can_cast(kind: SyntaxKind) -> bool { 2935 fn can_cast(kind: SyntaxKind) -> bool {
3374 match kind { 2936 match kind {
3375 TUPLE_FIELD_DEF => true, 2937 USE_TREE_LIST => true,
3376 _ => false, 2938 _ => false,
3377 } 2939 }
3378 } 2940 }
@@ -3387,21 +2949,19 @@ impl AstNode for TupleFieldDef {
3387 &self.syntax 2949 &self.syntax
3388 } 2950 }
3389} 2951}
3390impl ast::VisibilityOwner for TupleFieldDef {} 2952impl UseTreeList {
3391impl ast::AttrsOwner for TupleFieldDef {} 2953 pub fn use_trees(&self) -> AstChildren<UseTree> {
3392impl TupleFieldDef { 2954 AstChildren::new(&self.syntax)
3393 pub fn type_ref(&self) -> Option<TypeRef> {
3394 AstChildren::new(&self.syntax).next()
3395 } 2955 }
3396} 2956}
3397#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2957#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3398pub struct TupleFieldDefList { 2958pub struct ExternCrateItem {
3399 pub(crate) syntax: SyntaxNode, 2959 pub(crate) syntax: SyntaxNode,
3400} 2960}
3401impl AstNode for TupleFieldDefList { 2961impl AstNode for ExternCrateItem {
3402 fn can_cast(kind: SyntaxKind) -> bool { 2962 fn can_cast(kind: SyntaxKind) -> bool {
3403 match kind { 2963 match kind {
3404 TUPLE_FIELD_DEF_LIST => true, 2964 EXTERN_CRATE_ITEM => true,
3405 _ => false, 2965 _ => false,
3406 } 2966 }
3407 } 2967 }
@@ -3416,19 +2976,24 @@ impl AstNode for TupleFieldDefList {
3416 &self.syntax 2976 &self.syntax
3417 } 2977 }
3418} 2978}
3419impl TupleFieldDefList { 2979impl ast::AttrsOwner for ExternCrateItem {}
3420 pub fn fields(&self) -> AstChildren<TupleFieldDef> { 2980impl ast::VisibilityOwner for ExternCrateItem {}
3421 AstChildren::new(&self.syntax) 2981impl ExternCrateItem {
2982 pub fn name_ref(&self) -> Option<NameRef> {
2983 AstChildren::new(&self.syntax).next()
2984 }
2985 pub fn alias(&self) -> Option<Alias> {
2986 AstChildren::new(&self.syntax).next()
3422 } 2987 }
3423} 2988}
3424#[derive(Debug, Clone, PartialEq, Eq, Hash)] 2989#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3425pub struct TuplePat { 2990pub struct ArgList {
3426 pub(crate) syntax: SyntaxNode, 2991 pub(crate) syntax: SyntaxNode,
3427} 2992}
3428impl AstNode for TuplePat { 2993impl AstNode for ArgList {
3429 fn can_cast(kind: SyntaxKind) -> bool { 2994 fn can_cast(kind: SyntaxKind) -> bool {
3430 match kind { 2995 match kind {
3431 TUPLE_PAT => true, 2996 ARG_LIST => true,
3432 _ => false, 2997 _ => false,
3433 } 2998 }
3434 } 2999 }
@@ -3443,19 +3008,19 @@ impl AstNode for TuplePat {
3443 &self.syntax 3008 &self.syntax
3444 } 3009 }
3445} 3010}
3446impl TuplePat { 3011impl ArgList {
3447 pub fn args(&self) -> AstChildren<Pat> { 3012 pub fn args(&self) -> AstChildren<Expr> {
3448 AstChildren::new(&self.syntax) 3013 AstChildren::new(&self.syntax)
3449 } 3014 }
3450} 3015}
3451#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3016#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3452pub struct TupleStructPat { 3017pub struct Path {
3453 pub(crate) syntax: SyntaxNode, 3018 pub(crate) syntax: SyntaxNode,
3454} 3019}
3455impl AstNode for TupleStructPat { 3020impl AstNode for Path {
3456 fn can_cast(kind: SyntaxKind) -> bool { 3021 fn can_cast(kind: SyntaxKind) -> bool {
3457 match kind { 3022 match kind {
3458 TUPLE_STRUCT_PAT => true, 3023 PATH => true,
3459 _ => false, 3024 _ => false,
3460 } 3025 }
3461 } 3026 }
@@ -3470,22 +3035,22 @@ impl AstNode for TupleStructPat {
3470 &self.syntax 3035 &self.syntax
3471 } 3036 }
3472} 3037}
3473impl TupleStructPat { 3038impl Path {
3474 pub fn args(&self) -> AstChildren<Pat> { 3039 pub fn segment(&self) -> Option<PathSegment> {
3475 AstChildren::new(&self.syntax) 3040 AstChildren::new(&self.syntax).next()
3476 } 3041 }
3477 pub fn path(&self) -> Option<Path> { 3042 pub fn qualifier(&self) -> Option<Path> {
3478 AstChildren::new(&self.syntax).next() 3043 AstChildren::new(&self.syntax).next()
3479 } 3044 }
3480} 3045}
3481#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3046#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3482pub struct TupleType { 3047pub struct PathSegment {
3483 pub(crate) syntax: SyntaxNode, 3048 pub(crate) syntax: SyntaxNode,
3484} 3049}
3485impl AstNode for TupleType { 3050impl AstNode for PathSegment {
3486 fn can_cast(kind: SyntaxKind) -> bool { 3051 fn can_cast(kind: SyntaxKind) -> bool {
3487 match kind { 3052 match kind {
3488 TUPLE_TYPE => true, 3053 PATH_SEGMENT => true,
3489 _ => false, 3054 _ => false,
3490 } 3055 }
3491 } 3056 }
@@ -3500,19 +3065,31 @@ impl AstNode for TupleType {
3500 &self.syntax 3065 &self.syntax
3501 } 3066 }
3502} 3067}
3503impl TupleType { 3068impl PathSegment {
3504 pub fn fields(&self) -> AstChildren<TypeRef> { 3069 pub fn name_ref(&self) -> Option<NameRef> {
3505 AstChildren::new(&self.syntax) 3070 AstChildren::new(&self.syntax).next()
3071 }
3072 pub fn type_arg_list(&self) -> Option<TypeArgList> {
3073 AstChildren::new(&self.syntax).next()
3074 }
3075 pub fn param_list(&self) -> Option<ParamList> {
3076 AstChildren::new(&self.syntax).next()
3077 }
3078 pub fn ret_type(&self) -> Option<RetType> {
3079 AstChildren::new(&self.syntax).next()
3080 }
3081 pub fn path_type(&self) -> Option<PathType> {
3082 AstChildren::new(&self.syntax).next()
3506 } 3083 }
3507} 3084}
3508#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3085#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3509pub struct TypeAliasDef { 3086pub struct TypeArgList {
3510 pub(crate) syntax: SyntaxNode, 3087 pub(crate) syntax: SyntaxNode,
3511} 3088}
3512impl AstNode for TypeAliasDef { 3089impl AstNode for TypeArgList {
3513 fn can_cast(kind: SyntaxKind) -> bool { 3090 fn can_cast(kind: SyntaxKind) -> bool {
3514 match kind { 3091 match kind {
3515 TYPE_ALIAS_DEF => true, 3092 TYPE_ARG_LIST => true,
3516 _ => false, 3093 _ => false,
3517 } 3094 }
3518 } 3095 }
@@ -3527,15 +3104,18 @@ impl AstNode for TypeAliasDef {
3527 &self.syntax 3104 &self.syntax
3528 } 3105 }
3529} 3106}
3530impl ast::VisibilityOwner for TypeAliasDef {} 3107impl TypeArgList {
3531impl ast::NameOwner for TypeAliasDef {} 3108 pub fn type_args(&self) -> AstChildren<TypeArg> {
3532impl ast::TypeParamsOwner for TypeAliasDef {} 3109 AstChildren::new(&self.syntax)
3533impl ast::AttrsOwner for TypeAliasDef {} 3110 }
3534impl ast::DocCommentsOwner for TypeAliasDef {} 3111 pub fn lifetime_args(&self) -> AstChildren<LifetimeArg> {
3535impl ast::TypeBoundsOwner for TypeAliasDef {} 3112 AstChildren::new(&self.syntax)
3536impl TypeAliasDef { 3113 }
3537 pub fn type_ref(&self) -> Option<TypeRef> { 3114 pub fn assoc_type_args(&self) -> AstChildren<AssocTypeArg> {
3538 AstChildren::new(&self.syntax).next() 3115 AstChildren::new(&self.syntax)
3116 }
3117 pub fn const_arg(&self) -> AstChildren<ConstArg> {
3118 AstChildren::new(&self.syntax)
3539 } 3119 }
3540} 3120}
3541#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3121#[derive(Debug, Clone, PartialEq, Eq, Hash)]
@@ -3566,13 +3146,13 @@ impl TypeArg {
3566 } 3146 }
3567} 3147}
3568#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3148#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3569pub struct TypeArgList { 3149pub struct AssocTypeArg {
3570 pub(crate) syntax: SyntaxNode, 3150 pub(crate) syntax: SyntaxNode,
3571} 3151}
3572impl AstNode for TypeArgList { 3152impl AstNode for AssocTypeArg {
3573 fn can_cast(kind: SyntaxKind) -> bool { 3153 fn can_cast(kind: SyntaxKind) -> bool {
3574 match kind { 3154 match kind {
3575 TYPE_ARG_LIST => true, 3155 ASSOC_TYPE_ARG => true,
3576 _ => false, 3156 _ => false,
3577 } 3157 }
3578 } 3158 }
@@ -3587,25 +3167,22 @@ impl AstNode for TypeArgList {
3587 &self.syntax 3167 &self.syntax
3588 } 3168 }
3589} 3169}
3590impl TypeArgList { 3170impl AssocTypeArg {
3591 pub fn type_args(&self) -> AstChildren<TypeArg> { 3171 pub fn name_ref(&self) -> Option<NameRef> {
3592 AstChildren::new(&self.syntax) 3172 AstChildren::new(&self.syntax).next()
3593 }
3594 pub fn lifetime_args(&self) -> AstChildren<LifetimeArg> {
3595 AstChildren::new(&self.syntax)
3596 } 3173 }
3597 pub fn assoc_type_args(&self) -> AstChildren<AssocTypeArg> { 3174 pub fn type_ref(&self) -> Option<TypeRef> {
3598 AstChildren::new(&self.syntax) 3175 AstChildren::new(&self.syntax).next()
3599 } 3176 }
3600} 3177}
3601#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3178#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3602pub struct TypeBound { 3179pub struct LifetimeArg {
3603 pub(crate) syntax: SyntaxNode, 3180 pub(crate) syntax: SyntaxNode,
3604} 3181}
3605impl AstNode for TypeBound { 3182impl AstNode for LifetimeArg {
3606 fn can_cast(kind: SyntaxKind) -> bool { 3183 fn can_cast(kind: SyntaxKind) -> bool {
3607 match kind { 3184 match kind {
3608 TYPE_BOUND => true, 3185 LIFETIME_ARG => true,
3609 _ => false, 3186 _ => false,
3610 } 3187 }
3611 } 3188 }
@@ -3620,19 +3197,15 @@ impl AstNode for TypeBound {
3620 &self.syntax 3197 &self.syntax
3621 } 3198 }
3622} 3199}
3623impl TypeBound { 3200impl LifetimeArg {}
3624 pub fn type_ref(&self) -> Option<TypeRef> {
3625 AstChildren::new(&self.syntax).next()
3626 }
3627}
3628#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3201#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3629pub struct TypeBoundList { 3202pub struct ConstArg {
3630 pub(crate) syntax: SyntaxNode, 3203 pub(crate) syntax: SyntaxNode,
3631} 3204}
3632impl AstNode for TypeBoundList { 3205impl AstNode for ConstArg {
3633 fn can_cast(kind: SyntaxKind) -> bool { 3206 fn can_cast(kind: SyntaxKind) -> bool {
3634 match kind { 3207 match kind {
3635 TYPE_BOUND_LIST => true, 3208 CONST_ARG => true,
3636 _ => false, 3209 _ => false,
3637 } 3210 }
3638 } 3211 }
@@ -3647,19 +3220,22 @@ impl AstNode for TypeBoundList {
3647 &self.syntax 3220 &self.syntax
3648 } 3221 }
3649} 3222}
3650impl TypeBoundList { 3223impl ConstArg {
3651 pub fn bounds(&self) -> AstChildren<TypeBound> { 3224 pub fn literal(&self) -> Option<Literal> {
3652 AstChildren::new(&self.syntax) 3225 AstChildren::new(&self.syntax).next()
3226 }
3227 pub fn block_expr(&self) -> Option<BlockExpr> {
3228 AstChildren::new(&self.syntax).next()
3653 } 3229 }
3654} 3230}
3655#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3231#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3656pub struct TypeParam { 3232pub struct MacroItems {
3657 pub(crate) syntax: SyntaxNode, 3233 pub(crate) syntax: SyntaxNode,
3658} 3234}
3659impl AstNode for TypeParam { 3235impl AstNode for MacroItems {
3660 fn can_cast(kind: SyntaxKind) -> bool { 3236 fn can_cast(kind: SyntaxKind) -> bool {
3661 match kind { 3237 match kind {
3662 TYPE_PARAM => true, 3238 MACRO_ITEMS => true,
3663 _ => false, 3239 _ => false,
3664 } 3240 }
3665 } 3241 }
@@ -3674,22 +3250,17 @@ impl AstNode for TypeParam {
3674 &self.syntax 3250 &self.syntax
3675 } 3251 }
3676} 3252}
3677impl ast::NameOwner for TypeParam {} 3253impl ast::ModuleItemOwner for MacroItems {}
3678impl ast::AttrsOwner for TypeParam {} 3254impl ast::FnDefOwner for MacroItems {}
3679impl ast::TypeBoundsOwner for TypeParam {} 3255impl MacroItems {}
3680impl TypeParam {
3681 pub fn default_type(&self) -> Option<TypeRef> {
3682 AstChildren::new(&self.syntax).next()
3683 }
3684}
3685#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3256#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3686pub struct TypeParamList { 3257pub struct MacroStmts {
3687 pub(crate) syntax: SyntaxNode, 3258 pub(crate) syntax: SyntaxNode,
3688} 3259}
3689impl AstNode for TypeParamList { 3260impl AstNode for MacroStmts {
3690 fn can_cast(kind: SyntaxKind) -> bool { 3261 fn can_cast(kind: SyntaxKind) -> bool {
3691 match kind { 3262 match kind {
3692 TYPE_PARAM_LIST => true, 3263 MACRO_STMTS => true,
3693 _ => false, 3264 _ => false,
3694 } 3265 }
3695 } 3266 }
@@ -3704,15 +3275,63 @@ impl AstNode for TypeParamList {
3704 &self.syntax 3275 &self.syntax
3705 } 3276 }
3706} 3277}
3707impl TypeParamList { 3278impl MacroStmts {
3708 pub fn type_params(&self) -> AstChildren<TypeParam> { 3279 pub fn statements(&self) -> AstChildren<Stmt> {
3709 AstChildren::new(&self.syntax) 3280 AstChildren::new(&self.syntax)
3710 } 3281 }
3711 pub fn lifetime_params(&self) -> AstChildren<LifetimeParam> { 3282 pub fn expr(&self) -> Option<Expr> {
3712 AstChildren::new(&self.syntax) 3283 AstChildren::new(&self.syntax).next()
3713 } 3284 }
3714} 3285}
3715#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3286#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3287pub enum NominalDef {
3288 StructDef(StructDef),
3289 EnumDef(EnumDef),
3290 UnionDef(UnionDef),
3291}
3292impl From<StructDef> for NominalDef {
3293 fn from(node: StructDef) -> NominalDef {
3294 NominalDef::StructDef(node)
3295 }
3296}
3297impl From<EnumDef> for NominalDef {
3298 fn from(node: EnumDef) -> NominalDef {
3299 NominalDef::EnumDef(node)
3300 }
3301}
3302impl From<UnionDef> for NominalDef {
3303 fn from(node: UnionDef) -> NominalDef {
3304 NominalDef::UnionDef(node)
3305 }
3306}
3307impl AstNode for NominalDef {
3308 fn can_cast(kind: SyntaxKind) -> bool {
3309 match kind {
3310 STRUCT_DEF | ENUM_DEF | UNION_DEF => true,
3311 _ => false,
3312 }
3313 }
3314 fn cast(syntax: SyntaxNode) -> Option<Self> {
3315 let res = match syntax.kind() {
3316 STRUCT_DEF => NominalDef::StructDef(StructDef { syntax }),
3317 ENUM_DEF => NominalDef::EnumDef(EnumDef { syntax }),
3318 UNION_DEF => NominalDef::UnionDef(UnionDef { syntax }),
3319 _ => return None,
3320 };
3321 Some(res)
3322 }
3323 fn syntax(&self) -> &SyntaxNode {
3324 match self {
3325 NominalDef::StructDef(it) => &it.syntax,
3326 NominalDef::EnumDef(it) => &it.syntax,
3327 NominalDef::UnionDef(it) => &it.syntax,
3328 }
3329 }
3330}
3331impl ast::NameOwner for NominalDef {}
3332impl ast::TypeParamsOwner for NominalDef {}
3333impl ast::AttrsOwner for NominalDef {}
3334#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3716pub enum TypeRef { 3335pub enum TypeRef {
3717 ParenType(ParenType), 3336 ParenType(ParenType),
3718 TupleType(TupleType), 3337 TupleType(TupleType),
@@ -3839,231 +3458,637 @@ impl AstNode for TypeRef {
3839 } 3458 }
3840 } 3459 }
3841} 3460}
3842impl TypeRef {}
3843#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3461#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3844pub struct UnionDef { 3462pub enum ModuleItem {
3845 pub(crate) syntax: SyntaxNode, 3463 StructDef(StructDef),
3464 UnionDef(UnionDef),
3465 EnumDef(EnumDef),
3466 FnDef(FnDef),
3467 TraitDef(TraitDef),
3468 TypeAliasDef(TypeAliasDef),
3469 ImplBlock(ImplBlock),
3470 UseItem(UseItem),
3471 ExternCrateItem(ExternCrateItem),
3472 ConstDef(ConstDef),
3473 StaticDef(StaticDef),
3474 Module(Module),
3846} 3475}
3847impl AstNode for UnionDef { 3476impl From<StructDef> for ModuleItem {
3848 fn can_cast(kind: SyntaxKind) -> bool { 3477 fn from(node: StructDef) -> ModuleItem {
3849 match kind { 3478 ModuleItem::StructDef(node)
3850 UNION_DEF => true,
3851 _ => false,
3852 }
3853 } 3479 }
3854 fn cast(syntax: SyntaxNode) -> Option<Self> { 3480}
3855 if Self::can_cast(syntax.kind()) { 3481impl From<UnionDef> for ModuleItem {
3856 Some(Self { syntax }) 3482 fn from(node: UnionDef) -> ModuleItem {
3857 } else { 3483 ModuleItem::UnionDef(node)
3858 None
3859 }
3860 } 3484 }
3861 fn syntax(&self) -> &SyntaxNode { 3485}
3862 &self.syntax 3486impl From<EnumDef> for ModuleItem {
3487 fn from(node: EnumDef) -> ModuleItem {
3488 ModuleItem::EnumDef(node)
3863 } 3489 }
3864} 3490}
3865impl ast::VisibilityOwner for UnionDef {} 3491impl From<FnDef> for ModuleItem {
3866impl ast::NameOwner for UnionDef {} 3492 fn from(node: FnDef) -> ModuleItem {
3867impl ast::TypeParamsOwner for UnionDef {} 3493 ModuleItem::FnDef(node)
3868impl ast::AttrsOwner for UnionDef {}
3869impl ast::DocCommentsOwner for UnionDef {}
3870impl UnionDef {
3871 pub fn record_field_def_list(&self) -> Option<RecordFieldDefList> {
3872 AstChildren::new(&self.syntax).next()
3873 } 3494 }
3874} 3495}
3875#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3496impl From<TraitDef> for ModuleItem {
3876pub struct UseItem { 3497 fn from(node: TraitDef) -> ModuleItem {
3877 pub(crate) syntax: SyntaxNode, 3498 ModuleItem::TraitDef(node)
3499 }
3878} 3500}
3879impl AstNode for UseItem { 3501impl From<TypeAliasDef> for ModuleItem {
3502 fn from(node: TypeAliasDef) -> ModuleItem {
3503 ModuleItem::TypeAliasDef(node)
3504 }
3505}
3506impl From<ImplBlock> for ModuleItem {
3507 fn from(node: ImplBlock) -> ModuleItem {
3508 ModuleItem::ImplBlock(node)
3509 }
3510}
3511impl From<UseItem> for ModuleItem {
3512 fn from(node: UseItem) -> ModuleItem {
3513 ModuleItem::UseItem(node)
3514 }
3515}
3516impl From<ExternCrateItem> for ModuleItem {
3517 fn from(node: ExternCrateItem) -> ModuleItem {
3518 ModuleItem::ExternCrateItem(node)
3519 }
3520}
3521impl From<ConstDef> for ModuleItem {
3522 fn from(node: ConstDef) -> ModuleItem {
3523 ModuleItem::ConstDef(node)
3524 }
3525}
3526impl From<StaticDef> for ModuleItem {
3527 fn from(node: StaticDef) -> ModuleItem {
3528 ModuleItem::StaticDef(node)
3529 }
3530}
3531impl From<Module> for ModuleItem {
3532 fn from(node: Module) -> ModuleItem {
3533 ModuleItem::Module(node)
3534 }
3535}
3536impl AstNode for ModuleItem {
3880 fn can_cast(kind: SyntaxKind) -> bool { 3537 fn can_cast(kind: SyntaxKind) -> bool {
3881 match kind { 3538 match kind {
3882 USE_ITEM => true, 3539 STRUCT_DEF | UNION_DEF | ENUM_DEF | FN_DEF | TRAIT_DEF | TYPE_ALIAS_DEF
3540 | IMPL_BLOCK | USE_ITEM | EXTERN_CRATE_ITEM | CONST_DEF | STATIC_DEF | MODULE => true,
3883 _ => false, 3541 _ => false,
3884 } 3542 }
3885 } 3543 }
3886 fn cast(syntax: SyntaxNode) -> Option<Self> { 3544 fn cast(syntax: SyntaxNode) -> Option<Self> {
3887 if Self::can_cast(syntax.kind()) { 3545 let res = match syntax.kind() {
3888 Some(Self { syntax }) 3546 STRUCT_DEF => ModuleItem::StructDef(StructDef { syntax }),
3889 } else { 3547 UNION_DEF => ModuleItem::UnionDef(UnionDef { syntax }),
3890 None 3548 ENUM_DEF => ModuleItem::EnumDef(EnumDef { syntax }),
3891 } 3549 FN_DEF => ModuleItem::FnDef(FnDef { syntax }),
3550 TRAIT_DEF => ModuleItem::TraitDef(TraitDef { syntax }),
3551 TYPE_ALIAS_DEF => ModuleItem::TypeAliasDef(TypeAliasDef { syntax }),
3552 IMPL_BLOCK => ModuleItem::ImplBlock(ImplBlock { syntax }),
3553 USE_ITEM => ModuleItem::UseItem(UseItem { syntax }),
3554 EXTERN_CRATE_ITEM => ModuleItem::ExternCrateItem(ExternCrateItem { syntax }),
3555 CONST_DEF => ModuleItem::ConstDef(ConstDef { syntax }),
3556 STATIC_DEF => ModuleItem::StaticDef(StaticDef { syntax }),
3557 MODULE => ModuleItem::Module(Module { syntax }),
3558 _ => return None,
3559 };
3560 Some(res)
3892 } 3561 }
3893 fn syntax(&self) -> &SyntaxNode { 3562 fn syntax(&self) -> &SyntaxNode {
3894 &self.syntax 3563 match self {
3564 ModuleItem::StructDef(it) => &it.syntax,
3565 ModuleItem::UnionDef(it) => &it.syntax,
3566 ModuleItem::EnumDef(it) => &it.syntax,
3567 ModuleItem::FnDef(it) => &it.syntax,
3568 ModuleItem::TraitDef(it) => &it.syntax,
3569 ModuleItem::TypeAliasDef(it) => &it.syntax,
3570 ModuleItem::ImplBlock(it) => &it.syntax,
3571 ModuleItem::UseItem(it) => &it.syntax,
3572 ModuleItem::ExternCrateItem(it) => &it.syntax,
3573 ModuleItem::ConstDef(it) => &it.syntax,
3574 ModuleItem::StaticDef(it) => &it.syntax,
3575 ModuleItem::Module(it) => &it.syntax,
3576 }
3895 } 3577 }
3896} 3578}
3897impl ast::AttrsOwner for UseItem {} 3579impl ast::AttrsOwner for ModuleItem {}
3898impl ast::VisibilityOwner for UseItem {} 3580impl ast::VisibilityOwner for ModuleItem {}
3899impl UseItem { 3581#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3900 pub fn use_tree(&self) -> Option<UseTree> { 3582pub enum ImplItem {
3901 AstChildren::new(&self.syntax).next() 3583 FnDef(FnDef),
3584 TypeAliasDef(TypeAliasDef),
3585 ConstDef(ConstDef),
3586}
3587impl From<FnDef> for ImplItem {
3588 fn from(node: FnDef) -> ImplItem {
3589 ImplItem::FnDef(node)
3902 } 3590 }
3903} 3591}
3904#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3592impl From<TypeAliasDef> for ImplItem {
3905pub struct UseTree { 3593 fn from(node: TypeAliasDef) -> ImplItem {
3906 pub(crate) syntax: SyntaxNode, 3594 ImplItem::TypeAliasDef(node)
3595 }
3907} 3596}
3908impl AstNode for UseTree { 3597impl From<ConstDef> for ImplItem {
3598 fn from(node: ConstDef) -> ImplItem {
3599 ImplItem::ConstDef(node)
3600 }
3601}
3602impl AstNode for ImplItem {
3909 fn can_cast(kind: SyntaxKind) -> bool { 3603 fn can_cast(kind: SyntaxKind) -> bool {
3910 match kind { 3604 match kind {
3911 USE_TREE => true, 3605 FN_DEF | TYPE_ALIAS_DEF | CONST_DEF => true,
3912 _ => false, 3606 _ => false,
3913 } 3607 }
3914 } 3608 }
3915 fn cast(syntax: SyntaxNode) -> Option<Self> { 3609 fn cast(syntax: SyntaxNode) -> Option<Self> {
3916 if Self::can_cast(syntax.kind()) { 3610 let res = match syntax.kind() {
3917 Some(Self { syntax }) 3611 FN_DEF => ImplItem::FnDef(FnDef { syntax }),
3918 } else { 3612 TYPE_ALIAS_DEF => ImplItem::TypeAliasDef(TypeAliasDef { syntax }),
3919 None 3613 CONST_DEF => ImplItem::ConstDef(ConstDef { syntax }),
3920 } 3614 _ => return None,
3615 };
3616 Some(res)
3921 } 3617 }
3922 fn syntax(&self) -> &SyntaxNode { 3618 fn syntax(&self) -> &SyntaxNode {
3923 &self.syntax 3619 match self {
3620 ImplItem::FnDef(it) => &it.syntax,
3621 ImplItem::TypeAliasDef(it) => &it.syntax,
3622 ImplItem::ConstDef(it) => &it.syntax,
3623 }
3924 } 3624 }
3925} 3625}
3926impl UseTree { 3626impl ast::AttrsOwner for ImplItem {}
3927 pub fn path(&self) -> Option<Path> { 3627#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3928 AstChildren::new(&self.syntax).next() 3628pub enum Expr {
3629 TupleExpr(TupleExpr),
3630 ArrayExpr(ArrayExpr),
3631 ParenExpr(ParenExpr),
3632 PathExpr(PathExpr),
3633 LambdaExpr(LambdaExpr),
3634 IfExpr(IfExpr),
3635 LoopExpr(LoopExpr),
3636 ForExpr(ForExpr),
3637 WhileExpr(WhileExpr),
3638 ContinueExpr(ContinueExpr),
3639 BreakExpr(BreakExpr),
3640 Label(Label),
3641 BlockExpr(BlockExpr),
3642 ReturnExpr(ReturnExpr),
3643 MatchExpr(MatchExpr),
3644 RecordLit(RecordLit),
3645 CallExpr(CallExpr),
3646 IndexExpr(IndexExpr),
3647 MethodCallExpr(MethodCallExpr),
3648 FieldExpr(FieldExpr),
3649 AwaitExpr(AwaitExpr),
3650 TryExpr(TryExpr),
3651 TryBlockExpr(TryBlockExpr),
3652 CastExpr(CastExpr),
3653 RefExpr(RefExpr),
3654 PrefixExpr(PrefixExpr),
3655 RangeExpr(RangeExpr),
3656 BinExpr(BinExpr),
3657 Literal(Literal),
3658 MacroCall(MacroCall),
3659 BoxExpr(BoxExpr),
3660}
3661impl From<TupleExpr> for Expr {
3662 fn from(node: TupleExpr) -> Expr {
3663 Expr::TupleExpr(node)
3929 } 3664 }
3930 pub fn use_tree_list(&self) -> Option<UseTreeList> { 3665}
3931 AstChildren::new(&self.syntax).next() 3666impl From<ArrayExpr> for Expr {
3667 fn from(node: ArrayExpr) -> Expr {
3668 Expr::ArrayExpr(node)
3932 } 3669 }
3933 pub fn alias(&self) -> Option<Alias> { 3670}
3934 AstChildren::new(&self.syntax).next() 3671impl From<ParenExpr> for Expr {
3672 fn from(node: ParenExpr) -> Expr {
3673 Expr::ParenExpr(node)
3935 } 3674 }
3936} 3675}
3937#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3676impl From<PathExpr> for Expr {
3938pub struct UseTreeList { 3677 fn from(node: PathExpr) -> Expr {
3939 pub(crate) syntax: SyntaxNode, 3678 Expr::PathExpr(node)
3679 }
3940} 3680}
3941impl AstNode for UseTreeList { 3681impl From<LambdaExpr> for Expr {
3942 fn can_cast(kind: SyntaxKind) -> bool { 3682 fn from(node: LambdaExpr) -> Expr {
3943 match kind { 3683 Expr::LambdaExpr(node)
3944 USE_TREE_LIST => true,
3945 _ => false,
3946 }
3947 } 3684 }
3948 fn cast(syntax: SyntaxNode) -> Option<Self> { 3685}
3949 if Self::can_cast(syntax.kind()) { 3686impl From<IfExpr> for Expr {
3950 Some(Self { syntax }) 3687 fn from(node: IfExpr) -> Expr {
3951 } else { 3688 Expr::IfExpr(node)
3952 None
3953 }
3954 } 3689 }
3955 fn syntax(&self) -> &SyntaxNode { 3690}
3956 &self.syntax 3691impl From<LoopExpr> for Expr {
3692 fn from(node: LoopExpr) -> Expr {
3693 Expr::LoopExpr(node)
3957 } 3694 }
3958} 3695}
3959impl UseTreeList { 3696impl From<ForExpr> for Expr {
3960 pub fn use_trees(&self) -> AstChildren<UseTree> { 3697 fn from(node: ForExpr) -> Expr {
3961 AstChildren::new(&self.syntax) 3698 Expr::ForExpr(node)
3962 } 3699 }
3963} 3700}
3964#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3701impl From<WhileExpr> for Expr {
3965pub struct Visibility { 3702 fn from(node: WhileExpr) -> Expr {
3966 pub(crate) syntax: SyntaxNode, 3703 Expr::WhileExpr(node)
3704 }
3967} 3705}
3968impl AstNode for Visibility { 3706impl From<ContinueExpr> for Expr {
3707 fn from(node: ContinueExpr) -> Expr {
3708 Expr::ContinueExpr(node)
3709 }
3710}
3711impl From<BreakExpr> for Expr {
3712 fn from(node: BreakExpr) -> Expr {
3713 Expr::BreakExpr(node)
3714 }
3715}
3716impl From<Label> for Expr {
3717 fn from(node: Label) -> Expr {
3718 Expr::Label(node)
3719 }
3720}
3721impl From<BlockExpr> for Expr {
3722 fn from(node: BlockExpr) -> Expr {
3723 Expr::BlockExpr(node)
3724 }
3725}
3726impl From<ReturnExpr> for Expr {
3727 fn from(node: ReturnExpr) -> Expr {
3728 Expr::ReturnExpr(node)
3729 }
3730}
3731impl From<MatchExpr> for Expr {
3732 fn from(node: MatchExpr) -> Expr {
3733 Expr::MatchExpr(node)
3734 }
3735}
3736impl From<RecordLit> for Expr {
3737 fn from(node: RecordLit) -> Expr {
3738 Expr::RecordLit(node)
3739 }
3740}
3741impl From<CallExpr> for Expr {
3742 fn from(node: CallExpr) -> Expr {
3743 Expr::CallExpr(node)
3744 }
3745}
3746impl From<IndexExpr> for Expr {
3747 fn from(node: IndexExpr) -> Expr {
3748 Expr::IndexExpr(node)
3749 }
3750}
3751impl From<MethodCallExpr> for Expr {
3752 fn from(node: MethodCallExpr) -> Expr {
3753 Expr::MethodCallExpr(node)
3754 }
3755}
3756impl From<FieldExpr> for Expr {
3757 fn from(node: FieldExpr) -> Expr {
3758 Expr::FieldExpr(node)
3759 }
3760}
3761impl From<AwaitExpr> for Expr {
3762 fn from(node: AwaitExpr) -> Expr {
3763 Expr::AwaitExpr(node)
3764 }
3765}
3766impl From<TryExpr> for Expr {
3767 fn from(node: TryExpr) -> Expr {
3768 Expr::TryExpr(node)
3769 }
3770}
3771impl From<TryBlockExpr> for Expr {
3772 fn from(node: TryBlockExpr) -> Expr {
3773 Expr::TryBlockExpr(node)
3774 }
3775}
3776impl From<CastExpr> for Expr {
3777 fn from(node: CastExpr) -> Expr {
3778 Expr::CastExpr(node)
3779 }
3780}
3781impl From<RefExpr> for Expr {
3782 fn from(node: RefExpr) -> Expr {
3783 Expr::RefExpr(node)
3784 }
3785}
3786impl From<PrefixExpr> for Expr {
3787 fn from(node: PrefixExpr) -> Expr {
3788 Expr::PrefixExpr(node)
3789 }
3790}
3791impl From<RangeExpr> for Expr {
3792 fn from(node: RangeExpr) -> Expr {
3793 Expr::RangeExpr(node)
3794 }
3795}
3796impl From<BinExpr> for Expr {
3797 fn from(node: BinExpr) -> Expr {
3798 Expr::BinExpr(node)
3799 }
3800}
3801impl From<Literal> for Expr {
3802 fn from(node: Literal) -> Expr {
3803 Expr::Literal(node)
3804 }
3805}
3806impl From<MacroCall> for Expr {
3807 fn from(node: MacroCall) -> Expr {
3808 Expr::MacroCall(node)
3809 }
3810}
3811impl From<BoxExpr> for Expr {
3812 fn from(node: BoxExpr) -> Expr {
3813 Expr::BoxExpr(node)
3814 }
3815}
3816impl AstNode for Expr {
3969 fn can_cast(kind: SyntaxKind) -> bool { 3817 fn can_cast(kind: SyntaxKind) -> bool {
3970 match kind { 3818 match kind {
3971 VISIBILITY => true, 3819 TUPLE_EXPR | ARRAY_EXPR | PAREN_EXPR | PATH_EXPR | LAMBDA_EXPR | IF_EXPR
3820 | LOOP_EXPR | FOR_EXPR | WHILE_EXPR | CONTINUE_EXPR | BREAK_EXPR | LABEL
3821 | BLOCK_EXPR | RETURN_EXPR | MATCH_EXPR | RECORD_LIT | CALL_EXPR | INDEX_EXPR
3822 | METHOD_CALL_EXPR | FIELD_EXPR | AWAIT_EXPR | TRY_EXPR | TRY_BLOCK_EXPR
3823 | CAST_EXPR | REF_EXPR | PREFIX_EXPR | RANGE_EXPR | BIN_EXPR | LITERAL | MACRO_CALL
3824 | BOX_EXPR => true,
3972 _ => false, 3825 _ => false,
3973 } 3826 }
3974 } 3827 }
3975 fn cast(syntax: SyntaxNode) -> Option<Self> { 3828 fn cast(syntax: SyntaxNode) -> Option<Self> {
3976 if Self::can_cast(syntax.kind()) { 3829 let res = match syntax.kind() {
3977 Some(Self { syntax }) 3830 TUPLE_EXPR => Expr::TupleExpr(TupleExpr { syntax }),
3978 } else { 3831 ARRAY_EXPR => Expr::ArrayExpr(ArrayExpr { syntax }),
3979 None 3832 PAREN_EXPR => Expr::ParenExpr(ParenExpr { syntax }),
3980 } 3833 PATH_EXPR => Expr::PathExpr(PathExpr { syntax }),
3834 LAMBDA_EXPR => Expr::LambdaExpr(LambdaExpr { syntax }),
3835 IF_EXPR => Expr::IfExpr(IfExpr { syntax }),
3836 LOOP_EXPR => Expr::LoopExpr(LoopExpr { syntax }),
3837 FOR_EXPR => Expr::ForExpr(ForExpr { syntax }),
3838 WHILE_EXPR => Expr::WhileExpr(WhileExpr { syntax }),
3839 CONTINUE_EXPR => Expr::ContinueExpr(ContinueExpr { syntax }),
3840 BREAK_EXPR => Expr::BreakExpr(BreakExpr { syntax }),
3841 LABEL => Expr::Label(Label { syntax }),
3842 BLOCK_EXPR => Expr::BlockExpr(BlockExpr { syntax }),
3843 RETURN_EXPR => Expr::ReturnExpr(ReturnExpr { syntax }),
3844 MATCH_EXPR => Expr::MatchExpr(MatchExpr { syntax }),
3845 RECORD_LIT => Expr::RecordLit(RecordLit { syntax }),
3846 CALL_EXPR => Expr::CallExpr(CallExpr { syntax }),
3847 INDEX_EXPR => Expr::IndexExpr(IndexExpr { syntax }),
3848 METHOD_CALL_EXPR => Expr::MethodCallExpr(MethodCallExpr { syntax }),
3849 FIELD_EXPR => Expr::FieldExpr(FieldExpr { syntax }),
3850 AWAIT_EXPR => Expr::AwaitExpr(AwaitExpr { syntax }),
3851 TRY_EXPR => Expr::TryExpr(TryExpr { syntax }),
3852 TRY_BLOCK_EXPR => Expr::TryBlockExpr(TryBlockExpr { syntax }),
3853 CAST_EXPR => Expr::CastExpr(CastExpr { syntax }),
3854 REF_EXPR => Expr::RefExpr(RefExpr { syntax }),
3855 PREFIX_EXPR => Expr::PrefixExpr(PrefixExpr { syntax }),
3856 RANGE_EXPR => Expr::RangeExpr(RangeExpr { syntax }),
3857 BIN_EXPR => Expr::BinExpr(BinExpr { syntax }),
3858 LITERAL => Expr::Literal(Literal { syntax }),
3859 MACRO_CALL => Expr::MacroCall(MacroCall { syntax }),
3860 BOX_EXPR => Expr::BoxExpr(BoxExpr { syntax }),
3861 _ => return None,
3862 };
3863 Some(res)
3981 } 3864 }
3982 fn syntax(&self) -> &SyntaxNode { 3865 fn syntax(&self) -> &SyntaxNode {
3983 &self.syntax 3866 match self {
3867 Expr::TupleExpr(it) => &it.syntax,
3868 Expr::ArrayExpr(it) => &it.syntax,
3869 Expr::ParenExpr(it) => &it.syntax,
3870 Expr::PathExpr(it) => &it.syntax,
3871 Expr::LambdaExpr(it) => &it.syntax,
3872 Expr::IfExpr(it) => &it.syntax,
3873 Expr::LoopExpr(it) => &it.syntax,
3874 Expr::ForExpr(it) => &it.syntax,
3875 Expr::WhileExpr(it) => &it.syntax,
3876 Expr::ContinueExpr(it) => &it.syntax,
3877 Expr::BreakExpr(it) => &it.syntax,
3878 Expr::Label(it) => &it.syntax,
3879 Expr::BlockExpr(it) => &it.syntax,
3880 Expr::ReturnExpr(it) => &it.syntax,
3881 Expr::MatchExpr(it) => &it.syntax,
3882 Expr::RecordLit(it) => &it.syntax,
3883 Expr::CallExpr(it) => &it.syntax,
3884 Expr::IndexExpr(it) => &it.syntax,
3885 Expr::MethodCallExpr(it) => &it.syntax,
3886 Expr::FieldExpr(it) => &it.syntax,
3887 Expr::AwaitExpr(it) => &it.syntax,
3888 Expr::TryExpr(it) => &it.syntax,
3889 Expr::TryBlockExpr(it) => &it.syntax,
3890 Expr::CastExpr(it) => &it.syntax,
3891 Expr::RefExpr(it) => &it.syntax,
3892 Expr::PrefixExpr(it) => &it.syntax,
3893 Expr::RangeExpr(it) => &it.syntax,
3894 Expr::BinExpr(it) => &it.syntax,
3895 Expr::Literal(it) => &it.syntax,
3896 Expr::MacroCall(it) => &it.syntax,
3897 Expr::BoxExpr(it) => &it.syntax,
3898 }
3984 } 3899 }
3985} 3900}
3986impl Visibility {}
3987#[derive(Debug, Clone, PartialEq, Eq, Hash)] 3901#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3988pub struct WhereClause { 3902pub enum Pat {
3989 pub(crate) syntax: SyntaxNode, 3903 RefPat(RefPat),
3904 BoxPat(BoxPat),
3905 BindPat(BindPat),
3906 PlaceholderPat(PlaceholderPat),
3907 DotDotPat(DotDotPat),
3908 PathPat(PathPat),
3909 RecordPat(RecordPat),
3910 TupleStructPat(TupleStructPat),
3911 TuplePat(TuplePat),
3912 SlicePat(SlicePat),
3913 RangePat(RangePat),
3914 LiteralPat(LiteralPat),
3990} 3915}
3991impl AstNode for WhereClause { 3916impl From<RefPat> for Pat {
3917 fn from(node: RefPat) -> Pat {
3918 Pat::RefPat(node)
3919 }
3920}
3921impl From<BoxPat> for Pat {
3922 fn from(node: BoxPat) -> Pat {
3923 Pat::BoxPat(node)
3924 }
3925}
3926impl From<BindPat> for Pat {
3927 fn from(node: BindPat) -> Pat {
3928 Pat::BindPat(node)
3929 }
3930}
3931impl From<PlaceholderPat> for Pat {
3932 fn from(node: PlaceholderPat) -> Pat {
3933 Pat::PlaceholderPat(node)
3934 }
3935}
3936impl From<DotDotPat> for Pat {
3937 fn from(node: DotDotPat) -> Pat {
3938 Pat::DotDotPat(node)
3939 }
3940}
3941impl From<PathPat> for Pat {
3942 fn from(node: PathPat) -> Pat {
3943 Pat::PathPat(node)
3944 }
3945}
3946impl From<RecordPat> for Pat {
3947 fn from(node: RecordPat) -> Pat {
3948 Pat::RecordPat(node)
3949 }
3950}
3951impl From<TupleStructPat> for Pat {
3952 fn from(node: TupleStructPat) -> Pat {
3953 Pat::TupleStructPat(node)
3954 }
3955}
3956impl From<TuplePat> for Pat {
3957 fn from(node: TuplePat) -> Pat {
3958 Pat::TuplePat(node)
3959 }
3960}
3961impl From<SlicePat> for Pat {
3962 fn from(node: SlicePat) -> Pat {
3963 Pat::SlicePat(node)
3964 }
3965}
3966impl From<RangePat> for Pat {
3967 fn from(node: RangePat) -> Pat {
3968 Pat::RangePat(node)
3969 }
3970}
3971impl From<LiteralPat> for Pat {
3972 fn from(node: LiteralPat) -> Pat {
3973 Pat::LiteralPat(node)
3974 }
3975}
3976impl AstNode for Pat {
3992 fn can_cast(kind: SyntaxKind) -> bool { 3977 fn can_cast(kind: SyntaxKind) -> bool {
3993 match kind { 3978 match kind {
3994 WHERE_CLAUSE => true, 3979 REF_PAT | BOX_PAT | BIND_PAT | PLACEHOLDER_PAT | DOT_DOT_PAT | PATH_PAT
3980 | RECORD_PAT | TUPLE_STRUCT_PAT | TUPLE_PAT | SLICE_PAT | RANGE_PAT | LITERAL_PAT => {
3981 true
3982 }
3995 _ => false, 3983 _ => false,
3996 } 3984 }
3997 } 3985 }
3998 fn cast(syntax: SyntaxNode) -> Option<Self> { 3986 fn cast(syntax: SyntaxNode) -> Option<Self> {
3999 if Self::can_cast(syntax.kind()) { 3987 let res = match syntax.kind() {
4000 Some(Self { syntax }) 3988 REF_PAT => Pat::RefPat(RefPat { syntax }),
4001 } else { 3989 BOX_PAT => Pat::BoxPat(BoxPat { syntax }),
4002 None 3990 BIND_PAT => Pat::BindPat(BindPat { syntax }),
4003 } 3991 PLACEHOLDER_PAT => Pat::PlaceholderPat(PlaceholderPat { syntax }),
3992 DOT_DOT_PAT => Pat::DotDotPat(DotDotPat { syntax }),
3993 PATH_PAT => Pat::PathPat(PathPat { syntax }),
3994 RECORD_PAT => Pat::RecordPat(RecordPat { syntax }),
3995 TUPLE_STRUCT_PAT => Pat::TupleStructPat(TupleStructPat { syntax }),
3996 TUPLE_PAT => Pat::TuplePat(TuplePat { syntax }),
3997 SLICE_PAT => Pat::SlicePat(SlicePat { syntax }),
3998 RANGE_PAT => Pat::RangePat(RangePat { syntax }),
3999 LITERAL_PAT => Pat::LiteralPat(LiteralPat { syntax }),
4000 _ => return None,
4001 };
4002 Some(res)
4004 } 4003 }
4005 fn syntax(&self) -> &SyntaxNode { 4004 fn syntax(&self) -> &SyntaxNode {
4006 &self.syntax 4005 match self {
4006 Pat::RefPat(it) => &it.syntax,
4007 Pat::BoxPat(it) => &it.syntax,
4008 Pat::BindPat(it) => &it.syntax,
4009 Pat::PlaceholderPat(it) => &it.syntax,
4010 Pat::DotDotPat(it) => &it.syntax,
4011 Pat::PathPat(it) => &it.syntax,
4012 Pat::RecordPat(it) => &it.syntax,
4013 Pat::TupleStructPat(it) => &it.syntax,
4014 Pat::TuplePat(it) => &it.syntax,
4015 Pat::SlicePat(it) => &it.syntax,
4016 Pat::RangePat(it) => &it.syntax,
4017 Pat::LiteralPat(it) => &it.syntax,
4018 }
4007 } 4019 }
4008} 4020}
4009impl WhereClause { 4021#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4010 pub fn predicates(&self) -> AstChildren<WherePred> { 4022pub enum AttrInput {
4011 AstChildren::new(&self.syntax) 4023 Literal(Literal),
4024 TokenTree(TokenTree),
4025}
4026impl From<Literal> for AttrInput {
4027 fn from(node: Literal) -> AttrInput {
4028 AttrInput::Literal(node)
4012 } 4029 }
4013} 4030}
4014#[derive(Debug, Clone, PartialEq, Eq, Hash)] 4031impl From<TokenTree> for AttrInput {
4015pub struct WherePred { 4032 fn from(node: TokenTree) -> AttrInput {
4016 pub(crate) syntax: SyntaxNode, 4033 AttrInput::TokenTree(node)
4034 }
4017} 4035}
4018impl AstNode for WherePred { 4036impl AstNode for AttrInput {
4019 fn can_cast(kind: SyntaxKind) -> bool { 4037 fn can_cast(kind: SyntaxKind) -> bool {
4020 match kind { 4038 match kind {
4021 WHERE_PRED => true, 4039 LITERAL | TOKEN_TREE => true,
4022 _ => false, 4040 _ => false,
4023 } 4041 }
4024 } 4042 }
4025 fn cast(syntax: SyntaxNode) -> Option<Self> { 4043 fn cast(syntax: SyntaxNode) -> Option<Self> {
4026 if Self::can_cast(syntax.kind()) { 4044 let res = match syntax.kind() {
4027 Some(Self { syntax }) 4045 LITERAL => AttrInput::Literal(Literal { syntax }),
4028 } else { 4046 TOKEN_TREE => AttrInput::TokenTree(TokenTree { syntax }),
4029 None 4047 _ => return None,
4030 } 4048 };
4049 Some(res)
4031 } 4050 }
4032 fn syntax(&self) -> &SyntaxNode { 4051 fn syntax(&self) -> &SyntaxNode {
4033 &self.syntax 4052 match self {
4053 AttrInput::Literal(it) => &it.syntax,
4054 AttrInput::TokenTree(it) => &it.syntax,
4055 }
4034 } 4056 }
4035} 4057}
4036impl ast::TypeBoundsOwner for WherePred {} 4058#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4037impl WherePred { 4059pub enum Stmt {
4038 pub fn type_ref(&self) -> Option<TypeRef> { 4060 ExprStmt(ExprStmt),
4039 AstChildren::new(&self.syntax).next() 4061 LetStmt(LetStmt),
4062}
4063impl From<ExprStmt> for Stmt {
4064 fn from(node: ExprStmt) -> Stmt {
4065 Stmt::ExprStmt(node)
4040 } 4066 }
4041} 4067}
4042#[derive(Debug, Clone, PartialEq, Eq, Hash)] 4068impl From<LetStmt> for Stmt {
4043pub struct WhileExpr { 4069 fn from(node: LetStmt) -> Stmt {
4044 pub(crate) syntax: SyntaxNode, 4070 Stmt::LetStmt(node)
4071 }
4045} 4072}
4046impl AstNode for WhileExpr { 4073impl AstNode for Stmt {
4047 fn can_cast(kind: SyntaxKind) -> bool { 4074 fn can_cast(kind: SyntaxKind) -> bool {
4048 match kind { 4075 match kind {
4049 WHILE_EXPR => true, 4076 EXPR_STMT | LET_STMT => true,
4050 _ => false, 4077 _ => false,
4051 } 4078 }
4052 } 4079 }
4053 fn cast(syntax: SyntaxNode) -> Option<Self> { 4080 fn cast(syntax: SyntaxNode) -> Option<Self> {
4054 if Self::can_cast(syntax.kind()) { 4081 let res = match syntax.kind() {
4055 Some(Self { syntax }) 4082 EXPR_STMT => Stmt::ExprStmt(ExprStmt { syntax }),
4056 } else { 4083 LET_STMT => Stmt::LetStmt(LetStmt { syntax }),
4057 None 4084 _ => return None,
4058 } 4085 };
4086 Some(res)
4059 } 4087 }
4060 fn syntax(&self) -> &SyntaxNode { 4088 fn syntax(&self) -> &SyntaxNode {
4061 &self.syntax 4089 match self {
4062 } 4090 Stmt::ExprStmt(it) => &it.syntax,
4063} 4091 Stmt::LetStmt(it) => &it.syntax,
4064impl ast::LoopBodyOwner for WhileExpr {} 4092 }
4065impl WhileExpr {
4066 pub fn condition(&self) -> Option<Condition> {
4067 AstChildren::new(&self.syntax).next()
4068 } 4093 }
4069} 4094}
diff --git a/crates/ra_syntax/src/grammar.ron b/crates/ra_syntax/src/grammar.ron
deleted file mode 100644
index e43a724f0..000000000
--- a/crates/ra_syntax/src/grammar.ron
+++ /dev/null
@@ -1,736 +0,0 @@
1// Stores definitions which must be used in multiple places
2// See `cargo xtask codegen` (defined in xtasks/src/main.rs)
3Grammar(
4 punct: [
5 (";", "SEMI"),
6 (",", "COMMA"),
7 ("(", "L_PAREN"),
8 (")", "R_PAREN"),
9 ("{", "L_CURLY"),
10 ("}", "R_CURLY"),
11 ("[", "L_BRACK"),
12 ("]", "R_BRACK"),
13 ("<", "L_ANGLE"),
14 (">", "R_ANGLE"),
15 ("@", "AT"),
16 ("#", "POUND"),
17 ("~", "TILDE"),
18 ("?", "QUESTION"),
19 ("$", "DOLLAR"),
20 ("&", "AMP"),
21 ("|", "PIPE"),
22 ("+", "PLUS"),
23 ("*", "STAR"),
24 ("/", "SLASH"),
25 ("^", "CARET"),
26 ("%", "PERCENT"),
27 ("_", "UNDERSCORE"),
28 (".", "DOT"),
29 ("..", "DOTDOT"),
30 ("...", "DOTDOTDOT"),
31 ("..=", "DOTDOTEQ"),
32 (":", "COLON"),
33 ("::", "COLONCOLON"),
34 ("=", "EQ"),
35 ("==", "EQEQ"),
36 ("=>", "FAT_ARROW"),
37 ("!", "EXCL"),
38 ("!=", "NEQ"),
39 ("-", "MINUS"),
40 ("->", "THIN_ARROW"),
41 ("<=", "LTEQ"),
42 (">=", "GTEQ"),
43 ("+=", "PLUSEQ"),
44 ("-=", "MINUSEQ"),
45 ("|=", "PIPEEQ"),
46 ("&=", "AMPEQ"),
47 ("^=", "CARETEQ"),
48 ("/=", "SLASHEQ"),
49 ("*=", "STAREQ"),
50 ("%=", "PERCENTEQ"),
51 ("&&", "AMPAMP"),
52 ("||", "PIPEPIPE"),
53 ("<<", "SHL"),
54 (">>", "SHR"),
55 ("<<=", "SHLEQ"),
56 (">>=", "SHREQ"),
57 ],
58 keywords: [
59 "async",
60 "use",
61 "fn",
62 "struct",
63 "enum",
64 "trait",
65 "impl",
66 "dyn",
67 "true",
68 "false",
69 "as",
70 "extern",
71 "crate",
72 "mod",
73 "pub",
74 "self",
75 "super",
76 "in",
77 "where",
78 "for",
79 "loop",
80 "while",
81 "continue",
82 "break",
83 "if",
84 "else",
85 "match",
86 "const",
87 "static",
88 "mut",
89 "unsafe",
90 "type",
91 "ref",
92 "let",
93 "move",
94 "return",
95 "try",
96 "box",
97 "await",
98 "macro"
99 ],
100 contextual_keywords: [
101 "auto",
102 "default",
103 "existential",
104 "union",
105 ],
106 literals: [
107 "INT_NUMBER",
108 "FLOAT_NUMBER",
109 "CHAR",
110 "BYTE",
111 "STRING",
112 "RAW_STRING",
113 "BYTE_STRING",
114 "RAW_BYTE_STRING",
115 ],
116 tokens: [
117 "ERROR",
118 "IDENT",
119 "WHITESPACE",
120 "LIFETIME",
121 "COMMENT",
122 "SHEBANG",
123 "L_DOLLAR",
124 "R_DOLLAR",
125 ],
126 nodes: [
127 "SOURCE_FILE",
128
129 "STRUCT_DEF",
130 "UNION_DEF",
131 "ENUM_DEF",
132 "FN_DEF",
133 "RET_TYPE",
134 "EXTERN_CRATE_ITEM",
135 "MODULE",
136 "USE_ITEM",
137 "STATIC_DEF",
138 "CONST_DEF",
139 "TRAIT_DEF",
140 "IMPL_BLOCK",
141 "TYPE_ALIAS_DEF",
142 "MACRO_CALL",
143 "TOKEN_TREE",
144 "MACRO_DEF",
145
146 "PAREN_TYPE",
147 "TUPLE_TYPE",
148 "NEVER_TYPE",
149 "PATH_TYPE",
150 "POINTER_TYPE",
151 "ARRAY_TYPE",
152 "SLICE_TYPE",
153 "REFERENCE_TYPE",
154 "PLACEHOLDER_TYPE",
155 "FN_POINTER_TYPE",
156 "FOR_TYPE",
157 "IMPL_TRAIT_TYPE",
158 "DYN_TRAIT_TYPE",
159
160 "REF_PAT",
161 "BOX_PAT",
162 "BIND_PAT",
163 "PLACEHOLDER_PAT",
164 "DOT_DOT_PAT",
165 "PATH_PAT",
166 "RECORD_PAT",
167 "RECORD_FIELD_PAT_LIST",
168 "RECORD_FIELD_PAT",
169 "TUPLE_STRUCT_PAT",
170 "TUPLE_PAT",
171 "SLICE_PAT",
172 "RANGE_PAT",
173 "LITERAL_PAT",
174
175 // atoms
176 "TUPLE_EXPR",
177 "ARRAY_EXPR",
178 "PAREN_EXPR",
179 "PATH_EXPR",
180 "LAMBDA_EXPR",
181 "IF_EXPR",
182 "WHILE_EXPR",
183 "CONDITION",
184 "LOOP_EXPR",
185 "FOR_EXPR",
186 "CONTINUE_EXPR",
187 "BREAK_EXPR",
188 "LABEL",
189 "BLOCK_EXPR",
190 "RETURN_EXPR",
191 "MATCH_EXPR",
192 "MATCH_ARM_LIST",
193 "MATCH_ARM",
194 "MATCH_GUARD",
195 "RECORD_LIT",
196 "RECORD_FIELD_LIST",
197 "RECORD_FIELD",
198 "TRY_BLOCK_EXPR",
199 "BOX_EXPR",
200
201 // postfix
202 "CALL_EXPR",
203 "INDEX_EXPR",
204 "METHOD_CALL_EXPR",
205 "FIELD_EXPR",
206 "AWAIT_EXPR",
207 "TRY_EXPR",
208 "CAST_EXPR",
209
210 // unary
211 "REF_EXPR",
212 "PREFIX_EXPR",
213
214 "RANGE_EXPR", // just weird
215 "BIN_EXPR",
216
217 "BLOCK",
218 "EXTERN_BLOCK",
219 "EXTERN_ITEM_LIST",
220 "ENUM_VARIANT",
221 "RECORD_FIELD_DEF_LIST",
222 "RECORD_FIELD_DEF",
223 "TUPLE_FIELD_DEF_LIST",
224 "TUPLE_FIELD_DEF",
225 "ENUM_VARIANT_LIST",
226 "ITEM_LIST",
227 "ATTR",
228 "META_ITEM", // not an item actually
229 "USE_TREE",
230 "USE_TREE_LIST",
231 "PATH",
232 "PATH_SEGMENT",
233 "LITERAL",
234 "ALIAS",
235 "VISIBILITY",
236 "WHERE_CLAUSE",
237 "WHERE_PRED",
238 "ABI",
239 "NAME",
240 "NAME_REF",
241
242 "LET_STMT",
243 "EXPR_STMT",
244
245 "TYPE_PARAM_LIST",
246 "LIFETIME_PARAM",
247 "TYPE_PARAM",
248 "CONST_PARAM",
249 "TYPE_ARG_LIST",
250 "LIFETIME_ARG",
251 "TYPE_ARG",
252 "ASSOC_TYPE_ARG",
253
254 "PARAM_LIST",
255 "PARAM",
256 "SELF_PARAM",
257 "ARG_LIST",
258 "TYPE_BOUND",
259 "TYPE_BOUND_LIST",
260
261 // macro related
262 "MACRO_ITEMS",
263 "MACRO_STMTS",
264 ],
265 ast: {
266 "SourceFile": (
267 traits: [ "ModuleItemOwner", "FnDefOwner" ],
268 collections: [
269 ("modules", "Module"),
270 ]
271 ),
272 "FnDef": (
273 traits: [
274 "VisibilityOwner",
275 "NameOwner",
276 "TypeParamsOwner",
277 "AttrsOwner",
278 "DocCommentsOwner"
279 ],
280 options: [ "ParamList", ["body", "BlockExpr"], "RetType" ],
281 ),
282 "RetType": (options: ["TypeRef"]),
283 "StructDef": (
284 traits: [
285 "VisibilityOwner",
286 "NameOwner",
287 "TypeParamsOwner",
288 "AttrsOwner",
289 "DocCommentsOwner"
290 ]
291 ),
292 "UnionDef": (
293 traits: [
294 "VisibilityOwner",
295 "NameOwner",
296 "TypeParamsOwner",
297 "AttrsOwner",
298 "DocCommentsOwner"
299 ],
300 options: ["RecordFieldDefList"],
301 ),
302 "RecordFieldDefList": (collections: [("fields", "RecordFieldDef")]),
303 "RecordFieldDef": (
304 traits: [
305 "VisibilityOwner",
306 "NameOwner",
307 "AttrsOwner",
308 "DocCommentsOwner",
309 "TypeAscriptionOwner"
310 ]
311 ),
312 "TupleFieldDefList": (collections: [("fields", "TupleFieldDef")]),
313 "TupleFieldDef": ( traits: ["VisibilityOwner", "AttrsOwner"], options: ["TypeRef"]),
314 "EnumDef": ( traits: [
315 "VisibilityOwner",
316 "NameOwner",
317 "TypeParamsOwner",
318 "AttrsOwner",
319 "DocCommentsOwner"
320 ], options: [["variant_list", "EnumVariantList"]] ),
321 "EnumVariantList": ( collections: [("variants", "EnumVariant")] ),
322 "EnumVariant": ( traits: ["NameOwner", "DocCommentsOwner", "AttrsOwner"], options: ["Expr"] ),
323 "TraitDef": (
324 traits: ["VisibilityOwner", "NameOwner", "AttrsOwner", "DocCommentsOwner", "TypeParamsOwner", "TypeBoundsOwner"],
325 options: ["ItemList"]
326 ),
327 "Module": (
328 traits: ["VisibilityOwner", "NameOwner", "AttrsOwner", "DocCommentsOwner" ],
329 options: [ "ItemList" ]
330 ),
331 "ItemList": (
332 collections: [("impl_items", "ImplItem")],
333 traits: [ "FnDefOwner", "ModuleItemOwner" ],
334 ),
335 "ConstDef": (
336 traits: [
337 "VisibilityOwner",
338 "NameOwner",
339 "TypeParamsOwner",
340 "AttrsOwner",
341 "DocCommentsOwner",
342 "TypeAscriptionOwner",
343 ],
344 options: [ ["body","Expr"]],
345 ),
346 "StaticDef": (
347 traits: [
348 "VisibilityOwner",
349 "NameOwner",
350 "TypeParamsOwner",
351 "AttrsOwner",
352 "DocCommentsOwner",
353 "TypeAscriptionOwner",
354 ],
355 options: [ ["body","Expr"]],
356 ),
357 "TypeAliasDef": (
358 traits: [
359 "VisibilityOwner",
360 "NameOwner",
361 "TypeParamsOwner",
362 "AttrsOwner",
363 "DocCommentsOwner",
364 "TypeBoundsOwner",
365 ],
366 options: ["TypeRef"]
367 ),
368 "ImplBlock": (options: ["ItemList"], traits: ["TypeParamsOwner", "AttrsOwner"]),
369
370 "ParenType": (options: ["TypeRef"]),
371 "TupleType": ( collections: [("fields", "TypeRef")] ),
372 "NeverType": (),
373 "PathType": (options: ["Path"]),
374 "PointerType": (options: ["TypeRef"]),
375 "ArrayType": ( options: ["TypeRef", "Expr"] ),
376 "SliceType": ( options: ["TypeRef"] ),
377 "ReferenceType": (options: ["TypeRef"]),
378 "PlaceholderType": (),
379 "FnPointerType": (options: ["ParamList", "RetType"]),
380 "ForType": (options: ["TypeRef"]),
381 "ImplTraitType": (
382 traits: ["TypeBoundsOwner"],
383 ),
384 "DynTraitType": (
385 traits: ["TypeBoundsOwner"],
386 ),
387
388 "TypeRef": ( enum: [
389 "ParenType",
390 "TupleType",
391 "NeverType",
392 "PathType",
393 "PointerType",
394 "ArrayType",
395 "SliceType",
396 "ReferenceType",
397 "PlaceholderType",
398 "FnPointerType",
399 "ForType",
400 "ImplTraitType",
401 "DynTraitType",
402 ]),
403
404 "NominalDef": (
405 enum: ["StructDef", "EnumDef", "UnionDef"],
406 traits: [
407 "NameOwner",
408 "TypeParamsOwner",
409 "AttrsOwner"
410 ],
411 ),
412 "ModuleItem": (
413 enum: ["StructDef", "UnionDef", "EnumDef", "FnDef", "TraitDef", "TypeAliasDef", "ImplBlock",
414 "UseItem", "ExternCrateItem", "ConstDef", "StaticDef", "Module" ],
415 traits: ["AttrsOwner", "VisibilityOwner"],
416 ),
417 "ImplItem": (
418 enum: ["FnDef", "TypeAliasDef", "ConstDef"],
419 traits: ["AttrsOwner"]
420 ),
421
422 "TupleExpr": (
423 collections: [("exprs", "Expr")]
424 ),
425 "ArrayExpr": (
426 collections: [("exprs", "Expr")]
427 ),
428 "ParenExpr": (options: ["Expr"]),
429 "PathExpr": (options: ["Path"]),
430 "LambdaExpr": (
431 options: [
432 "ParamList", "RetType",
433 ["body", "Expr"],
434 ]
435 ),
436 "IfExpr": (
437 options: [ "Condition" ]
438 ),
439 "LoopExpr": (
440 traits: ["LoopBodyOwner"],
441 ),
442 "TryBlockExpr": (
443 options: [["body", "BlockExpr"]],
444 ),
445 "ForExpr": (
446 traits: ["LoopBodyOwner"],
447 options: [
448 "Pat",
449 ["iterable", "Expr"],
450 ]
451 ),
452 "WhileExpr": (
453 traits: ["LoopBodyOwner"],
454 options: [ "Condition" ]
455 ),
456 "ContinueExpr": (),
457 "BreakExpr": (options: ["Expr"]),
458 "Label": (),
459 "BlockExpr": (
460 options: [ "Block" ]
461 ),
462 "ReturnExpr": (options: ["Expr"]),
463 "MatchExpr": (
464 options: [ "Expr", "MatchArmList" ],
465 ),
466 "MatchArmList": (
467 collections: [ ("arms", "MatchArm") ],
468 traits: [ "AttrsOwner" ]
469 ),
470 "MatchArm": (
471 options: [
472 [ "guard", "MatchGuard" ],
473 "Expr",
474 ],
475 collections: [ ("pats", "Pat") ],
476 traits: [ "AttrsOwner" ]
477 ),
478 "MatchGuard": (options: ["Expr"]),
479 "RecordLit": (options: ["Path", "RecordFieldList"]),
480 "RecordFieldList": (
481 collections: [ ("fields", "RecordField") ],
482 options: [["spread", "Expr"]]
483 ),
484 "RecordField": (options: ["NameRef", "Expr"]),
485 "CallExpr": (
486 traits: ["ArgListOwner"],
487 options: [ "Expr" ],
488 ),
489 "MethodCallExpr": (
490 traits: ["ArgListOwner"],
491 options: [ "Expr", "NameRef", "TypeArgList" ],
492 ),
493 "IndexExpr": (),
494 "FieldExpr": (options: ["Expr", "NameRef"]),
495 "AwaitExpr": (options: ["Expr"]),
496 "TryExpr": (options: ["Expr"]),
497 "CastExpr": (options: ["Expr", "TypeRef"]),
498 "RefExpr": (options: ["Expr"]),
499 "PrefixExpr": (options: ["Expr"]),
500 "BoxExpr": (options: ["Expr"]),
501 "RangeExpr": (),
502 "BinExpr": (),
503
504 "Literal": (),
505
506 "Expr": (
507 enum: [
508 "TupleExpr",
509 "ArrayExpr",
510 "ParenExpr",
511 "PathExpr",
512 "LambdaExpr",
513 "IfExpr",
514 "LoopExpr",
515 "ForExpr",
516 "WhileExpr",
517 "ContinueExpr",
518 "BreakExpr",
519 "Label",
520 "BlockExpr",
521 "ReturnExpr",
522 "MatchExpr",
523 "RecordLit",
524 "CallExpr",
525 "IndexExpr",
526 "MethodCallExpr",
527 "FieldExpr",
528 "AwaitExpr",
529 "TryExpr",
530 "TryBlockExpr",
531 "CastExpr",
532 "RefExpr",
533 "PrefixExpr",
534 "RangeExpr",
535 "BinExpr",
536 "Literal",
537 "MacroCall",
538 "BoxExpr",
539 ],
540 ),
541
542 "RefPat": ( options: [ "Pat" ]),
543 "BoxPat": ( options: [ "Pat" ]),
544 "BindPat": (
545 options: [ "Pat" ],
546 traits: ["NameOwner"]
547 ),
548 "PlaceholderPat": (),
549 "DotDotPat": (),
550 "PathPat": ( options: [ "Path" ] ),
551 "RecordPat": ( options: ["RecordFieldPatList", "Path"] ),
552 "RecordFieldPatList": (
553 collections: [
554 ("record_field_pats", "RecordFieldPat"),
555 ("bind_pats", "BindPat"),
556 ]
557 ),
558 "RecordFieldPat": (
559 traits: ["NameOwner"],
560 options: ["Pat"]
561 ),
562 "TupleStructPat": (
563 options: ["Path"],
564 collections: [("args", "Pat")],
565 ),
566 "TuplePat": ( collections: [("args", "Pat")] ),
567 "SlicePat": (),
568 "RangePat": (),
569 "LiteralPat": (options: ["Literal"]),
570
571 "Pat": (
572 enum: [
573 "RefPat",
574 "BoxPat",
575 "BindPat",
576 "PlaceholderPat",
577 "DotDotPat",
578 "PathPat",
579 "RecordPat",
580 "TupleStructPat",
581 "TuplePat",
582 "SlicePat",
583 "RangePat",
584 "LiteralPat",
585 ],
586 ),
587
588 "Visibility": (),
589 "Name": (),
590 "NameRef": (),
591 "MacroCall": (
592 traits: [ "NameOwner", "AttrsOwner","DocCommentsOwner" ],
593 options: [ "TokenTree", "Path" ],
594 ),
595 "AttrInput": ( enum: [ "Literal", "TokenTree" ] ),
596 "Attr": ( options: [ "Path", [ "input", "AttrInput" ] ] ),
597 "TokenTree": (),
598 "TypeParamList": (
599 collections: [
600 ("type_params", "TypeParam" ),
601 ("lifetime_params", "LifetimeParam" ),
602 ]
603 ),
604 "TypeParam": (
605 options: [("default_type", "TypeRef")],
606 traits: ["NameOwner", "AttrsOwner", "TypeBoundsOwner"],
607 ),
608 "ConstParam": (
609 options: [("default_val", "Expr")],
610 traits: ["NameOwner", "AttrsOwner", "TypeAscriptionOwner"],
611 ),
612 "LifetimeParam": (
613 traits: ["AttrsOwner"],
614 ),
615 "TypeBound": (
616 options: [
617 "TypeRef",
618 ]
619 ),
620 "TypeBoundList": (
621 collections: [
622 ("bounds", "TypeBound"),
623 ]
624 ),
625 "WherePred": (
626 options: [
627 "TypeRef",
628 ],
629 traits: [
630 "TypeBoundsOwner",
631 ],
632 ),
633 "WhereClause": (
634 collections: [
635 ("predicates", "WherePred"),
636 ],
637 ),
638 "ExprStmt": (
639 options: [ ["expr", "Expr"] ]
640 ),
641 "LetStmt": (
642 options: [
643 ["pat", "Pat"],
644 ["initializer", "Expr"],
645 ],
646 traits: [
647 "TypeAscriptionOwner",
648 ]
649 ),
650 "Condition": (
651 options: [ "Pat", "Expr" ]
652 ),
653 "Stmt": (
654 enum: ["ExprStmt", "LetStmt"],
655 ),
656 "Block": (
657 options: [ "Expr" ],
658 collections: [
659 ("statements", "Stmt"),
660 ],
661 traits: [
662 "AttrsOwner",
663 "ModuleItemOwner",
664 ]
665 ),
666 "ParamList": (
667 options: [ "SelfParam" ],
668 collections: [
669 ("params", "Param"),
670 ]
671 ),
672 "SelfParam": (
673 traits: [
674 "TypeAscriptionOwner",
675 "AttrsOwner",
676 ]
677 ),
678 "Param": (
679 options: [ "Pat" ],
680 traits: [
681 "TypeAscriptionOwner",
682 "AttrsOwner",
683 ]
684 ),
685 "UseItem": (
686 traits: ["AttrsOwner", "VisibilityOwner"],
687 options: [ "UseTree" ],
688 ),
689 "UseTree": (
690 options: [ "Path", "UseTreeList", "Alias" ]
691 ),
692 "Alias": (
693 traits: ["NameOwner"],
694 ),
695 "UseTreeList": (
696 collections: [("use_trees", "UseTree")]
697 ),
698 "ExternCrateItem": (
699 traits: ["AttrsOwner", "VisibilityOwner"],
700 options: ["NameRef", "Alias"],
701 ),
702 "ArgList": (
703 collections: [
704 ("args", "Expr"),
705 ]
706 ),
707 "Path": (
708 options: [
709 ["segment", "PathSegment"],
710 ["qualifier", "Path"],
711 ]
712 ),
713 "PathSegment": (
714 options: [ "NameRef", "TypeArgList", "ParamList", "RetType", "PathType" ]
715 ),
716 "TypeArgList": (collections: [
717 ("type_args", "TypeArg"),
718 ("lifetime_args", "LifetimeArg"),
719 ("assoc_type_args", "AssocTypeArg"),
720 ]),
721 "TypeArg": (options: ["TypeRef"]),
722 "AssocTypeArg": (options: ["NameRef", "TypeRef"]),
723 "LifetimeArg": (),
724
725 "MacroItems": (
726 traits: [ "ModuleItemOwner", "FnDefOwner" ],
727 ),
728
729 "MacroStmts" : (
730 options: [ "Expr" ],
731 collections: [
732 ("statements", "Stmt"),
733 ],
734 )
735 },
736)
diff --git a/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.rs b/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.rs
index 385c43131..0d07d7651 100644
--- a/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.rs
+++ b/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.rs
@@ -1 +1 @@
type A = B<'static, i32, Item=u64>; type A = B<'static, i32, 1, { 2 }, Item=u64>;
diff --git a/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.txt b/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.txt
index 4786bf77a..025faf5ca 100644
--- a/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.txt
+++ b/crates/ra_syntax/test_data/parser/inline/ok/0039_type_arg.txt
@@ -1,5 +1,5 @@
1SOURCE_FILE@[0; 36) 1SOURCE_FILE@[0; 46)
2 TYPE_ALIAS_DEF@[0; 35) 2 TYPE_ALIAS_DEF@[0; 45)
3 TYPE_KW@[0; 4) "type" 3 TYPE_KW@[0; 4) "type"
4 WHITESPACE@[4; 5) " " 4 WHITESPACE@[4; 5) " "
5 NAME@[5; 6) 5 NAME@[5; 6)
@@ -7,12 +7,12 @@ SOURCE_FILE@[0; 36)
7 WHITESPACE@[6; 7) " " 7 WHITESPACE@[6; 7) " "
8 EQ@[7; 8) "=" 8 EQ@[7; 8) "="
9 WHITESPACE@[8; 9) " " 9 WHITESPACE@[8; 9) " "
10 PATH_TYPE@[9; 34) 10 PATH_TYPE@[9; 44)
11 PATH@[9; 34) 11 PATH@[9; 44)
12 PATH_SEGMENT@[9; 34) 12 PATH_SEGMENT@[9; 44)
13 NAME_REF@[9; 10) 13 NAME_REF@[9; 10)
14 IDENT@[9; 10) "B" 14 IDENT@[9; 10) "B"
15 TYPE_ARG_LIST@[10; 34) 15 TYPE_ARG_LIST@[10; 44)
16 L_ANGLE@[10; 11) "<" 16 L_ANGLE@[10; 11) "<"
17 LIFETIME_ARG@[11; 18) 17 LIFETIME_ARG@[11; 18)
18 LIFETIME@[11; 18) "\'static" 18 LIFETIME@[11; 18) "\'static"
@@ -26,15 +26,30 @@ SOURCE_FILE@[0; 36)
26 IDENT@[20; 23) "i32" 26 IDENT@[20; 23) "i32"
27 COMMA@[23; 24) "," 27 COMMA@[23; 24) ","
28 WHITESPACE@[24; 25) " " 28 WHITESPACE@[24; 25) " "
29 ASSOC_TYPE_ARG@[25; 33) 29 CONST_ARG@[25; 26)
30 NAME_REF@[25; 29) 30 INT_NUMBER@[25; 26) "1"
31 IDENT@[25; 29) "Item" 31 COMMA@[26; 27) ","
32 EQ@[29; 30) "=" 32 WHITESPACE@[27; 28) " "
33 PATH_TYPE@[30; 33) 33 CONST_ARG@[28; 33)
34 PATH@[30; 33) 34 BLOCK_EXPR@[28; 33)
35 PATH_SEGMENT@[30; 33) 35 BLOCK@[28; 33)
36 NAME_REF@[30; 33) 36 L_CURLY@[28; 29) "{"
37 IDENT@[30; 33) "u64" 37 WHITESPACE@[29; 30) " "
38 R_ANGLE@[33; 34) ">" 38 LITERAL@[30; 31)
39 SEMI@[34; 35) ";" 39 INT_NUMBER@[30; 31) "2"
40 WHITESPACE@[35; 36) "\n" 40 WHITESPACE@[31; 32) " "
41 R_CURLY@[32; 33) "}"
42 COMMA@[33; 34) ","
43 WHITESPACE@[34; 35) " "
44 ASSOC_TYPE_ARG@[35; 43)
45 NAME_REF@[35; 39)
46 IDENT@[35; 39) "Item"
47 EQ@[39; 40) "="
48 PATH_TYPE@[40; 43)
49 PATH@[40; 43)
50 PATH_SEGMENT@[40; 43)
51 NAME_REF@[40; 43)
52 IDENT@[40; 43) "u64"
53 R_ANGLE@[43; 44) ">"
54 SEMI@[44; 45) ";"
55 WHITESPACE@[45; 46) "\n"
diff --git a/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.rs b/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.rs
new file mode 100644
index 000000000..cb0a105c2
--- /dev/null
+++ b/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.rs
@@ -0,0 +1 @@
impl<const N: u32> Bar<N> {}
diff --git a/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.txt b/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.txt
new file mode 100644
index 000000000..47fadef85
--- /dev/null
+++ b/crates/ra_syntax/test_data/parser/inline/ok/0150_impl_type_params.txt
@@ -0,0 +1,38 @@
1SOURCE_FILE@[0; 29)
2 IMPL_BLOCK@[0; 28)
3 IMPL_KW@[0; 4) "impl"
4 TYPE_PARAM_LIST@[4; 18)
5 L_ANGLE@[4; 5) "<"
6 CONST_PARAM@[5; 17)
7 CONST_KW@[5; 10) "const"
8 WHITESPACE@[10; 11) " "
9 NAME@[11; 12)
10 IDENT@[11; 12) "N"
11 COLON@[12; 13) ":"
12 WHITESPACE@[13; 14) " "
13 PATH_TYPE@[14; 17)
14 PATH@[14; 17)
15 PATH_SEGMENT@[14; 17)
16 NAME_REF@[14; 17)
17 IDENT@[14; 17) "u32"
18 R_ANGLE@[17; 18) ">"
19 WHITESPACE@[18; 19) " "
20 PATH_TYPE@[19; 25)
21 PATH@[19; 25)
22 PATH_SEGMENT@[19; 25)
23 NAME_REF@[19; 22)
24 IDENT@[19; 22) "Bar"
25 TYPE_ARG_LIST@[22; 25)
26 L_ANGLE@[22; 23) "<"
27 TYPE_ARG@[23; 24)
28 PATH_TYPE@[23; 24)
29 PATH@[23; 24)
30 PATH_SEGMENT@[23; 24)
31 NAME_REF@[23; 24)
32 IDENT@[23; 24) "N"
33 R_ANGLE@[24; 25) ">"
34 WHITESPACE@[25; 26) " "
35 ITEM_LIST@[26; 28)
36 L_CURLY@[26; 27) "{"
37 R_CURLY@[27; 28) "}"
38 WHITESPACE@[28; 29) "\n"
diff --git a/docs/dev/lsp-features.md b/docs/dev/lsp-features.md
index d3e79b8be..00b0867d7 100644
--- a/docs/dev/lsp-features.md
+++ b/docs/dev/lsp-features.md
@@ -41,7 +41,7 @@ This list documents LSP features, supported by rust-analyzer.
41 - trigger characters: `:`, `.` 41 - trigger characters: `:`, `.`
42- [x] [textDocument/hover](https://microsoft.github.io/language-server-protocol/specification#textDocument_hover) 42- [x] [textDocument/hover](https://microsoft.github.io/language-server-protocol/specification#textDocument_hover)
43- [x] [textDocument/signatureHelp](https://microsoft.github.io/language-server-protocol/specification#textDocument_signatureHelp) 43- [x] [textDocument/signatureHelp](https://microsoft.github.io/language-server-protocol/specification#textDocument_signatureHelp)
44 - trigger characters: `(`, `,`, `)` 44 - trigger characters: `(`, `,`
45- [ ] [textDocument/declaration](https://microsoft.github.io/language-server-protocol/specification#textDocument_declaration) 45- [ ] [textDocument/declaration](https://microsoft.github.io/language-server-protocol/specification#textDocument_declaration)
46- [x] [textDocument/definition](https://microsoft.github.io/language-server-protocol/specification#textDocument_definition) 46- [x] [textDocument/definition](https://microsoft.github.io/language-server-protocol/specification#textDocument_definition)
47- [x] [textDocument/typeDefinition](https://microsoft.github.io/language-server-protocol/specification#textDocument_typeDefinition) 47- [x] [textDocument/typeDefinition](https://microsoft.github.io/language-server-protocol/specification#textDocument_typeDefinition)
@@ -58,7 +58,7 @@ This list documents LSP features, supported by rust-analyzer.
58 - rust-analyzer.run 58 - rust-analyzer.run
59 - rust-analyzer.analyzerStatus 59 - rust-analyzer.analyzerStatus
60- [x] [textDocument/codeLens](https://microsoft.github.io/language-server-protocol/specification#textDocument_codeLens) 60- [x] [textDocument/codeLens](https://microsoft.github.io/language-server-protocol/specification#textDocument_codeLens)
61- [ ] [textDocument/documentLink](https://microsoft.github.io/language-server-protocol/specification#codeLens_resolve) 61- [x] [codeLens/resolve](https://microsoft.github.io/language-server-protocol/specification#codeLens_resolve)
62- [ ] [documentLink/resolve](https://microsoft.github.io/language-server-protocol/specification#documentLink_resolve) 62- [ ] [documentLink/resolve](https://microsoft.github.io/language-server-protocol/specification#documentLink_resolve)
63- [ ] [textDocument/documentColor](https://microsoft.github.io/language-server-protocol/specification#textDocument_documentColor) 63- [ ] [textDocument/documentColor](https://microsoft.github.io/language-server-protocol/specification#textDocument_documentColor)
64- [ ] [textDocument/colorPresentation](https://microsoft.github.io/language-server-protocol/specification#textDocument_colorPresentation) 64- [ ] [textDocument/colorPresentation](https://microsoft.github.io/language-server-protocol/specification#textDocument_colorPresentation)
diff --git a/docs/user/README.md b/docs/user/README.md
index 8cf4b68fd..fa202f06c 100644
--- a/docs/user/README.md
+++ b/docs/user/README.md
@@ -44,6 +44,10 @@ $ cargo xtask install
44The automatic installation is expected to *just work* for common cases, if it 44The automatic installation is expected to *just work* for common cases, if it
45doesn't, report bugs! 45doesn't, report bugs!
46 46
47**Note** [#1831](https://github.com/rust-analyzer/rust-analyzer/issues/1831): If you are using the popular
48[Vim emulation plugin](https://github.com/VSCodeVim/Vim), you will likely
49need to turn off the `rust-analyzer.enableEnhancedTyping` setting.
50
47If you have an unusual setup (for example, `code` is not in the `PATH`), you 51If you have an unusual setup (for example, `code` is not in the `PATH`), you
48should adapt these manual installation instructions: 52should adapt these manual installation instructions:
49 53
diff --git a/editors/code/src/client.ts b/editors/code/src/client.ts
index 743384bd7..1ff64a930 100644
--- a/editors/code/src/client.ts
+++ b/editors/code/src/client.ts
@@ -1,5 +1,6 @@
1import { homedir } from 'os'; 1import { homedir } from 'os';
2import * as lc from 'vscode-languageclient'; 2import * as lc from 'vscode-languageclient';
3import { spawnSync } from 'child_process';
3 4
4import { window, workspace } from 'vscode'; 5import { window, workspace } from 'vscode';
5import { Config } from './config'; 6import { Config } from './config';
@@ -13,6 +14,9 @@ export function createClient(config: Config): lc.LanguageClient {
13 } 14 }
14 15
15 const command = expandPathResolving(config.raLspServerPath); 16 const command = expandPathResolving(config.raLspServerPath);
17 if (spawnSync(command, ["--version"]).status !== 0) {
18 window.showErrorMessage(`Unable to execute '${command} --version'`);
19 }
16 const run: lc.Executable = { 20 const run: lc.Executable = {
17 command, 21 command,
18 options: { cwd: folder }, 22 options: { cwd: folder },
diff --git a/xtask/Cargo.toml b/xtask/Cargo.toml
index 65cabf005..72dd5e581 100644
--- a/xtask/Cargo.toml
+++ b/xtask/Cargo.toml
@@ -13,6 +13,4 @@ walkdir = "2.1.3"
13pico-args = "0.3.0" 13pico-args = "0.3.0"
14quote = "1.0.2" 14quote = "1.0.2"
15proc-macro2 = "1.0.1" 15proc-macro2 = "1.0.1"
16ron = "0.5.1"
17serde = { version = "1.0.0", features = ["derive"] }
18anyhow = "1.0.19" 16anyhow = "1.0.19"
diff --git a/xtask/src/ast_src.rs b/xtask/src/ast_src.rs
new file mode 100644
index 000000000..67d1f41bc
--- /dev/null
+++ b/xtask/src/ast_src.rs
@@ -0,0 +1,621 @@
1pub(crate) struct KindsSrc<'a> {
2 pub(crate) punct: &'a [(&'a str, &'a str)],
3 pub(crate) keywords: &'a [&'a str],
4 pub(crate) contextual_keywords: &'a [&'a str],
5 pub(crate) literals: &'a [&'a str],
6 pub(crate) tokens: &'a [&'a str],
7 pub(crate) nodes: &'a [&'a str],
8}
9
10pub(crate) const KINDS_SRC: KindsSrc = KindsSrc {
11 punct: &[
12 (";", "SEMI"),
13 (",", "COMMA"),
14 ("(", "L_PAREN"),
15 (")", "R_PAREN"),
16 ("{", "L_CURLY"),
17 ("}", "R_CURLY"),
18 ("[", "L_BRACK"),
19 ("]", "R_BRACK"),
20 ("<", "L_ANGLE"),
21 (">", "R_ANGLE"),
22 ("@", "AT"),
23 ("#", "POUND"),
24 ("~", "TILDE"),
25 ("?", "QUESTION"),
26 ("$", "DOLLAR"),
27 ("&", "AMP"),
28 ("|", "PIPE"),
29 ("+", "PLUS"),
30 ("*", "STAR"),
31 ("/", "SLASH"),
32 ("^", "CARET"),
33 ("%", "PERCENT"),
34 ("_", "UNDERSCORE"),
35 (".", "DOT"),
36 ("..", "DOTDOT"),
37 ("...", "DOTDOTDOT"),
38 ("..=", "DOTDOTEQ"),
39 (":", "COLON"),
40 ("::", "COLONCOLON"),
41 ("=", "EQ"),
42 ("==", "EQEQ"),
43 ("=>", "FAT_ARROW"),
44 ("!", "EXCL"),
45 ("!=", "NEQ"),
46 ("-", "MINUS"),
47 ("->", "THIN_ARROW"),
48 ("<=", "LTEQ"),
49 (">=", "GTEQ"),
50 ("+=", "PLUSEQ"),
51 ("-=", "MINUSEQ"),
52 ("|=", "PIPEEQ"),
53 ("&=", "AMPEQ"),
54 ("^=", "CARETEQ"),
55 ("/=", "SLASHEQ"),
56 ("*=", "STAREQ"),
57 ("%=", "PERCENTEQ"),
58 ("&&", "AMPAMP"),
59 ("||", "PIPEPIPE"),
60 ("<<", "SHL"),
61 (">>", "SHR"),
62 ("<<=", "SHLEQ"),
63 (">>=", "SHREQ"),
64 ],
65 keywords: &[
66 "as", "async", "await", "box", "break", "const", "continue", "crate", "dyn", "else",
67 "enum", "extern", "false", "fn", "for", "if", "impl", "in", "let", "loop", "macro",
68 "match", "mod", "move", "mut", "pub", "ref", "return", "self", "static", "struct", "super",
69 "trait", "true", "try", "type", "unsafe", "use", "where", "while",
70 ],
71 contextual_keywords: &["auto", "default", "existential", "union"],
72 literals: &[
73 "INT_NUMBER",
74 "FLOAT_NUMBER",
75 "CHAR",
76 "BYTE",
77 "STRING",
78 "RAW_STRING",
79 "BYTE_STRING",
80 "RAW_BYTE_STRING",
81 ],
82 tokens: &[
83 "ERROR",
84 "IDENT",
85 "WHITESPACE",
86 "LIFETIME",
87 "COMMENT",
88 "SHEBANG",
89 "L_DOLLAR",
90 "R_DOLLAR",
91 ],
92 nodes: &[
93 "SOURCE_FILE",
94 "STRUCT_DEF",
95 "UNION_DEF",
96 "ENUM_DEF",
97 "FN_DEF",
98 "RET_TYPE",
99 "EXTERN_CRATE_ITEM",
100 "MODULE",
101 "USE_ITEM",
102 "STATIC_DEF",
103 "CONST_DEF",
104 "TRAIT_DEF",
105 "IMPL_BLOCK",
106 "TYPE_ALIAS_DEF",
107 "MACRO_CALL",
108 "TOKEN_TREE",
109 "MACRO_DEF",
110 "PAREN_TYPE",
111 "TUPLE_TYPE",
112 "NEVER_TYPE",
113 "PATH_TYPE",
114 "POINTER_TYPE",
115 "ARRAY_TYPE",
116 "SLICE_TYPE",
117 "REFERENCE_TYPE",
118 "PLACEHOLDER_TYPE",
119 "FN_POINTER_TYPE",
120 "FOR_TYPE",
121 "IMPL_TRAIT_TYPE",
122 "DYN_TRAIT_TYPE",
123 "REF_PAT",
124 "BOX_PAT",
125 "BIND_PAT",
126 "PLACEHOLDER_PAT",
127 "DOT_DOT_PAT",
128 "PATH_PAT",
129 "RECORD_PAT",
130 "RECORD_FIELD_PAT_LIST",
131 "RECORD_FIELD_PAT",
132 "TUPLE_STRUCT_PAT",
133 "TUPLE_PAT",
134 "SLICE_PAT",
135 "RANGE_PAT",
136 "LITERAL_PAT",
137 // atoms
138 "TUPLE_EXPR",
139 "ARRAY_EXPR",
140 "PAREN_EXPR",
141 "PATH_EXPR",
142 "LAMBDA_EXPR",
143 "IF_EXPR",
144 "WHILE_EXPR",
145 "CONDITION",
146 "LOOP_EXPR",
147 "FOR_EXPR",
148 "CONTINUE_EXPR",
149 "BREAK_EXPR",
150 "LABEL",
151 "BLOCK_EXPR",
152 "RETURN_EXPR",
153 "MATCH_EXPR",
154 "MATCH_ARM_LIST",
155 "MATCH_ARM",
156 "MATCH_GUARD",
157 "RECORD_LIT",
158 "RECORD_FIELD_LIST",
159 "RECORD_FIELD",
160 "TRY_BLOCK_EXPR",
161 "BOX_EXPR",
162 // postfix
163 "CALL_EXPR",
164 "INDEX_EXPR",
165 "METHOD_CALL_EXPR",
166 "FIELD_EXPR",
167 "AWAIT_EXPR",
168 "TRY_EXPR",
169 "CAST_EXPR",
170 // unary
171 "REF_EXPR",
172 "PREFIX_EXPR",
173 "RANGE_EXPR", // just weird
174 "BIN_EXPR",
175 "BLOCK",
176 "EXTERN_BLOCK",
177 "EXTERN_ITEM_LIST",
178 "ENUM_VARIANT",
179 "RECORD_FIELD_DEF_LIST",
180 "RECORD_FIELD_DEF",
181 "TUPLE_FIELD_DEF_LIST",
182 "TUPLE_FIELD_DEF",
183 "ENUM_VARIANT_LIST",
184 "ITEM_LIST",
185 "ATTR",
186 "META_ITEM", // not an item actually
187 "USE_TREE",
188 "USE_TREE_LIST",
189 "PATH",
190 "PATH_SEGMENT",
191 "LITERAL",
192 "ALIAS",
193 "VISIBILITY",
194 "WHERE_CLAUSE",
195 "WHERE_PRED",
196 "ABI",
197 "NAME",
198 "NAME_REF",
199 "LET_STMT",
200 "EXPR_STMT",
201 "TYPE_PARAM_LIST",
202 "LIFETIME_PARAM",
203 "TYPE_PARAM",
204 "CONST_PARAM",
205 "TYPE_ARG_LIST",
206 "LIFETIME_ARG",
207 "TYPE_ARG",
208 "ASSOC_TYPE_ARG",
209 "CONST_ARG",
210 "PARAM_LIST",
211 "PARAM",
212 "SELF_PARAM",
213 "ARG_LIST",
214 "TYPE_BOUND",
215 "TYPE_BOUND_LIST",
216 // macro related
217 "MACRO_ITEMS",
218 "MACRO_STMTS",
219 ],
220};
221
222pub(crate) struct AstSrc<'a> {
223 pub(crate) nodes: &'a [AstNodeSrc<'a>],
224 pub(crate) enums: &'a [AstEnumSrc<'a>],
225}
226
227pub(crate) struct AstNodeSrc<'a> {
228 pub(crate) name: &'a str,
229 pub(crate) traits: &'a [&'a str],
230 pub(crate) fields: &'a [(&'a str, FieldSrc<&'a str>)],
231}
232
233pub(crate) enum FieldSrc<T> {
234 Shorthand,
235 Optional(T),
236 Many(T),
237}
238
239pub(crate) struct AstEnumSrc<'a> {
240 pub(crate) name: &'a str,
241 pub(crate) traits: &'a [&'a str],
242 pub(crate) variants: &'a [&'a str],
243}
244
245macro_rules! ast_nodes {
246 ($(
247 struct $name:ident$(: $($trait:ident),*)? {
248 $($field_name:ident $(: $ty:tt)?),*$(,)?
249 }
250 )*) => {
251 [$(
252 AstNodeSrc {
253 name: stringify!($name),
254 traits: &[$($(stringify!($trait)),*)?],
255 fields: &[$(
256 (stringify!($field_name), field_ty!($field_name $($ty)?))
257 ),*],
258
259 }
260 ),*]
261 };
262}
263
264macro_rules! field_ty {
265 ($field_name:ident) => {
266 FieldSrc::Shorthand
267 };
268 ($field_name:ident [$ty:ident]) => {
269 FieldSrc::Many(stringify!($ty))
270 };
271 ($field_name:ident $ty:ident) => {
272 FieldSrc::Optional(stringify!($ty))
273 };
274}
275
276macro_rules! ast_enums {
277 ($(
278 enum $name:ident $(: $($trait:ident),*)? {
279 $($variant:ident),*$(,)?
280 }
281 )*) => {
282 [$(
283 AstEnumSrc {
284 name: stringify!($name),
285 traits: &[$($(stringify!($trait)),*)?],
286 variants: &[$(stringify!($variant)),*],
287
288 }
289 ),*]
290 };
291}
292
293pub(crate) const AST_SRC: AstSrc = AstSrc {
294 nodes: &ast_nodes! {
295 struct SourceFile: ModuleItemOwner, FnDefOwner {
296 modules: [Module],
297 }
298
299 struct FnDef: VisibilityOwner, NameOwner, TypeParamsOwner, DocCommentsOwner, AttrsOwner {
300 ParamList,
301 RetType,
302 body: BlockExpr,
303 }
304
305 struct RetType { TypeRef }
306
307 struct StructDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner {
308 }
309
310 struct UnionDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner {
311 RecordFieldDefList,
312 }
313
314 struct RecordFieldDefList { fields: [RecordFieldDef] }
315 struct RecordFieldDef: VisibilityOwner, NameOwner, AttrsOwner, DocCommentsOwner, TypeAscriptionOwner { }
316
317 struct TupleFieldDefList { fields: [TupleFieldDef] }
318 struct TupleFieldDef: VisibilityOwner, AttrsOwner {
319 TypeRef,
320 }
321
322 struct EnumDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner {
323 variant_list: EnumVariantList,
324 }
325 struct EnumVariantList {
326 variants: [EnumVariant],
327 }
328 struct EnumVariant: NameOwner, DocCommentsOwner, AttrsOwner {
329 Expr
330 }
331
332 struct TraitDef: VisibilityOwner, NameOwner, AttrsOwner, DocCommentsOwner, TypeParamsOwner, TypeBoundsOwner {
333 ItemList,
334 }
335
336 struct Module: VisibilityOwner, NameOwner, AttrsOwner, DocCommentsOwner {
337 ItemList,
338 }
339
340 struct ItemList: FnDefOwner, ModuleItemOwner {
341 impl_items: [ImplItem],
342 }
343
344 struct ConstDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner, TypeAscriptionOwner {
345 body: Expr,
346 }
347
348 struct StaticDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner, TypeAscriptionOwner {
349 body: Expr,
350 }
351
352 struct TypeAliasDef: VisibilityOwner, NameOwner, TypeParamsOwner, AttrsOwner, DocCommentsOwner, TypeBoundsOwner {
353 TypeRef,
354 }
355
356 struct ImplBlock: TypeParamsOwner, AttrsOwner {
357 ItemList,
358 }
359
360 struct ParenType { TypeRef }
361 struct TupleType { fields: [TypeRef] }
362 struct NeverType { }
363 struct PathType { Path }
364 struct PointerType { TypeRef }
365 struct ArrayType { TypeRef, Expr }
366 struct SliceType { TypeRef }
367 struct ReferenceType { TypeRef }
368 struct PlaceholderType { }
369 struct FnPointerType { ParamList, RetType }
370 struct ForType { TypeRef }
371 struct ImplTraitType: TypeBoundsOwner {}
372 struct DynTraitType: TypeBoundsOwner {}
373
374 struct TupleExpr { exprs: [Expr] }
375 struct ArrayExpr { exprs: [Expr] }
376 struct ParenExpr { Expr }
377 struct PathExpr { Path }
378 struct LambdaExpr {
379 ParamList,
380 RetType,
381 body: Expr,
382 }
383 struct IfExpr { Condition }
384 struct LoopExpr: LoopBodyOwner { }
385 struct TryBlockExpr { body: BlockExpr }
386 struct ForExpr: LoopBodyOwner {
387 Pat,
388 iterable: Expr,
389 }
390 struct WhileExpr: LoopBodyOwner { Condition }
391 struct ContinueExpr {}
392 struct BreakExpr { Expr }
393 struct Label {}
394 struct BlockExpr { Block }
395 struct ReturnExpr { Expr }
396 struct CallExpr: ArgListOwner { Expr }
397 struct MethodCallExpr: ArgListOwner {
398 Expr, NameRef, TypeArgList,
399 }
400 struct IndexExpr {}
401 struct FieldExpr { Expr, NameRef }
402 struct AwaitExpr { Expr }
403 struct TryExpr { Expr }
404 struct CastExpr { Expr, TypeRef }
405 struct RefExpr { Expr }
406 struct PrefixExpr { Expr }
407 struct BoxExpr { Expr }
408 struct RangeExpr {}
409 struct BinExpr {}
410 struct Literal {}
411
412 struct MatchExpr { Expr, MatchArmList }
413 struct MatchArmList: AttrsOwner { arms: [MatchArm] }
414 struct MatchArm: AttrsOwner {
415 pats: [Pat],
416 guard: MatchGuard,
417 Expr,
418 }
419 struct MatchGuard { Expr }
420
421 struct RecordLit { Path, RecordFieldList }
422 struct RecordFieldList {
423 fields: [RecordField],
424 spread: Expr,
425 }
426 struct RecordField { NameRef, Expr }
427
428 struct RefPat { Pat }
429 struct BoxPat { Pat }
430 struct BindPat: NameOwner { Pat }
431 struct PlaceholderPat { }
432 struct DotDotPat { }
433 struct PathPat { Path }
434 struct SlicePat {}
435 struct RangePat {}
436 struct LiteralPat { Literal }
437
438 struct RecordPat { RecordFieldPatList, Path }
439 struct RecordFieldPatList {
440 record_field_pats: [RecordFieldPat],
441 bind_pats: [BindPat],
442 }
443 struct RecordFieldPat: NameOwner { Pat }
444
445 struct TupleStructPat { Path, args: [Pat] }
446 struct TuplePat { args: [Pat] }
447
448 struct Visibility {}
449 struct Name {}
450 struct NameRef {}
451
452 struct MacroCall: NameOwner, AttrsOwner,DocCommentsOwner {
453 TokenTree, Path
454 }
455 struct Attr { Path, input: AttrInput }
456 struct TokenTree {}
457 struct TypeParamList {
458 type_params: [TypeParam],
459 lifetime_params: [LifetimeParam],
460 }
461 struct TypeParam: NameOwner, AttrsOwner, TypeBoundsOwner {
462 default_type: TypeRef,
463 }
464 struct ConstParam: NameOwner, AttrsOwner, TypeAscriptionOwner {
465 default_val: Expr,
466 }
467 struct LifetimeParam: AttrsOwner { }
468 struct TypeBound { TypeRef}
469 struct TypeBoundList { bounds: [TypeBound] }
470 struct WherePred: TypeBoundsOwner { TypeRef }
471 struct WhereClause { predicates: [WherePred] }
472 struct ExprStmt { Expr }
473 struct LetStmt: TypeAscriptionOwner {
474 Pat,
475 initializer: Expr,
476 }
477 struct Condition { Pat, Expr }
478 struct Block: AttrsOwner, ModuleItemOwner {
479 statements: [Stmt],
480 Expr,
481 }
482 struct ParamList {
483 SelfParam,
484 params: [Param],
485 }
486 struct SelfParam: TypeAscriptionOwner, AttrsOwner { }
487 struct Param: TypeAscriptionOwner, AttrsOwner {
488 Pat,
489 }
490 struct UseItem: AttrsOwner, VisibilityOwner {
491 UseTree,
492 }
493 struct UseTree {
494 Path, UseTreeList, Alias
495 }
496 struct Alias: NameOwner { }
497 struct UseTreeList { use_trees: [UseTree] }
498 struct ExternCrateItem: AttrsOwner, VisibilityOwner {
499 NameRef, Alias,
500 }
501 struct ArgList {
502 args: [Expr],
503 }
504 struct Path {
505 segment: PathSegment,
506 qualifier: Path,
507 }
508 struct PathSegment {
509 NameRef, TypeArgList, ParamList, RetType, PathType,
510 }
511 struct TypeArgList {
512 type_args: [TypeArg],
513 lifetime_args: [LifetimeArg],
514 assoc_type_args: [AssocTypeArg],
515 const_arg: [ConstArg],
516 }
517 struct TypeArg { TypeRef }
518 struct AssocTypeArg { NameRef, TypeRef }
519 struct LifetimeArg {}
520 struct ConstArg { Literal, BlockExpr }
521
522 struct MacroItems: ModuleItemOwner, FnDefOwner { }
523
524 struct MacroStmts {
525 statements: [Stmt],
526 Expr,
527 }
528 },
529 enums: &ast_enums! {
530 enum NominalDef: NameOwner, TypeParamsOwner, AttrsOwner {
531 StructDef, EnumDef, UnionDef,
532 }
533
534 enum TypeRef {
535 ParenType,
536 TupleType,
537 NeverType,
538 PathType,
539 PointerType,
540 ArrayType,
541 SliceType,
542 ReferenceType,
543 PlaceholderType,
544 FnPointerType,
545 ForType,
546 ImplTraitType,
547 DynTraitType,
548 }
549
550 enum ModuleItem: AttrsOwner, VisibilityOwner {
551 StructDef,
552 UnionDef,
553 EnumDef,
554 FnDef,
555 TraitDef,
556 TypeAliasDef,
557 ImplBlock,
558 UseItem,
559 ExternCrateItem,
560 ConstDef,
561 StaticDef,
562 Module,
563 }
564
565 enum ImplItem: AttrsOwner {
566 FnDef, TypeAliasDef, ConstDef,
567 }
568
569 enum Expr {
570 TupleExpr,
571 ArrayExpr,
572 ParenExpr,
573 PathExpr,
574 LambdaExpr,
575 IfExpr,
576 LoopExpr,
577 ForExpr,
578 WhileExpr,
579 ContinueExpr,
580 BreakExpr,
581 Label,
582 BlockExpr,
583 ReturnExpr,
584 MatchExpr,
585 RecordLit,
586 CallExpr,
587 IndexExpr,
588 MethodCallExpr,
589 FieldExpr,
590 AwaitExpr,
591 TryExpr,
592 TryBlockExpr,
593 CastExpr,
594 RefExpr,
595 PrefixExpr,
596 RangeExpr,
597 BinExpr,
598 Literal,
599 MacroCall,
600 BoxExpr,
601 }
602
603 enum Pat {
604 RefPat,
605 BoxPat,
606 BindPat,
607 PlaceholderPat,
608 DotDotPat,
609 PathPat,
610 RecordPat,
611 TupleStructPat,
612 TuplePat,
613 SlicePat,
614 RangePat,
615 LiteralPat,
616 }
617
618 enum AttrInput { Literal, TokenTree }
619 enum Stmt { ExprStmt, LetStmt }
620 },
621};
diff --git a/xtask/src/boilerplate_gen.rs b/xtask/src/boilerplate_gen.rs
deleted file mode 100644
index e69de29bb..000000000
--- a/xtask/src/boilerplate_gen.rs
+++ /dev/null
diff --git a/xtask/src/cmd.rs b/xtask/src/cmd.rs
new file mode 100644
index 000000000..2027f4893
--- /dev/null
+++ b/xtask/src/cmd.rs
@@ -0,0 +1,53 @@
1use std::process::{Command, Output, Stdio};
2
3use anyhow::{Context, Result};
4
5use crate::project_root;
6
7pub struct Cmd<'a> {
8 pub unix: &'a str,
9 pub windows: &'a str,
10 pub work_dir: &'a str,
11}
12
13impl Cmd<'_> {
14 pub fn run(self) -> Result<()> {
15 if cfg!(windows) {
16 run(self.windows, self.work_dir)
17 } else {
18 run(self.unix, self.work_dir)
19 }
20 }
21 pub fn run_with_output(self) -> Result<Output> {
22 if cfg!(windows) {
23 run_with_output(self.windows, self.work_dir)
24 } else {
25 run_with_output(self.unix, self.work_dir)
26 }
27 }
28}
29
30pub fn run(cmdline: &str, dir: &str) -> Result<()> {
31 do_run(cmdline, dir, &mut |c| {
32 c.stdout(Stdio::inherit());
33 })
34 .map(|_| ())
35}
36
37pub fn run_with_output(cmdline: &str, dir: &str) -> Result<Output> {
38 do_run(cmdline, dir, &mut |_| {})
39}
40
41fn do_run(cmdline: &str, dir: &str, f: &mut dyn FnMut(&mut Command)) -> Result<Output> {
42 eprintln!("\nwill run: {}", cmdline);
43 let proj_dir = project_root().join(dir);
44 let mut args = cmdline.split_whitespace();
45 let exec = args.next().unwrap();
46 let mut cmd = Command::new(exec);
47 f(cmd.args(args).current_dir(proj_dir).stderr(Stdio::inherit()));
48 let output = cmd.output().with_context(|| format!("running `{}`", cmdline))?;
49 if !output.status.success() {
50 anyhow::bail!("`{}` exited with {}", cmdline, output.status);
51 }
52 Ok(output)
53}
diff --git a/xtask/src/codegen.rs b/xtask/src/codegen.rs
index 53f524f42..158cfc2d6 100644
--- a/xtask/src/codegen.rs
+++ b/xtask/src/codegen.rs
@@ -24,7 +24,6 @@ pub use self::{
24 gen_syntax::generate_syntax, 24 gen_syntax::generate_syntax,
25}; 25};
26 26
27pub const GRAMMAR: &str = "crates/ra_syntax/src/grammar.ron";
28const GRAMMAR_DIR: &str = "crates/ra_parser/src/grammar"; 27const GRAMMAR_DIR: &str = "crates/ra_parser/src/grammar";
29const OK_INLINE_TESTS_DIR: &str = "crates/ra_syntax/test_data/parser/inline/ok"; 28const OK_INLINE_TESTS_DIR: &str = "crates/ra_syntax/test_data/parser/inline/ok";
30const ERR_INLINE_TESTS_DIR: &str = "crates/ra_syntax/test_data/parser/inline/err"; 29const ERR_INLINE_TESTS_DIR: &str = "crates/ra_syntax/test_data/parser/inline/err";
diff --git a/xtask/src/codegen/gen_syntax.rs b/xtask/src/codegen/gen_syntax.rs
index 88f2ac0e3..0f50ca569 100644
--- a/xtask/src/codegen/gen_syntax.rs
+++ b/xtask/src/codegen/gen_syntax.rs
@@ -3,149 +3,142 @@
3//! Specifically, it generates the `SyntaxKind` enum and a number of newtype 3//! Specifically, it generates the `SyntaxKind` enum and a number of newtype
4//! wrappers around `SyntaxNode` which implement `ra_syntax::AstNode`. 4//! wrappers around `SyntaxNode` which implement `ra_syntax::AstNode`.
5 5
6use std::{collections::BTreeMap, fs};
7
8use proc_macro2::{Punct, Spacing}; 6use proc_macro2::{Punct, Spacing};
9use quote::{format_ident, quote}; 7use quote::{format_ident, quote};
10use ron;
11use serde::Deserialize;
12 8
13use crate::{ 9use crate::{
10 ast_src::{AstSrc, FieldSrc, KindsSrc, AST_SRC, KINDS_SRC},
14 codegen::{self, update, Mode}, 11 codegen::{self, update, Mode},
15 project_root, Result, 12 project_root, Result,
16}; 13};
17 14
18pub fn generate_syntax(mode: Mode) -> Result<()> { 15pub fn generate_syntax(mode: Mode) -> Result<()> {
19 let grammar = project_root().join(codegen::GRAMMAR);
20 let grammar: Grammar = {
21 let text = fs::read_to_string(grammar)?;
22 ron::de::from_str(&text)?
23 };
24
25 let syntax_kinds_file = project_root().join(codegen::SYNTAX_KINDS); 16 let syntax_kinds_file = project_root().join(codegen::SYNTAX_KINDS);
26 let syntax_kinds = generate_syntax_kinds(&grammar)?; 17 let syntax_kinds = generate_syntax_kinds(KINDS_SRC)?;
27 update(syntax_kinds_file.as_path(), &syntax_kinds, mode)?; 18 update(syntax_kinds_file.as_path(), &syntax_kinds, mode)?;
28 19
29 let ast_file = project_root().join(codegen::AST); 20 let ast_file = project_root().join(codegen::AST);
30 let ast = generate_ast(&grammar)?; 21 let ast = generate_ast(AST_SRC)?;
31 update(ast_file.as_path(), &ast, mode)?; 22 update(ast_file.as_path(), &ast, mode)?;
32 23
33 Ok(()) 24 Ok(())
34} 25}
35 26
36fn generate_ast(grammar: &Grammar) -> Result<String> { 27fn generate_ast(grammar: AstSrc<'_>) -> Result<String> {
37 let nodes = grammar.ast.iter().map(|(name, ast_node)| { 28 let nodes = grammar.nodes.iter().map(|node| {
38 let variants = 29 let name = format_ident!("{}", node.name);
39 ast_node.variants.iter().map(|var| format_ident!("{}", var)).collect::<Vec<_>>(); 30 let kind = format_ident!("{}", to_upper_snake_case(&name.to_string()));
40 let name = format_ident!("{}", name); 31 let traits = node.traits.iter().map(|trait_name| {
41 32 let trait_name = format_ident!("{}", trait_name);
42 let adt = if variants.is_empty() { 33 quote!(impl ast::#trait_name for #name {})
43 let kind = format_ident!("{}", to_upper_snake_case(&name.to_string())); 34 });
44 quote! {
45 #[derive(Debug, Clone, PartialEq, Eq, Hash)]
46 pub struct #name {
47 pub(crate) syntax: SyntaxNode,
48 }
49 35
50 impl AstNode for #name { 36 let methods = node.fields.iter().map(|(name, field)| {
51 fn can_cast(kind: SyntaxKind) -> bool { 37 let method_name = match field {
52 match kind { 38 FieldSrc::Shorthand => format_ident!("{}", to_lower_snake_case(&name)),
53 #kind => true, 39 _ => format_ident!("{}", name),
54 _ => false, 40 };
41 let ty = match field {
42 FieldSrc::Optional(ty) | FieldSrc::Many(ty) => ty,
43 FieldSrc::Shorthand => name,
44 };
45 let ty = format_ident!("{}", ty);
46
47 match field {
48 FieldSrc::Many(_) => {
49 quote! {
50 pub fn #method_name(&self) -> AstChildren<#ty> {
51 AstChildren::new(&self.syntax)
55 } 52 }
56 } 53 }
57 fn cast(syntax: SyntaxNode) -> Option<Self> { 54 }
58 if Self::can_cast(syntax.kind()) { Some(Self { syntax }) } else { None } 55 FieldSrc::Optional(_) | FieldSrc::Shorthand => {
56 quote! {
57 pub fn #method_name(&self) -> Option<#ty> {
58 AstChildren::new(&self.syntax).next()
59 }
59 } 60 }
60 fn syntax(&self) -> &SyntaxNode { &self.syntax }
61 } 61 }
62 } 62 }
63 } else { 63 });
64 let kinds = variants
65 .iter()
66 .map(|name| format_ident!("{}", to_upper_snake_case(&name.to_string())))
67 .collect::<Vec<_>>();
68
69 quote! {
70 #[derive(Debug, Clone, PartialEq, Eq, Hash)]
71 pub enum #name {
72 #(#variants(#variants),)*
73 }
74 64
75 #( 65 quote! {
76 impl From<#variants> for #name { 66 #[derive(Debug, Clone, PartialEq, Eq, Hash)]
77 fn from(node: #variants) -> #name { 67 pub struct #name {
78 #name::#variants(node) 68 pub(crate) syntax: SyntaxNode,
79 } 69 }
80 }
81 )*
82 70
83 impl AstNode for #name { 71 impl AstNode for #name {
84 fn can_cast(kind: SyntaxKind) -> bool { 72 fn can_cast(kind: SyntaxKind) -> bool {
85 match kind { 73 match kind {
86 #(#kinds)|* => true, 74 #kind => true,
87 _ => false, 75 _ => false,
88 }
89 }
90 fn cast(syntax: SyntaxNode) -> Option<Self> {
91 let res = match syntax.kind() {
92 #(
93 #kinds => #name::#variants(#variants { syntax }),
94 )*
95 _ => return None,
96 };
97 Some(res)
98 }
99 fn syntax(&self) -> &SyntaxNode {
100 match self {
101 #(
102 #name::#variants(it) => &it.syntax,
103 )*
104 }
105 } 76 }
106 } 77 }
78 fn cast(syntax: SyntaxNode) -> Option<Self> {
79 if Self::can_cast(syntax.kind()) { Some(Self { syntax }) } else { None }
80 }
81 fn syntax(&self) -> &SyntaxNode { &self.syntax }
107 } 82 }
108 }; 83 #(#traits)*
84
85 impl #name {
86 #(#methods)*
87 }
88 }
89 });
109 90
110 let traits = ast_node.traits.iter().map(|trait_name| { 91 let enums = grammar.enums.iter().map(|en| {
92 let variants = en.variants.iter().map(|var| format_ident!("{}", var)).collect::<Vec<_>>();
93 let name = format_ident!("{}", en.name);
94 let kinds = variants
95 .iter()
96 .map(|name| format_ident!("{}", to_upper_snake_case(&name.to_string())))
97 .collect::<Vec<_>>();
98 let traits = en.traits.iter().map(|trait_name| {
111 let trait_name = format_ident!("{}", trait_name); 99 let trait_name = format_ident!("{}", trait_name);
112 quote!(impl ast::#trait_name for #name {}) 100 quote!(impl ast::#trait_name for #name {})
113 }); 101 });
114 102
115 let collections = ast_node.collections.iter().map(|(name, kind)| { 103 quote! {
116 let method_name = format_ident!("{}", name); 104 #[derive(Debug, Clone, PartialEq, Eq, Hash)]
117 let kind = format_ident!("{}", kind); 105 pub enum #name {
118 quote! { 106 #(#variants(#variants),)*
119 pub fn #method_name(&self) -> AstChildren<#kind> {
120 AstChildren::new(&self.syntax)
121 }
122 } 107 }
123 });
124 108
125 let options = ast_node.options.iter().map(|attr| { 109 #(
126 let method_name = match attr { 110 impl From<#variants> for #name {
127 Attr::Type(t) => format_ident!("{}", to_lower_snake_case(&t)), 111 fn from(node: #variants) -> #name {
128 Attr::NameType(n, _) => format_ident!("{}", n), 112 #name::#variants(node)
129 };
130 let ty = match attr {
131 Attr::Type(t) | Attr::NameType(_, t) => format_ident!("{}", t),
132 };
133 quote! {
134 pub fn #method_name(&self) -> Option<#ty> {
135 AstChildren::new(&self.syntax).next()
136 } 113 }
137 } 114 }
138 }); 115 )*
139
140 quote! {
141 #adt
142
143 #(#traits)*
144 116
145 impl #name { 117 impl AstNode for #name {
146 #(#collections)* 118 fn can_cast(kind: SyntaxKind) -> bool {
147 #(#options)* 119 match kind {
120 #(#kinds)|* => true,
121 _ => false,
122 }
123 }
124 fn cast(syntax: SyntaxNode) -> Option<Self> {
125 let res = match syntax.kind() {
126 #(
127 #kinds => #name::#variants(#variants { syntax }),
128 )*
129 _ => return None,
130 };
131 Some(res)
132 }
133 fn syntax(&self) -> &SyntaxNode {
134 match self {
135 #(
136 #name::#variants(it) => &it.syntax,
137 )*
138 }
139 }
148 } 140 }
141 #(#traits)*
149 } 142 }
150 }); 143 });
151 144
@@ -156,13 +149,14 @@ fn generate_ast(grammar: &Grammar) -> Result<String> {
156 }; 149 };
157 150
158 #(#nodes)* 151 #(#nodes)*
152 #(#enums)*
159 }; 153 };
160 154
161 let pretty = codegen::reformat(ast)?; 155 let pretty = codegen::reformat(ast)?;
162 Ok(pretty) 156 Ok(pretty)
163} 157}
164 158
165fn generate_syntax_kinds(grammar: &Grammar) -> Result<String> { 159fn generate_syntax_kinds(grammar: KindsSrc<'_>) -> Result<String> {
166 let (single_byte_tokens_values, single_byte_tokens): (Vec<_>, Vec<_>) = grammar 160 let (single_byte_tokens_values, single_byte_tokens): (Vec<_>, Vec<_>) = grammar
167 .punct 161 .punct
168 .iter() 162 .iter()
@@ -274,38 +268,6 @@ fn generate_syntax_kinds(grammar: &Grammar) -> Result<String> {
274 codegen::reformat(ast) 268 codegen::reformat(ast)
275} 269}
276 270
277#[derive(Deserialize, Debug)]
278struct Grammar {
279 punct: Vec<(String, String)>,
280 keywords: Vec<String>,
281 contextual_keywords: Vec<String>,
282 literals: Vec<String>,
283 tokens: Vec<String>,
284 nodes: Vec<String>,
285 ast: BTreeMap<String, AstNode>,
286}
287
288#[derive(Deserialize, Debug)]
289struct AstNode {
290 #[serde(default)]
291 #[serde(rename = "enum")]
292 variants: Vec<String>,
293
294 #[serde(default)]
295 traits: Vec<String>,
296 #[serde(default)]
297 collections: Vec<(String, String)>,
298 #[serde(default)]
299 options: Vec<Attr>,
300}
301
302#[derive(Deserialize, Debug)]
303#[serde(untagged)]
304enum Attr {
305 Type(String),
306 NameType(String, String),
307}
308
309fn to_upper_snake_case(s: &str) -> String { 271fn to_upper_snake_case(s: &str) -> String {
310 let mut buf = String::with_capacity(s.len()); 272 let mut buf = String::with_capacity(s.len());
311 let mut prev_is_upper = None; 273 let mut prev_is_upper = None;
diff --git a/xtask/src/help.rs b/xtask/src/help.rs
deleted file mode 100644
index f4e25dcde..000000000
--- a/xtask/src/help.rs
+++ /dev/null
@@ -1,46 +0,0 @@
1//! FIXME: write short doc here
2
3pub const GLOBAL_HELP: &str = "tasks
4
5USAGE:
6 ra_tools <SUBCOMMAND>
7
8FLAGS:
9 -h, --help Prints help information
10
11SUBCOMMANDS:
12 format
13 install-pre-commit-hook
14 fuzz-tests
15 codegen
16 install
17 lint";
18
19pub const INSTALL_HELP: &str = "ra_tools-install
20
21USAGE:
22 ra_tools.exe install [FLAGS]
23
24FLAGS:
25 --client-code
26 -h, --help Prints help information
27 --jemalloc
28 --server";
29
30pub fn print_no_param_subcommand_help(subcommand: &str) {
31 eprintln!(
32 "ra_tools-{}
33
34USAGE:
35 ra_tools {}
36
37FLAGS:
38 -h, --help Prints help information",
39 subcommand, subcommand
40 );
41}
42
43pub const INSTALL_RA_CONFLICT: &str =
44 "error: The argument `--server` cannot be used with `--client-code`
45
46For more information try --help";
diff --git a/xtask/src/install.rs b/xtask/src/install.rs
new file mode 100644
index 000000000..fa82633de
--- /dev/null
+++ b/xtask/src/install.rs
@@ -0,0 +1,178 @@
1//! Installs rust-analyzer language server and/or editor plugin.
2
3use std::{env, path::PathBuf, str};
4
5use anyhow::{Context, Result};
6
7use crate::cmd::{run, run_with_output, Cmd};
8
9// Latest stable, feel free to send a PR if this lags behind.
10const REQUIRED_RUST_VERSION: u32 = 40;
11
12pub struct InstallCmd {
13 pub client: Option<ClientOpt>,
14 pub server: Option<ServerOpt>,
15}
16
17pub enum ClientOpt {
18 VsCode,
19}
20
21pub struct ServerOpt {
22 pub jemalloc: bool,
23}
24
25impl InstallCmd {
26 pub fn run(self) -> Result<()> {
27 if cfg!(target_os = "macos") {
28 fix_path_for_mac().context("Fix path for mac")?
29 }
30 if let Some(server) = self.server {
31 install_server(server).context("install server")?;
32 }
33 if let Some(client) = self.client {
34 install_client(client).context("install client")?;
35 }
36 Ok(())
37 }
38}
39
40fn fix_path_for_mac() -> Result<()> {
41 let mut vscode_path: Vec<PathBuf> = {
42 const COMMON_APP_PATH: &str =
43 r"/Applications/Visual Studio Code.app/Contents/Resources/app/bin";
44 const ROOT_DIR: &str = "";
45 let home_dir = match env::var("HOME") {
46 Ok(home) => home,
47 Err(e) => anyhow::bail!("Failed getting HOME from environment with error: {}.", e),
48 };
49
50 [ROOT_DIR, &home_dir]
51 .iter()
52 .map(|dir| String::from(*dir) + COMMON_APP_PATH)
53 .map(PathBuf::from)
54 .filter(|path| path.exists())
55 .collect()
56 };
57
58 if !vscode_path.is_empty() {
59 let vars = match env::var_os("PATH") {
60 Some(path) => path,
61 None => anyhow::bail!("Could not get PATH variable from env."),
62 };
63
64 let mut paths = env::split_paths(&vars).collect::<Vec<_>>();
65 paths.append(&mut vscode_path);
66 let new_paths = env::join_paths(paths).context("build env PATH")?;
67 env::set_var("PATH", &new_paths);
68 }
69
70 Ok(())
71}
72
73fn install_client(ClientOpt::VsCode: ClientOpt) -> Result<()> {
74 let npm_version = Cmd {
75 unix: r"npm --version",
76 windows: r"cmd.exe /c npm --version",
77 work_dir: "./editors/code",
78 }
79 .run();
80
81 if npm_version.is_err() {
82 eprintln!("\nERROR: `npm --version` failed, `npm` is required to build the VS Code plugin")
83 }
84
85 Cmd { unix: r"npm install", windows: r"cmd.exe /c npm install", work_dir: "./editors/code" }
86 .run()?;
87 Cmd {
88 unix: r"npm run package --scripts-prepend-node-path",
89 windows: r"cmd.exe /c npm run package",
90 work_dir: "./editors/code",
91 }
92 .run()?;
93
94 let code_binary = ["code", "code-insiders", "codium", "code-oss"].iter().find(|bin| {
95 Cmd {
96 unix: &format!("{} --version", bin),
97 windows: &format!("cmd.exe /c {}.cmd --version", bin),
98 work_dir: "./editors/code",
99 }
100 .run()
101 .is_ok()
102 });
103
104 let code_binary = match code_binary {
105 Some(it) => it,
106 None => anyhow::bail!("Can't execute `code --version`. Perhaps it is not in $PATH?"),
107 };
108
109 Cmd {
110 unix: &format!(r"{} --install-extension ./ra-lsp-0.0.1.vsix --force", code_binary),
111 windows: &format!(
112 r"cmd.exe /c {}.cmd --install-extension ./ra-lsp-0.0.1.vsix --force",
113 code_binary
114 ),
115 work_dir: "./editors/code",
116 }
117 .run()?;
118
119 let output = Cmd {
120 unix: &format!(r"{} --list-extensions", code_binary),
121 windows: &format!(r"cmd.exe /c {}.cmd --list-extensions", code_binary),
122 work_dir: ".",
123 }
124 .run_with_output()?;
125
126 if !str::from_utf8(&output.stdout)?.contains("ra-lsp") {
127 anyhow::bail!(
128 "Could not install the Visual Studio Code extension. \
129 Please make sure you have at least NodeJS 10.x together with the latest version of VS Code installed and try again."
130 );
131 }
132
133 Ok(())
134}
135
136fn install_server(opts: ServerOpt) -> Result<()> {
137 let mut old_rust = false;
138 if let Ok(output) = run_with_output("cargo --version", ".") {
139 if let Ok(stdout) = String::from_utf8(output.stdout) {
140 println!("{}", stdout);
141 if !check_version(&stdout, REQUIRED_RUST_VERSION) {
142 old_rust = true;
143 }
144 }
145 }
146
147 if old_rust {
148 eprintln!(
149 "\nWARNING: at least rust 1.{}.0 is required to compile rust-analyzer\n",
150 REQUIRED_RUST_VERSION,
151 )
152 }
153
154 let res = if opts.jemalloc {
155 run("cargo install --path crates/ra_lsp_server --locked --force --features jemalloc", ".")
156 } else {
157 run("cargo install --path crates/ra_lsp_server --locked --force", ".")
158 };
159
160 if res.is_err() && old_rust {
161 eprintln!(
162 "\nWARNING: at least rust 1.{}.0 is required to compile rust-analyzer\n",
163 REQUIRED_RUST_VERSION,
164 )
165 }
166
167 res
168}
169
170fn check_version(version_output: &str, min_minor_version: u32) -> bool {
171 // Parse second the number out of
172 // cargo 1.39.0-beta (1c6ec66d5 2019-09-30)
173 let minor: Option<u32> = version_output.split('.').nth(1).and_then(|it| it.parse().ok());
174 match minor {
175 None => true,
176 Some(minor) => minor >= min_minor_version,
177 }
178}
diff --git a/xtask/src/lib.rs b/xtask/src/lib.rs
index 40a6682be..e46c21db7 100644
--- a/xtask/src/lib.rs
+++ b/xtask/src/lib.rs
@@ -1,17 +1,22 @@
1//! FIXME: write short doc here 1//! FIXME: write short doc here
2 2
3mod cmd;
4pub mod install;
5pub mod pre_commit;
6
3pub mod codegen; 7pub mod codegen;
8mod ast_src;
4 9
5use anyhow::Context; 10use anyhow::Context;
6pub use anyhow::Result;
7use std::{ 11use std::{
8 env, fs, 12 env, fs,
9 io::{Error as IoError, ErrorKind},
10 path::{Path, PathBuf}, 13 path::{Path, PathBuf},
11 process::{Command, Output, Stdio}, 14 process::{Command, Stdio},
12}; 15};
13 16
14use crate::codegen::Mode; 17use crate::{cmd::run, codegen::Mode};
18
19pub use anyhow::Result;
15 20
16const TOOLCHAIN: &str = "stable"; 21const TOOLCHAIN: &str = "stable";
17 22
@@ -25,40 +30,6 @@ pub fn project_root() -> PathBuf {
25 .to_path_buf() 30 .to_path_buf()
26} 31}
27 32
28pub struct Cmd<'a> {
29 pub unix: &'a str,
30 pub windows: &'a str,
31 pub work_dir: &'a str,
32}
33
34impl Cmd<'_> {
35 pub fn run(self) -> Result<()> {
36 if cfg!(windows) {
37 run(self.windows, self.work_dir)
38 } else {
39 run(self.unix, self.work_dir)
40 }
41 }
42 pub fn run_with_output(self) -> Result<Output> {
43 if cfg!(windows) {
44 run_with_output(self.windows, self.work_dir)
45 } else {
46 run_with_output(self.unix, self.work_dir)
47 }
48 }
49}
50
51pub fn run(cmdline: &str, dir: &str) -> Result<()> {
52 do_run(cmdline, dir, |c| {
53 c.stdout(Stdio::inherit());
54 })
55 .map(|_| ())
56}
57
58pub fn run_with_output(cmdline: &str, dir: &str) -> Result<Output> {
59 do_run(cmdline, dir, |_| {})
60}
61
62pub fn run_rustfmt(mode: Mode) -> Result<()> { 33pub fn run_rustfmt(mode: Mode) -> Result<()> {
63 match Command::new("rustup") 34 match Command::new("rustup")
64 .args(&["run", TOOLCHAIN, "--", "cargo", "fmt", "--version"]) 35 .args(&["run", TOOLCHAIN, "--", "cargo", "fmt", "--version"])
@@ -78,23 +49,11 @@ pub fn run_rustfmt(mode: Mode) -> Result<()> {
78 Ok(()) 49 Ok(())
79} 50}
80 51
81pub fn install_rustfmt() -> Result<()> { 52fn install_rustfmt() -> Result<()> {
82 run(&format!("rustup toolchain install {}", TOOLCHAIN), ".")?; 53 run(&format!("rustup toolchain install {}", TOOLCHAIN), ".")?;
83 run(&format!("rustup component add rustfmt --toolchain {}", TOOLCHAIN), ".") 54 run(&format!("rustup component add rustfmt --toolchain {}", TOOLCHAIN), ".")
84} 55}
85 56
86pub fn install_pre_commit_hook() -> Result<()> {
87 let result_path =
88 PathBuf::from(format!("./.git/hooks/pre-commit{}", std::env::consts::EXE_SUFFIX));
89 if !result_path.exists() {
90 let me = std::env::current_exe()?;
91 fs::copy(me, result_path)?;
92 } else {
93 Err(IoError::new(ErrorKind::AlreadyExists, "Git hook already created"))?;
94 }
95 Ok(())
96}
97
98pub fn run_clippy() -> Result<()> { 57pub fn run_clippy() -> Result<()> {
99 match Command::new("rustup") 58 match Command::new("rustup")
100 .args(&["run", TOOLCHAIN, "--", "cargo", "clippy", "--version"]) 59 .args(&["run", TOOLCHAIN, "--", "cargo", "clippy", "--version"])
@@ -124,7 +83,7 @@ pub fn run_clippy() -> Result<()> {
124 Ok(()) 83 Ok(())
125} 84}
126 85
127pub fn install_clippy() -> Result<()> { 86fn install_clippy() -> Result<()> {
128 run(&format!("rustup toolchain install {}", TOOLCHAIN), ".")?; 87 run(&format!("rustup toolchain install {}", TOOLCHAIN), ".")?;
129 run(&format!("rustup component add clippy --toolchain {}", TOOLCHAIN), ".") 88 run(&format!("rustup component add clippy --toolchain {}", TOOLCHAIN), ".")
130} 89}
@@ -143,41 +102,40 @@ pub fn run_fuzzer() -> Result<()> {
143 run("rustup run nightly -- cargo fuzz run parser", "./crates/ra_syntax") 102 run("rustup run nightly -- cargo fuzz run parser", "./crates/ra_syntax")
144} 103}
145 104
146pub fn reformat_staged_files() -> Result<()> { 105/// Cleans the `./target` dir after the build such that only
147 run_rustfmt(Mode::Overwrite)?; 106/// dependencies are cached on CI.
148 let root = project_root(); 107pub fn run_pre_cache() -> Result<()> {
149 let output = Command::new("git") 108 let slow_tests_cookie = Path::new("./target/.slow_tests_cookie");
150 .arg("diff") 109 if !slow_tests_cookie.exists() {
151 .arg("--diff-filter=MAR") 110 panic!("slow tests were skipped on CI!")
152 .arg("--name-only")
153 .arg("--cached")
154 .current_dir(&root)
155 .output()?;
156 if !output.status.success() {
157 anyhow::bail!(
158 "`git diff --diff-filter=MAR --name-only --cached` exited with {}",
159 output.status
160 );
161 } 111 }
162 for line in String::from_utf8(output.stdout)?.lines() { 112 rm_rf(slow_tests_cookie)?;
163 run(&format!("git update-index --add {}", root.join(line).to_string_lossy()), ".")?; 113
114 for entry in Path::new("./target/debug").read_dir()? {
115 let entry = entry?;
116 if entry.file_type().map(|it| it.is_file()).ok() == Some(true) {
117 // Can't delete yourself on windows :-(
118 if !entry.path().ends_with("xtask.exe") {
119 rm_rf(&entry.path())?
120 }
121 }
122 }
123
124 fs::remove_file("./target/.rustc_info.json")?;
125 let to_delete = ["ra_", "heavy_test"];
126 for &dir in ["./target/debug/deps", "target/debug/.fingerprint"].iter() {
127 for entry in Path::new(dir).read_dir()? {
128 let entry = entry?;
129 if to_delete.iter().any(|&it| entry.path().display().to_string().contains(it)) {
130 rm_rf(&entry.path())?
131 }
132 }
164 } 133 }
134
165 Ok(()) 135 Ok(())
166} 136}
167 137
168fn do_run<F>(cmdline: &str, dir: &str, mut f: F) -> Result<Output> 138fn rm_rf(path: &Path) -> Result<()> {
169where 139 if path.is_file() { fs::remove_file(path) } else { fs::remove_dir_all(path) }
170 F: FnMut(&mut Command), 140 .with_context(|| format!("failed to remove {:?}", path))
171{
172 eprintln!("\nwill run: {}", cmdline);
173 let proj_dir = project_root().join(dir);
174 let mut args = cmdline.split_whitespace();
175 let exec = args.next().unwrap();
176 let mut cmd = Command::new(exec);
177 f(cmd.args(args).current_dir(proj_dir).stderr(Stdio::inherit()));
178 let output = cmd.output().with_context(|| format!("running `{}`", cmdline))?;
179 if !output.status.success() {
180 anyhow::bail!("`{}` exited with {}", cmdline, output.status);
181 }
182 Ok(output)
183} 141}
diff --git a/xtask/src/main.rs b/xtask/src/main.rs
index 9cefad925..c347de9ab 100644
--- a/xtask/src/main.rs
+++ b/xtask/src/main.rs
@@ -7,272 +7,109 @@
7//! 7//!
8//! This binary is integrated into the `cargo` command line by using an alias in 8//! This binary is integrated into the `cargo` command line by using an alias in
9//! `.cargo/config`. 9//! `.cargo/config`.
10mod help;
11 10
12use std::{env, fmt::Write, path::PathBuf, str}; 11use std::env;
13 12
14use anyhow::Context;
15use pico_args::Arguments; 13use pico_args::Arguments;
16use xtask::{ 14use xtask::{
17 codegen::{self, Mode}, 15 codegen::{self, Mode},
18 install_pre_commit_hook, reformat_staged_files, run, run_clippy, run_fuzzer, run_rustfmt, 16 install::{ClientOpt, InstallCmd, ServerOpt},
19 run_with_output, Cmd, Result, 17 pre_commit, run_clippy, run_fuzzer, run_pre_cache, run_rustfmt, Result,
20}; 18};
21 19
22// Latest stable, feel free to send a PR if this lags behind.
23const REQUIRED_RUST_VERSION: u32 = 40;
24
25struct InstallOpt {
26 client: Option<ClientOpt>,
27 server: Option<ServerOpt>,
28}
29
30enum ClientOpt {
31 VsCode,
32}
33
34struct ServerOpt {
35 jemalloc: bool,
36}
37
38fn main() -> Result<()> { 20fn main() -> Result<()> {
39 if env::args().next().map(|it| it.contains("pre-commit")) == Some(true) { 21 if env::args().next().map(|it| it.contains("pre-commit")) == Some(true) {
40 return reformat_staged_files(); 22 return pre_commit::run_hook();
41 } 23 }
42 24
43 let subcommand = match std::env::args_os().nth(1) { 25 let mut args = Arguments::from_env();
44 None => { 26 let subcommand = args.subcommand()?.unwrap_or_default();
45 eprintln!("{}", help::GLOBAL_HELP); 27
46 return Ok(()); 28 match subcommand.as_str() {
47 }
48 Some(s) => s,
49 };
50 let mut matches = Arguments::from_vec(std::env::args_os().skip(2).collect());
51 let subcommand = &*subcommand.to_string_lossy();
52 match subcommand {
53 "install" => { 29 "install" => {
54 if matches.contains(["-h", "--help"]) { 30 if args.contains(["-h", "--help"]) {
55 eprintln!("{}", help::INSTALL_HELP); 31 eprintln!(
32 "\
33cargo xtask install
34Install rust-analyzer server or editor plugin.
35
36USAGE:
37 cargo xtask install [FLAGS]
38
39FLAGS:
40 --client-code Install only VS Code plugin
41 --server Install only the language server
42 --jemalloc Use jemalloc for server
43 -h, --help Prints help information
44 "
45 );
56 return Ok(()); 46 return Ok(());
57 } 47 }
58 let server = matches.contains("--server"); 48 let server = args.contains("--server");
59 let client_code = matches.contains("--client-code"); 49 let client_code = args.contains("--client-code");
60 if server && client_code { 50 if server && client_code {
61 eprintln!("{}", help::INSTALL_RA_CONFLICT); 51 eprintln!(
52 "error: The argument `--server` cannot be used with `--client-code`\n\n\
53 For more information try --help"
54 );
62 return Ok(()); 55 return Ok(());
63 } 56 }
64 let jemalloc = matches.contains("--jemalloc"); 57
65 matches.finish().or_else(handle_extra_flags)?; 58 let jemalloc = args.contains("--jemalloc");
66 let opts = InstallOpt { 59
60 args.finish()?;
61
62 InstallCmd {
67 client: if server { None } else { Some(ClientOpt::VsCode) }, 63 client: if server { None } else { Some(ClientOpt::VsCode) },
68 server: if client_code { None } else { Some(ServerOpt { jemalloc }) }, 64 server: if client_code { None } else { Some(ServerOpt { jemalloc }) },
69 }; 65 }
70 install(opts)? 66 .run()
71 } 67 }
72 "codegen" => { 68 "codegen" => {
73 if matches.contains(["-h", "--help"]) { 69 args.finish()?;
74 help::print_no_param_subcommand_help(&subcommand);
75 return Ok(());
76 }
77 codegen::generate_syntax(Mode::Overwrite)?; 70 codegen::generate_syntax(Mode::Overwrite)?;
78 codegen::generate_parser_tests(Mode::Overwrite)?; 71 codegen::generate_parser_tests(Mode::Overwrite)?;
79 codegen::generate_assists_docs(Mode::Overwrite)?; 72 codegen::generate_assists_docs(Mode::Overwrite)?;
73 Ok(())
80 } 74 }
81 "format" => { 75 "format" => {
82 if matches.contains(["-h", "--help"]) { 76 args.finish()?;
83 help::print_no_param_subcommand_help(&subcommand); 77 run_rustfmt(Mode::Overwrite)
84 return Ok(());
85 }
86 run_rustfmt(Mode::Overwrite)?
87 } 78 }
88 "install-pre-commit-hook" => { 79 "install-pre-commit-hook" => {
89 if matches.contains(["-h", "--help"]) { 80 args.finish()?;
90 help::print_no_param_subcommand_help(&subcommand); 81 pre_commit::install_hook()
91 return Ok(());
92 }
93 install_pre_commit_hook()?
94 } 82 }
95 "lint" => { 83 "lint" => {
96 if matches.contains(["-h", "--help"]) { 84 args.finish()?;
97 help::print_no_param_subcommand_help(&subcommand); 85 run_clippy()
98 return Ok(());
99 }
100 run_clippy()?
101 } 86 }
102 "fuzz-tests" => { 87 "fuzz-tests" => {
103 if matches.contains(["-h", "--help"]) { 88 args.finish()?;
104 help::print_no_param_subcommand_help(&subcommand); 89 run_fuzzer()
105 return Ok(());
106 }
107 run_fuzzer()?
108 } 90 }
109 _ => eprintln!("{}", help::GLOBAL_HELP), 91 "pre-cache" => {
110 } 92 args.finish()?;
111 Ok(()) 93 run_pre_cache()
112}
113
114fn handle_extra_flags(e: pico_args::Error) -> Result<()> {
115 if let pico_args::Error::UnusedArgsLeft(flags) = e {
116 let mut invalid_flags = String::new();
117 for flag in flags {
118 write!(&mut invalid_flags, "{}, ", flag)?;
119 }
120 let (invalid_flags, _) = invalid_flags.split_at(invalid_flags.len() - 2);
121 anyhow::bail!("Invalid flags: {}", invalid_flags)
122 } else {
123 anyhow::bail!(e.to_string())
124 }
125}
126
127fn install(opts: InstallOpt) -> Result<()> {
128 if cfg!(target_os = "macos") {
129 fix_path_for_mac().context("Fix path for mac")?
130 }
131 if let Some(server) = opts.server {
132 install_server(server).context("install server")?;
133 }
134 if let Some(client) = opts.client {
135 install_client(client).context("install client")?;
136 }
137 Ok(())
138}
139
140fn fix_path_for_mac() -> Result<()> {
141 let mut vscode_path: Vec<PathBuf> = {
142 const COMMON_APP_PATH: &str =
143 r"/Applications/Visual Studio Code.app/Contents/Resources/app/bin";
144 const ROOT_DIR: &str = "";
145 let home_dir = match env::var("HOME") {
146 Ok(home) => home,
147 Err(e) => anyhow::bail!("Failed getting HOME from environment with error: {}.", e),
148 };
149
150 [ROOT_DIR, &home_dir]
151 .iter()
152 .map(|dir| String::from(*dir) + COMMON_APP_PATH)
153 .map(PathBuf::from)
154 .filter(|path| path.exists())
155 .collect()
156 };
157
158 if !vscode_path.is_empty() {
159 let vars = match env::var_os("PATH") {
160 Some(path) => path,
161 None => anyhow::bail!("Could not get PATH variable from env."),
162 };
163
164 let mut paths = env::split_paths(&vars).collect::<Vec<_>>();
165 paths.append(&mut vscode_path);
166 let new_paths = env::join_paths(paths).context("build env PATH")?;
167 env::set_var("PATH", &new_paths);
168 }
169
170 Ok(())
171}
172
173fn install_client(ClientOpt::VsCode: ClientOpt) -> Result<()> {
174 let npm_version = Cmd {
175 unix: r"npm --version",
176 windows: r"cmd.exe /c npm --version",
177 work_dir: "./editors/code",
178 }
179 .run();
180
181 if npm_version.is_err() {
182 eprintln!("\nERROR: `npm --version` failed, `npm` is required to build the VS Code plugin")
183 }
184
185 Cmd { unix: r"npm install", windows: r"cmd.exe /c npm install", work_dir: "./editors/code" }
186 .run()?;
187 Cmd {
188 unix: r"npm run package --scripts-prepend-node-path",
189 windows: r"cmd.exe /c npm run package",
190 work_dir: "./editors/code",
191 }
192 .run()?;
193
194 let code_binary = ["code", "code-insiders", "codium"].iter().find(|bin| {
195 Cmd {
196 unix: &format!("{} --version", bin),
197 windows: &format!("cmd.exe /c {}.cmd --version", bin),
198 work_dir: "./editors/code",
199 } 94 }
200 .run() 95 _ => {
201 .is_ok() 96 eprintln!(
202 }); 97 "\
203 98cargo xtask
204 let code_binary = match code_binary { 99Run custom build command.
205 Some(it) => it, 100
206 None => anyhow::bail!("Can't execute `code --version`. Perhaps it is not in $PATH?"), 101USAGE:
207 }; 102 cargo xtask <SUBCOMMAND>
208 103
209 Cmd { 104SUBCOMMANDS:
210 unix: &format!(r"{} --install-extension ./ra-lsp-0.0.1.vsix --force", code_binary), 105 format
211 windows: &format!( 106 install-pre-commit-hook
212 r"cmd.exe /c {}.cmd --install-extension ./ra-lsp-0.0.1.vsix --force", 107 fuzz-tests
213 code_binary 108 codegen
214 ), 109 install
215 work_dir: "./editors/code", 110 lint"
216 } 111 );
217 .run()?; 112 Ok(())
218
219 let output = Cmd {
220 unix: &format!(r"{} --list-extensions", code_binary),
221 windows: &format!(r"cmd.exe /c {}.cmd --list-extensions", code_binary),
222 work_dir: ".",
223 }
224 .run_with_output()?;
225
226 if !str::from_utf8(&output.stdout)?.contains("ra-lsp") {
227 anyhow::bail!(
228 "Could not install the Visual Studio Code extension. \
229 Please make sure you have at least NodeJS 10.x together with the latest version of VS Code installed and try again."
230 );
231 }
232
233 Ok(())
234}
235
236fn install_server(opts: ServerOpt) -> Result<()> {
237 let mut old_rust = false;
238 if let Ok(output) = run_with_output("cargo --version", ".") {
239 if let Ok(stdout) = String::from_utf8(output.stdout) {
240 println!("{}", stdout);
241 if !check_version(&stdout, REQUIRED_RUST_VERSION) {
242 old_rust = true;
243 }
244 } 113 }
245 } 114 }
246
247 if old_rust {
248 eprintln!(
249 "\nWARNING: at least rust 1.{}.0 is required to compile rust-analyzer\n",
250 REQUIRED_RUST_VERSION,
251 )
252 }
253
254 let res = if opts.jemalloc {
255 run("cargo install --path crates/ra_lsp_server --locked --force --features jemalloc", ".")
256 } else {
257 run("cargo install --path crates/ra_lsp_server --locked --force", ".")
258 };
259
260 if res.is_err() && old_rust {
261 eprintln!(
262 "\nWARNING: at least rust 1.{}.0 is required to compile rust-analyzer\n",
263 REQUIRED_RUST_VERSION,
264 )
265 }
266
267 res
268}
269
270fn check_version(version_output: &str, min_minor_version: u32) -> bool {
271 // Parse second the number out of
272 // cargo 1.39.0-beta (1c6ec66d5 2019-09-30)
273 let minor: Option<u32> = version_output.split('.').nth(1).and_then(|it| it.parse().ok());
274 match minor {
275 None => true,
276 Some(minor) => minor >= min_minor_version,
277 }
278} 115}
diff --git a/xtask/src/pre_commit.rs b/xtask/src/pre_commit.rs
new file mode 100644
index 000000000..88e868ca6
--- /dev/null
+++ b/xtask/src/pre_commit.rs
@@ -0,0 +1,36 @@
1//! pre-commit hook for code formatting.
2
3use std::{fs, path::PathBuf};
4
5use anyhow::{bail, Result};
6
7use crate::{cmd::run_with_output, project_root, run, run_rustfmt, Mode};
8
9// FIXME: if there are changed `.ts` files, also reformat TypeScript (by
10// shelling out to `npm fmt`).
11pub fn run_hook() -> Result<()> {
12 run_rustfmt(Mode::Overwrite)?;
13
14 let diff = run_with_output("git diff --diff-filter=MAR --name-only --cached", ".")?;
15
16 let root = project_root();
17 for line in String::from_utf8(diff.stdout)?.lines() {
18 run(&format!("git update-index --add {}", root.join(line).to_string_lossy()), ".")?;
19 }
20
21 Ok(())
22}
23
24pub fn install_hook() -> Result<()> {
25 let hook_path: PathBuf =
26 format!("./.git/hooks/pre-commit{}", std::env::consts::EXE_SUFFIX).into();
27
28 if hook_path.exists() {
29 bail!("Git hook already created");
30 }
31
32 let me = std::env::current_exe()?;
33 fs::copy(me, hook_path)?;
34
35 Ok(())
36}