Merge remote-tracking branch 'origin/master' into azure-pipelines

This commit is contained in:
Alex Crichton 2019-05-21 15:37:07 -07:00
commit fe3dd0b50f
1132 changed files with 14666 additions and 7553 deletions

View File

@ -155,6 +155,8 @@ Mark Sinclair <mark.edward.x@gmail.com> =Mark Sinclair <=125axel125@gmail.com>
Markus Westerlind <marwes91@gmail.com> Markus <marwes91@gmail.com>
Martin Hafskjold Thoresen <martinhath@gmail.com>
Matej Lach <matej.lach@gmail.com> Matej Ľach <matej.lach@gmail.com>
Mateusz Mikuła <matti@marinelayer.io> <mati865@gmail.com>
Mateusz Mikuła <matti@marinelayer.io> <mati865@users.noreply.github.com>
Matt Brubeck <mbrubeck@limpet.net> <mbrubeck@cs.hmc.edu>
Matthew Auld <matthew.auld@intel.com>
Matthew McPherrin <matthew@mcpherrin.ca> <matt@mcpherrin.ca>

View File

@ -13,11 +13,19 @@ dependencies = [
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "aho-corasick"
version = "0.7.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "alloc"
version = "0.0.0"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
"rand 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"rand_xorshift 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -115,7 +123,7 @@ version = "0.1.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cc 1.0.35 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-std-workspace-core 1.0.0",
]
@ -181,6 +189,14 @@ dependencies = [
"toml 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "bstr"
version = "0.1.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
name = "bufstream"
version = "0.1.4"
@ -246,7 +262,7 @@ dependencies = [
"clap 2.32.0 (registry+https://github.com/rust-lang/crates.io-index)",
"core-foundation 0.6.3 (registry+https://github.com/rust-lang/crates.io-index)",
"crates-io 0.25.0",
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"crypto-hash 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)",
"curl 0.4.21 (registry+https://github.com/rust-lang/crates.io-index)",
"curl-sys 0.4.18 (registry+https://github.com/rust-lang/crates.io-index)",
@ -261,7 +277,7 @@ dependencies = [
"glob 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"hex 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
"home 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
"ignore 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"ignore 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)",
"im-rc 12.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"jobserver 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -373,12 +389,11 @@ dependencies = [
"compiletest_rs 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)",
"derive-new 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-workspace-hack 1.0.0",
"rustc_tools_util 0.1.1",
"semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_derive 1.0.81 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -396,10 +411,9 @@ dependencies = [
"matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)",
"pulldown-cmark 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
"quine-mc_cluskey 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)",
"semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_derive 1.0.81 (registry+https://github.com/rust-lang/crates.io-index)",
"smallvec 0.6.7 (registry+https://github.com/rust-lang/crates.io-index)",
"toml 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
"unicode-normalization 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)",
@ -448,7 +462,7 @@ dependencies = [
[[package]]
name = "compiler_builtins"
version = "0.1.12"
version = "0.1.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cc 1.0.35 (registry+https://github.com/rust-lang/crates.io-index)",
@ -461,13 +475,12 @@ version = "0.0.0"
dependencies = [
"diff 0.1.11 (registry+https://github.com/rust-lang/crates.io-index)",
"env_logger 0.5.13 (registry+https://github.com/rust-lang/crates.io-index)",
"filetime 0.2.4 (registry+https://github.com/rust-lang/crates.io-index)",
"getopts 0.2.19 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"miow 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rustfix 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
@ -486,7 +499,7 @@ dependencies = [
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"miow 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rustfix 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_derive 1.0.81 (registry+https://github.com/rust-lang/crates.io-index)",
@ -553,13 +566,10 @@ dependencies = [
[[package]]
name = "crossbeam-channel"
version = "0.3.4"
version = "0.3.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-epoch 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
"rand 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"smallvec 0.6.7 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -578,7 +588,7 @@ version = "0.6.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-epoch 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -602,7 +612,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"arrayvec 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)",
"cfg-if 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"memoffset 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
@ -618,10 +628,11 @@ dependencies = [
[[package]]
name = "crossbeam-utils"
version = "0.6.2"
version = "0.6.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"cfg-if 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -733,7 +744,7 @@ name = "dlmalloc"
version = "0.1.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-std-workspace-core 1.0.0",
]
@ -749,7 +760,7 @@ version = "2.3.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_derive 1.0.81 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
@ -781,7 +792,7 @@ dependencies = [
"atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"humantime 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"termcolor 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -793,7 +804,7 @@ dependencies = [
"atty 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)",
"humantime 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"termcolor 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -899,7 +910,7 @@ name = "fortanix-sgx-abi"
version = "0.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-std-workspace-core 1.0.0",
]
@ -1010,14 +1021,14 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "globset"
version = "0.4.2"
version = "0.4.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)",
"aho-corasick 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)",
"bstr 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)",
"fnv 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -1034,7 +1045,7 @@ dependencies = [
"pest 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)",
"pest_derive 1.0.8 (registry+https://github.com/rust-lang/crates.io-index)",
"quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -1049,7 +1060,7 @@ dependencies = [
"pest 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"pest_derive 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"quick-error 1.2.2 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
"walkdir 2.2.7 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1060,7 +1071,7 @@ name = "hashbrown"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-std-workspace-alloc 1.0.0",
"rustc-std-workspace-core 1.0.0",
]
@ -1135,19 +1146,19 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "ignore"
version = "0.4.6"
version = "0.4.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-channel 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)",
"globset 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-channel 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
"globset 0.4.3 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"same-file 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
"thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"walkdir 2.2.7 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -1471,7 +1482,7 @@ dependencies = [
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"open 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"pulldown-cmark 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_derive 1.0.81 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1483,7 +1494,7 @@ dependencies = [
[[package]]
name = "measureme"
version = "0.2.1"
version = "0.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"byteorder 1.2.7 (registry+https://github.com/rust-lang/crates.io-index)",
@ -1761,7 +1772,7 @@ dependencies = [
name = "panic_abort"
version = "0.0.0"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -1771,7 +1782,7 @@ name = "panic_unwind"
version = "0.0.0"
dependencies = [
"alloc 0.0.0",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
"unwind 0.0.0",
@ -1956,7 +1967,7 @@ name = "profiler_builtins"
version = "0.0.0"
dependencies = [
"cc 1.0.35 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
]
@ -1974,7 +1985,7 @@ dependencies = [
"rand 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"rand_chacha 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"rand_xorshift 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rusty-fork 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"tempfile 3.0.5 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -2182,12 +2193,12 @@ dependencies = [
[[package]]
name = "regex"
version = "1.1.0"
version = "1.1.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)",
"aho-corasick 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)",
"memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)",
"regex-syntax 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)",
"thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"utf8-ranges 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -2202,7 +2213,7 @@ dependencies = [
[[package]]
name = "regex-syntax"
version = "0.6.4"
version = "0.6.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)",
@ -2231,7 +2242,7 @@ dependencies = [
"cargo 0.37.0",
"cargo_metadata 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
"clippy_lints 0.0.212",
"crossbeam-channel 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-channel 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
"difference 2.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"env_logger 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)",
"failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
@ -2249,7 +2260,7 @@ dependencies = [
"racer 2.1.22 (registry+https://github.com/rust-lang/crates.io-index)",
"rand 0.6.1 (registry+https://github.com/rust-lang/crates.io-index)",
"rayon 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rls-analysis 0.17.0 (registry+https://github.com/rust-lang/crates.io-index)",
"rls-blacklist 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)",
"rls-data 0.19.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -2348,7 +2359,7 @@ dependencies = [
"jobserver 0.1.13 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"measureme 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)",
"measureme 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
"parking_lot 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)",
"polonius-engine 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -2481,7 +2492,7 @@ name = "rustc-demangle"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-std-workspace-core 1.0.0",
]
@ -2609,7 +2620,7 @@ dependencies = [
"alloc 0.0.0",
"build_helper 0.1.0",
"cmake 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
]
@ -2839,7 +2850,7 @@ dependencies = [
"alloc 0.0.0",
"build_helper 0.1.0",
"cmake 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
]
@ -2901,7 +2912,7 @@ dependencies = [
"alloc 0.0.0",
"build_helper 0.1.0",
"cmake 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
]
@ -3018,7 +3029,7 @@ dependencies = [
"alloc 0.0.0",
"build_helper 0.1.0",
"cmake 0.1.38 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
]
@ -3092,11 +3103,11 @@ dependencies = [
"env_logger 0.6.0 (registry+https://github.com/rust-lang/crates.io-index)",
"failure 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
"getopts 0.2.19 (registry+https://github.com/rust-lang/crates.io-index)",
"ignore 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"ignore 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)",
"itertools 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-ap-rustc_target 407.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-ap-syntax 407.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-ap-syntax_pos 407.0.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -3132,7 +3143,7 @@ name = "same-file"
version = "1.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -3287,7 +3298,7 @@ dependencies = [
"alloc 0.0.0",
"backtrace-sys 0.1.27 (registry+https://github.com/rust-lang/crates.io-index)",
"cc 1.0.35 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
"dlmalloc 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)",
"fortanix-sgx-abi 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)",
@ -3553,7 +3564,7 @@ dependencies = [
name = "tidy"
version = "0.1.0"
dependencies = [
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"serde 1.0.82 (registry+https://github.com/rust-lang/crates.io-index)",
"serde_json 1.0.33 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -3614,7 +3625,7 @@ name = "tokio-executor"
version = "0.1.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"futures 0.1.21 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -3658,7 +3669,7 @@ name = "tokio-reactor"
version = "0.1.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"futures 0.1.21 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -3704,9 +3715,9 @@ name = "tokio-threadpool"
version = "0.1.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-channel 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-channel 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-deque 0.6.3 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"futures 0.1.21 (registry+https://github.com/rust-lang/crates.io-index)",
"log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
"num_cpus 1.8.0 (registry+https://github.com/rust-lang/crates.io-index)",
@ -3719,7 +3730,7 @@ name = "tokio-timer"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)",
"crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)",
"futures 0.1.21 (registry+https://github.com/rust-lang/crates.io-index)",
"slab 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
"tokio-executor 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -3792,7 +3803,7 @@ dependencies = [
"error-chain 0.12.0 (registry+https://github.com/rust-lang/crates.io-index)",
"is-match 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)",
"toml 0.4.10 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -3878,7 +3889,7 @@ name = "unwind"
version = "0.0.0"
dependencies = [
"cc 1.0.35 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)",
"compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)",
"core 0.0.0",
"libc 0.2.54 (registry+https://github.com/rust-lang/crates.io-index)",
]
@ -3957,7 +3968,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"same-file 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -3986,7 +3997,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
[[package]]
name = "winapi-util"
version = "0.1.1"
version = "0.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
@ -4003,7 +4014,7 @@ version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
"winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)",
]
[[package]]
@ -4039,6 +4050,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
[metadata]
"checksum adler32 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "7e522997b529f05601e05166c07ed17789691f562762c7f3b987263d2dedee5c"
"checksum aho-corasick 0.6.9 (registry+https://github.com/rust-lang/crates.io-index)" = "1e9a933f4e58658d7b12defcf96dc5c720f20832deebe3e0a19efd3b6aaeeb9e"
"checksum aho-corasick 0.7.3 (registry+https://github.com/rust-lang/crates.io-index)" = "e6f484ae0c99fec2e858eb6134949117399f222608d84cadb3f58c1f97c2364c"
"checksum ammonia 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "fd4c682378117e4186a492b2252b9537990e1617f44aed9788b9a1149de45477"
"checksum annotate-snippets 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e8bcdcd5b291ce85a78f2b9d082a8de9676c12b1840d386d67bc5eea6f9d2b4e"
"checksum ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b"
@ -4055,6 +4067,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum bitflags 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "228047a76f468627ca71776ecdebd732a3423081fcf5125585bcd7c49886ce12"
"checksum blake2-rfc 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)" = "5d6d530bdd2d52966a6d03b7a964add7ae1a288d25214066fd4b600f0f796400"
"checksum block-buffer 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "a076c298b9ecdb530ed9d967e74a6027d6a7478924520acddcddc24c1c8ab3ab"
"checksum bstr 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "853b090ce0f45d0265902666bf88039ea3da825e33796716c511a1ec9c170036"
"checksum bufstream 0.1.4 (registry+https://github.com/rust-lang/crates.io-index)" = "40e38929add23cdf8a366df9b0e088953150724bcbe5fc330b0d8eb3b328eec8"
"checksum build_const 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "39092a32794787acd8525ee150305ff051b0aa6cc2abaf193924f5ab05425f39"
"checksum byte-tools 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "560c32574a12a89ecd91f5e742165893f86e3ab98d21f8ea548658eb9eef5f40"
@ -4074,20 +4087,20 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum colored 1.6.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b0aa3473e85a3161b59845d6096b289bb577874cafeaf75ea1b1beaa6572c7fc"
"checksum commoncrypto 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d056a8586ba25a1e4d61cb090900e495952c7886786fc55f909ab2f819b69007"
"checksum commoncrypto-sys 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1fed34f46747aa73dfaa578069fd8279d2818ade2b55f38f22a9401c7f4083e2"
"checksum compiler_builtins 0.1.12 (registry+https://github.com/rust-lang/crates.io-index)" = "6549720ae78db799196d4af8f719facb4c7946710b4b64148482553e54b56d15"
"checksum compiler_builtins 0.1.14 (registry+https://github.com/rust-lang/crates.io-index)" = "e3f235c329e5cb9fa3d2ca2cc36256ba9a7f23fa76e0f4db6f68c23b73b2ac69"
"checksum compiletest_rs 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)" = "f40ecc9332b68270998995c00f8051ee856121764a0d3230e64c9efd059d27b6"
"checksum constant_time_eq 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "8ff012e225ce166d4422e0e78419d901719760f62ae2b7969ca6b564d1b54a9e"
"checksum core-foundation 0.6.3 (registry+https://github.com/rust-lang/crates.io-index)" = "4e2640d6d0bf22e82bed1b73c6aef8d5dd31e5abe6666c57e6d45e2649f4f887"
"checksum core-foundation-sys 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e7ca8a5221364ef15ce201e8ed2f609fc312682a8f4e0e3d4aa5879764e0fa3b"
"checksum crc 1.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d663548de7f5cca343f1e0a48d14dcfb0e9eb4e079ec58883b7251539fa10aeb"
"checksum crc32fast 1.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e91d5240c6975ef33aeb5f148f35275c25eda8e8a5f95abe421978b05b8bf192"
"checksum crossbeam-channel 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "5b2a9ea8f77c7f9efd317a8a5645f515d903a2d86ee14d2337a5facd1bd52c12"
"checksum crossbeam-channel 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)" = "0f0ed1a4de2235cabda8558ff5840bffb97fcb64c97827f354a451307df5f72b"
"checksum crossbeam-deque 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "f739f8c5363aca78cfb059edf753d8f0d36908c348f3d8d1503f03d8b75d9cf3"
"checksum crossbeam-deque 0.6.3 (registry+https://github.com/rust-lang/crates.io-index)" = "05e44b8cf3e1a625844d1750e1f7820da46044ff6d28f4d43e455ba3e5bb2c13"
"checksum crossbeam-epoch 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "927121f5407de9956180ff5e936fe3cf4324279280001cd56b669d28ee7e9150"
"checksum crossbeam-epoch 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "f10a4f8f409aaac4b16a5474fb233624238fcdeefb9ba50d5ea059aab63ba31c"
"checksum crossbeam-utils 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "2760899e32a1d58d5abb31129f8fae5de75220bc2176e77ff7c627ae45c918d9"
"checksum crossbeam-utils 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e07fc155212827475223f0bcfae57e945e694fc90950ddf3f6695bbfd5555c72"
"checksum crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "f8306fcef4a7b563b76b7dd949ca48f52bc1141aa067d2ea09565f3e2652aa5c"
"checksum crypto-hash 0.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "09de9ee0fc255ace04c7fa0763c9395a945c37c8292bb554f8d48361d1dcf1b4"
"checksum curl 0.4.21 (registry+https://github.com/rust-lang/crates.io-index)" = "a85f2f95f2bd277d316d1aa8a477687ab4a6942258c7db7c89c187534669979c"
"checksum curl-sys 0.4.18 (registry+https://github.com/rust-lang/crates.io-index)" = "9d91a0052d5b982887d8e829bee0faffc7218ea3c6ebd3d6c2c8f678a93c9a42"
@ -4131,7 +4144,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum git2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c7339329bfa14a00223244311560d11f8f489b453fb90092af97f267a6090ab0"
"checksum git2-curl 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d58551e903ed7e2d6fe3a2f3c7efa3a784ec29b19d0fbb035aaf0497c183fbdd"
"checksum glob 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9b919933a397b79c37e33b77bb2aa3dc8eb6e165ad809e58ff75bc7db2e34574"
"checksum globset 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4743617a7464bbda3c8aec8558ff2f9429047e025771037df561d383337ff865"
"checksum globset 0.4.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ef4feaabe24a0a658fd9cf4a9acf6ed284f045c77df0f49020ba3245cfb7b454"
"checksum handlebars 0.32.4 (registry+https://github.com/rust-lang/crates.io-index)" = "d89ec99d1594f285d4590fc32bac5f75cdab383f1123d504d27862c644a807dd"
"checksum handlebars 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d82e5750d8027a97b9640e3fefa66bbaf852a35228e1c90790efd13c4b09c166"
"checksum hashbrown 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "570178d5e4952010d138b0f1d581271ff3a02406d990f887d1e87e3d6e43b0ac"
@ -4143,7 +4156,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum humantime 1.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3ca7e5f2e110db35f93b837c81797f3714500b81d517bf20c431b16d3ca4f114"
"checksum idna 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "38f09e0f0b1fb55fdee1f17470ad800da77af5186a1a76c026b679358b7e844e"
"checksum if_chain 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "4bac95d9aa0624e7b78187d6fb8ab012b41d9f6f54b1bcb61e61c4845f8357ec"
"checksum ignore 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)" = "ad03ca67dc12474ecd91fdb94d758cbd20cb4e7a78ebe831df26a9b7511e1162"
"checksum ignore 0.4.7 (registry+https://github.com/rust-lang/crates.io-index)" = "8dc57fa12805f367736a38541ac1a9fc6a52812a0ca959b1d4d4b640a89eb002"
"checksum im-rc 12.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9460397452f537fd51808056ff209f4c4c4c9d20d42ae952f517708726284972"
"checksum iovec 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "dbe6e417e7d0975db6512b90796e8ce223145ac4e33c377e4a42882a0e88bb08"
"checksum is-match 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "7e5b386aef33a1c677be65237cb9d32c3f3ef56bd035949710c4bb13083eb053"
@ -4176,7 +4189,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum matches 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "7ffc5c5338469d4d3ea17d269fa8ea3512ad247247c30bd2df69e68309ed0a08"
"checksum mdbook 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "90b5a8d7e341ceee5db3882a06078d42661ddcfa2b3687319cc5da76ec4e782f"
"checksum mdbook 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "0ba0d44cb4089c741b9a91f3e5218298a40699c2f3a070a85014eed290c60819"
"checksum measureme 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "36bb2b263a6795d352035024d6b30ce465bb79a5e5280d74c3b5f8464c657bcc"
"checksum measureme 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d09de7dafa3aa334bc806447c7e4de69419723312f4b88b80b561dea66601ce8"
"checksum memchr 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "2efc7bc57c883d4a4d6e3246905283d8dae951bb3bd32f49d6ef297f546e1c39"
"checksum memmap 0.6.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e2ffa2c986de11a9df78620c01eeaaf27d94d3ff02bf81bfcca953102dd0c6ff"
"checksum memoffset 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "0f9dc261e2b62d7a622bf416ea3c5245cdd5d9a7fcc428c0d06804dfce1775b3"
@ -4249,9 +4262,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum redox_termios 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "7e891cfe48e9100a70a3b6eb652fef28920c117d366339687bd5576160db0f76"
"checksum redox_users 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "214a97e49be64fd2c86f568dd0cb2c757d2cc53de95b273b6ad0a1c908482f26"
"checksum regex 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "9329abc99e39129fcceabd24cf5d85b4671ef7c29c50e972bc5afe32438ec384"
"checksum regex 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "37e7cbbd370869ce2e8dff25c7018702d10b21a20ef7135316f8daecd6c25b7f"
"checksum regex 1.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "8f0a0bcab2fd7d1d7c54fa9eae6f43eddeb9ce2e7352f8518a814a4f65d60c58"
"checksum regex-syntax 0.5.6 (registry+https://github.com/rust-lang/crates.io-index)" = "7d707a4fa2637f2dca2ef9fd02225ec7661fe01a53623c1e6515b6916511f7a7"
"checksum regex-syntax 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)" = "4e47a2ed29da7a9e1960e1639e7a982e6edc6d49be308a3b02daf511504a16d1"
"checksum regex-syntax 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)" = "dcfd8681eebe297b81d98498869d4aae052137651ad7b96822f09ceb690d0a96"
"checksum remove_dir_all 0.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "3488ba1b9a2084d38645c4c08276a1752dcbf2c7130d74f1569681ad5d2799c5"
"checksum rls-analysis 0.17.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d53d49a28f75da9d02790d9256fecf6c0481e0871374326023c7a33131295579"
"checksum rls-blacklist 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "b8ce1fdac03e138c4617ff87b194e1ff57a39bb985a044ccbd8673d30701e411"
@ -4365,7 +4378,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
"checksum winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "92c1eb33641e276cfa214a0522acad57be5c56b10cb348b3c5117db75f3ac4b0"
"checksum winapi-build 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc"
"checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"
"checksum winapi-util 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "afc5508759c5bf4285e61feb862b6083c8480aec864fa17a81fdec6f69b461ab"
"checksum winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7168bab6e1daee33b4557efd0e95d5ca70a03706d39fa5f3fe7a236f584b03c9"
"checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
"checksum wincolor 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)" = "561ed901ae465d6185fa7864d63fbd5720d0ef718366c9a4dc83cf6170d7e9ba"
"checksum ws2_32-sys 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e"

View File

@ -130,9 +130,15 @@ build.
#### MSVC
[windows-msvc]: #windows-msvc
MSVC builds of Rust additionally require an installation of Visual Studio 2013
(or later) so `rustc` can use its linker. Make sure to check the “C++ tools”
option.
MSVC builds of Rust additionally require an installation of Visual Studio 2017
(or later) so `rustc` can use its linker. The simplest way is to get the
[Visual Studio Build Tools] and check the “C++ build tools” workload.
[Visual Studio Build Tools]: https://visualstudio.microsoft.com/downloads/#build-tools-for-visual-studio-2019
At last check (cmake 3.14.3 and msvc 16.0.3) using the 2019 tools fails to
build the in-tree LLVM build with a CMake error, so use 2017 instead by
including the “MSVC v141 VS 2017 C++ x64/x86 build tools (v14.16)” component.
With these dependencies installed, you can build the compiler in a `cmd.exe`
shell with:

View File

@ -1,3 +1,109 @@
Version 1.35.0 (2019-05-23)
==========================
Language
--------
- [`FnOnce`, `FnMut`, and the `Fn` traits are now implemented for `Box<FnOnce>`,
`Box<FnMut>`, and `Box<Fn>` respectively.][59500]
- [You can now coerce closures into unsafe function pointers.][59580] e.g.
```rust
unsafe fn call_unsafe(func: unsafe fn()) {
func()
}
pub fn main() {
unsafe { call_unsafe(|| {}); }
}
```
Compiler
--------
- [Added the `armv6-unknown-freebsd-gnueabihf` and
`armv7-unknown-freebsd-gnueabihf` targets.][58080]
- [Added the `wasm32-unknown-wasi` target.][59464]
Libraries
---------
- [`Thread` will now show its ID in `Debug` output.][59460]
- [`StdinLock`, `StdoutLock`, and `StderrLock` now implement `AsRawFd`.][59512]
- [`alloc::System` now implements `Default`.][59451]
- [Expanded `Debug` output (`{:#?}`) for structs now has a trailing comma on the
last field.][59076]
- [`char::{ToLowercase, ToUppercase}` now
implement `ExactSizeIterator`.][58778]
- [All `NonZero` numeric types now implement `FromStr`.][58717]
- [Removed the `Read` trait bounds
on the `BufReader::{get_ref, get_mut, into_inner}` methods.][58423]
- [You can now call the `dbg!` macro without any parameters to print the file
and line where it is called.][57847]
- [In place ASCII case conversions are now up to 4× faster.][59283]
e.g. `str::make_ascii_lowercase`
- [`hash_map::{OccupiedEntry, VacantEntry}` now implement `Sync`
and `Send`.][58369]
Stabilized APIs
---------------
- [`f32::copysign`]
- [`f64::copysign`]
- [`RefCell::replace_with`]
- [`RefCell::map_split`]
- [`ptr::hash`]
- [`Range::contains`]
- [`RangeFrom::contains`]
- [`RangeTo::contains`]
- [`RangeInclusive::contains`]
- [`RangeToInclusive::contains`]
- [`Option::copied`]
Cargo
-----
- [You can now set `cargo:rustc-cdylib-link-arg` at build time to pass custom
linker arguments when building a `cdylib`.][cargo/6298] Its usage is highly
platform specific.
Misc
----
- [The Rust toolchain is now available natively for musl based distros.][58575]
[59460]: https://github.com/rust-lang/rust/pull/59460/
[59464]: https://github.com/rust-lang/rust/pull/59464/
[59500]: https://github.com/rust-lang/rust/pull/59500/
[59512]: https://github.com/rust-lang/rust/pull/59512/
[59580]: https://github.com/rust-lang/rust/pull/59580/
[59283]: https://github.com/rust-lang/rust/pull/59283/
[59451]: https://github.com/rust-lang/rust/pull/59451/
[59076]: https://github.com/rust-lang/rust/pull/59076/
[58778]: https://github.com/rust-lang/rust/pull/58778/
[58717]: https://github.com/rust-lang/rust/pull/58717/
[58369]: https://github.com/rust-lang/rust/pull/58369/
[58423]: https://github.com/rust-lang/rust/pull/58423/
[58080]: https://github.com/rust-lang/rust/pull/58080/
[57847]: https://github.com/rust-lang/rust/pull/57847/
[58575]: https://github.com/rust-lang/rust/pull/58575
[cargo/6298]: https://github.com/rust-lang/cargo/pull/6298/
[`f32::copysign`]: https://doc.rust-lang.org/stable/std/primitive.f32.html#method.copysign
[`f64::copysign`]: https://doc.rust-lang.org/stable/std/primitive.f64.html#method.copysign
[`RefCell::replace_with`]: https://doc.rust-lang.org/stable/std/cell/struct.RefCell.html#method.replace_with
[`RefCell::map_split`]: https://doc.rust-lang.org/stable/std/cell/struct.RefCell.html#method.map_split
[`ptr::hash`]: https://doc.rust-lang.org/stable/std/ptr/fn.hash.html
[`Range::contains`]: https://doc.rust-lang.org/std/ops/struct.Range.html#method.contains
[`RangeFrom::contains`]: https://doc.rust-lang.org/std/ops/struct.RangeFrom.html#method.contains
[`RangeTo::contains`]: https://doc.rust-lang.org/std/ops/struct.RangeTo.html#method.contains
[`RangeInclusive::contains`]: https://doc.rust-lang.org/std/ops/struct.RangeInclusive.html#method.contains
[`RangeToInclusive::contains`]: https://doc.rust-lang.org/std/ops/struct.RangeToInclusive.html#method.contains
[`Option::copied`]: https://doc.rust-lang.org/std/option/enum.Option.html#method.copied
Version 1.34.2 (2019-05-14)
===========================
* [Destabilize the `Error::type_id` function due to a security
vulnerability][60785] ([CVE-2019-12083])
[60785]: https://github.com/rust-lang/rust/pull/60785
[CVE-2019-12083]: https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-12083
Version 1.34.1 (2019-04-25)
===========================

View File

@ -480,7 +480,7 @@
# linked binaries
#musl-root = "..."
# The root location of the `wasm32-unknown-wasi` sysroot.
# The root location of the `wasm32-wasi` sysroot.
#wasi-root = "..."
# Used in testing for configuring where the QEMU images are located, you

View File

@ -177,7 +177,6 @@ def default_build_triple():
# The goal here is to come up with the same triple as LLVM would,
# at least for the subset of platforms we're willing to target.
ostype_mapper = {
'Bitrig': 'unknown-bitrig',
'Darwin': 'apple-darwin',
'DragonFly': 'unknown-dragonfly',
'FreeBSD': 'unknown-freebsd',

View File

@ -168,7 +168,7 @@ pub fn std_cargo(builder: &Builder<'_>,
.arg("--manifest-path")
.arg(builder.src.join("src/liballoc/Cargo.toml"))
.arg("--features")
.arg("compiler-builtins-mem");
.arg("compiler-builtins-mem compiler-builtins-c");
} else {
let features = builder.std_features();

View File

@ -317,6 +317,10 @@ fn check_llvm_version(builder: &Builder<'_>, llvm_config: &Path) {
fn configure_cmake(builder: &Builder<'_>,
target: Interned<String>,
cfg: &mut cmake::Config) {
// Do not print installation messages for up-to-date files.
// LLVM and LLD builds can produce a lot of those and hit CI limits on log size.
cfg.define("CMAKE_INSTALL_MESSAGE", "LAZY");
if builder.config.ninja {
cfg.generator("Ninja");
}

View File

@ -683,7 +683,7 @@ impl Step for RustdocUi {
target: self.target,
mode: "ui",
suite: "rustdoc-ui",
path: None,
path: Some("src/test/rustdoc-ui"),
compare_mode: None,
})
}
@ -1184,8 +1184,19 @@ impl Step for Compiletest {
Err(_) => p,
}
})
.filter(|p| p.starts_with(suite_path) && p.is_file())
.map(|p| p.strip_prefix(suite_path).unwrap().to_str().unwrap())
.filter(|p| p.starts_with(suite_path) && (p.is_dir() || p.is_file()))
.filter_map(|p| {
// Since test suite paths are themselves directories, if we don't
// specify a directory or file, we'll get an empty string here
// (the result of the test suite directory without its suite prefix).
// Therefore, we need to filter these out, as only the first --test-args
// flag is respected, so providing an empty --test-args conflicts with
// any following it.
match p.strip_prefix(suite_path).ok().and_then(|p| p.to_str()) {
Some(s) if s != "" => Some(s),
_ => None,
}
})
.collect();
test_args.append(&mut builder.config.cmd.test_args());
@ -1870,6 +1881,10 @@ impl Step for CrateRustdoc {
cargo.arg("--");
cargo.args(&builder.config.cmd.test_args());
if self.host.contains("musl") {
cargo.arg("'-Ctarget-feature=-crt-static'");
}
if !builder.config.verbose_tests {
cargo.arg("--quiet");
}

View File

@ -113,7 +113,7 @@ pub fn gnu_target(target: &str) -> &str {
}
pub fn make(host: &str) -> PathBuf {
if host.contains("bitrig") || host.contains("dragonfly") || host.contains("freebsd")
if host.contains("dragonfly") || host.contains("freebsd")
|| host.contains("netbsd") || host.contains("openbsd")
{
PathBuf::from("gmake")

View File

@ -75,7 +75,7 @@ ENV CARGO_TARGET_AARCH64_FUCHSIA_RUSTFLAGS \
ENV TARGETS=x86_64-fuchsia
ENV TARGETS=$TARGETS,aarch64-fuchsia
ENV TARGETS=$TARGETS,wasm32-unknown-unknown
ENV TARGETS=$TARGETS,wasm32-unknown-wasi
ENV TARGETS=$TARGETS,wasm32-wasi
# FIXME(#61022) - reenable solaris
# ENV TARGETS=$TARGETS,sparcv9-sun-solaris
# ENV TARGETS=$TARGETS,x86_64-sun-solaris
@ -87,5 +87,5 @@ ENV TARGETS=$TARGETS,nvptx64-nvidia-cuda
ENV X86_FORTANIX_SGX_LIBS="/x86_64-fortanix-unknown-sgx/lib/"
ENV RUST_CONFIGURE_ARGS --enable-extended --enable-lld --disable-docs \
--set target.wasm32-unknown-wasi.wasi-root=/wasm32-unknown-wasi
--set target.wasm32-wasi.wasi-root=/wasm32-wasi
ENV SCRIPT python2.7 ../x.py dist --target $TARGETS

View File

@ -13,7 +13,7 @@ git clone https://github.com/CraneStation/wasi-sysroot
cd wasi-sysroot
git reset --hard e5f14be38362f1ab83302895a6e74b2ffd0e2302
make -j$(nproc) INSTALL_DIR=/wasm32-unknown-wasi install
make -j$(nproc) INSTALL_DIR=/wasm32-wasi install
cd ..
rm -rf reference-sysroot-wasi

View File

@ -23,7 +23,7 @@ COPY scripts/musl-toolchain.sh /build/
# We need to mitigate rust-lang/rust#34978 when compiling musl itself as well
RUN CFLAGS="-Wa,-mrelax-relocations=no -Wa,--compress-debug-sections=none -Wl,--compress-debug-sections=none" \
CXXFLAGS="-Wa,-mrelax-relocations=no -Wa,--compress-debug-sections=none -Wl,--compress-debug-sections=none" \
bash musl-toolchain.sh x86_64 && rm -rf build
REPLACE_CC=1 bash musl-toolchain.sh x86_64 && rm -rf build
COPY scripts/sccache.sh /scripts/
RUN sh /scripts/sccache.sh
@ -35,10 +35,7 @@ ENV RUST_CONFIGURE_ARGS \
--enable-extended \
--disable-docs \
--set target.x86_64-unknown-linux-musl.crt-static=false \
--build $HOSTS \
--set target.x86_64-unknown-linux-musl.cc=x86_64-linux-musl-gcc \
--set target.x86_64-unknown-linux-musl.cxx=x86_64-linux-musl-g++ \
--set target.x86_64-unknown-linux-musl.linker=x86_64-linux-musl-gcc
--build $HOSTS
# Newer binutils broke things on some vms/distros (i.e., linking against
# unknown relocs disabled by the following flag), so we need to go out of our
@ -49,4 +46,5 @@ ENV RUST_CONFIGURE_ARGS \
ENV CFLAGS_x86_64_unknown_linux_musl="-Wa,-mrelax-relocations=no -Wa,--compress-debug-sections=none \
-Wl,--compress-debug-sections=none"
# To run native tests replace `dist` below with `test`
ENV SCRIPT python2.7 ../x.py dist --build $HOSTS

View File

@ -45,6 +45,15 @@ cd -
ln -s $OUTPUT/$TARGET/lib/libc.so /lib/ld-musl-$ARCH.so.1
echo $OUTPUT/$TARGET/lib >> /etc/ld-musl-$ARCH.path
# Now when musl bootstraps itself create proper toolchain symlinks to make build and tests easier
if [ "$REPLACE_CC" = "1" ]; then
for exec in cc gcc; do
ln -s $TARGET-gcc /usr/local/bin/$exec
done
for exec in cpp c++ g++; do
ln -s $TARGET-g++ /usr/local/bin/$exec
done
fi
export CC=$TARGET-gcc
export CXX=$TARGET-g++

View File

@ -74,7 +74,9 @@ status_check() {
check_dispatch $1 beta nomicon src/doc/nomicon
check_dispatch $1 beta reference src/doc/reference
check_dispatch $1 beta rust-by-example src/doc/rust-by-example
check_dispatch $1 beta edition-guide src/doc/edition-guide
# Temporarily disabled until
# https://github.com/rust-lang/rust/issues/60459 is fixed.
# check_dispatch $1 beta edition-guide src/doc/edition-guide
check_dispatch $1 beta rls src/tools/rls
check_dispatch $1 beta rustfmt src/tools/rustfmt
check_dispatch $1 beta clippy-driver src/tools/clippy

@ -1 +1 @@
Subproject commit db919bc6bb9071566e9c4f05053672133eaac33e
Subproject commit 29fe982990e43b9367be0ff47abc82fb2123fd03

@ -1 +1 @@
Subproject commit c413d42a207bd082f801ec0137c31b71e4bfed4c
Subproject commit 581c6cccfaf995394ea9dcac362dc8e731c18558

@ -1 +1 @@
Subproject commit de3d55f521e657863df45260ebbca1b10527f662
Subproject commit 9858872bd1b7dbba5ec27dc30d34eba00acd7ef9

@ -1 +1 @@
Subproject commit fb29b147be4d9a1f8e24aba753a7e1de537abf61
Subproject commit c656171b749b7307f21371dd0d3278efee5573b8

@ -1 +1 @@
Subproject commit 2a2de9ce095979978ad7b582daecf94e4070b916
Subproject commit 862b669c395822bb0938781d74f860e5762ad4fb

@ -1 +1 @@
Subproject commit 1ff0f8e018838a710ebc0cc1a7bf74ebe73ad9f1
Subproject commit 811c697b232c611ed754d279ed20643a0c4096f6

@ -1 +1 @@
Subproject commit 99e1b1d53656be08654df399fc200584aebb50e4
Subproject commit 3cb727b62b953d59b4360d39aa68b6dc8f157655

View File

@ -17,28 +17,147 @@ to `#[cfg(verbose)]` and `#[cfg(feature = "serde")]` respectively.
## `-L`: add a directory to the library search path
When looking for external crates, a directory passed to this flag will be searched.
When looking for external crates or libraries, a directory passed to this flag
will be searched.
The kind of search path can optionally be specified with the form `-L
KIND=PATH` where `KIND` may be one of:
- `dependency` Only search for transitive dependencies in this directory.
- `crate` Only search for this crate's direct dependencies in this
directory.
- `native` — Only search for native libraries in this directory.
- `framework` Only search for macOS frameworks in this directory.
- `all` Search for all library kinds in this directory. This is the default
if `KIND` is not specified.
## `-l`: link the generated crate to a native library
This flag allows you to specify linking to a specific native library when building
a crate.
The kind of library can optionally be specified with the form `-l KIND=lib`
where `KIND` may be one of:
- `dylib` A native dynamic library.
- `static` A native static library (such as a `.a` archive).
- `framework` A macOS framework.
The kind of library can be specified in a [`#[link]`
attribute][link-attribute]. If the kind is not specified in the `link`
attribute or on the command-line, it will link a dynamic library if available,
otherwise it will use a static library. If the kind is specified on the
command-line, it will override the kind specified in a `link` attribute.
The name used in a `link` attribute may be overridden using the form `-l
ATTR_NAME:LINK_NAME` where `ATTR_NAME` is the name in the `link` attribute,
and `LINK_NAME` is the name of the actual library that will be linked.
[link-attribute]: ../reference/items/external-blocks.html#the-link-attribute
## `--crate-type`: a list of types of crates for the compiler to emit
This instructs `rustc` on which crate type to build.
This instructs `rustc` on which crate type to build. This flag accepts a
comma-separated list of values, and may be specified multiple times. The valid
crate types are:
- `lib` — Generates a library kind preferred by the compiler, currently
defaults to `rlib`.
- `rlib` — A Rust static library.
- `staticlib` — A native static library.
- `dylib` — A Rust dynamic library.
- `cdylib` — A native dynamic library.
- `bin` — A runnable executable program.
- `proc-macro` — Generates a format suitable for a procedural macro library
that may be loaded by the compiler.
The crate type may be specified with the [`crate_type` attribute][crate_type].
The `--crate-type` command-line value will override the `crate_type`
attribute.
More details may be found in the [linkage chapter] of the reference.
[linkage chapter]: ../reference/linkage.html
[crate_type]: ../reference/linkage.html
## `--crate-name`: specify the name of the crate being built
This informs `rustc` of the name of your crate.
## `--emit`: emit output other than a crate
## `--edition`: specify the edition to use
Instead of producing a crate, this flag can print out things like the assembly or LLVM-IR.
This flag takes a value of `2015` or `2018`. The default is `2015`. More
information about editions may be found in the [edition guide].
[edition guide]: ../edition-guide/introduction.html
## `--emit`: specifies the types of output files to generate
This flag controls the types of output files generated by the compiler. It
accepts a comma-separated list of values, and may be specified multiple times.
The valid emit kinds are:
- `asm` — Generates a file with the crate's assembly code. The default output
filename is `CRATE_NAME.s`.
- `dep-info` — Generates a file with Makefile syntax that indicates all the
source files that were loaded to generate the crate. The default output
filename is `CRATE_NAME.d`.
- `link` — Generates the crates specified by `--crate-type`. The default
output filenames depend on the crate type and platform. This is the default
if `--emit` is not specified.
- `llvm-bc` — Generates a binary file containing the [LLVM bitcode]. The
default output filename is `CRATE_NAME.bc`.
- `llvm-ir` — Generates a file containing [LLVM IR]. The default output
filename is `CRATE_NAME.ll`.
- `metadata` — Generates a file containing metadata about the crate. The
default output filename is `CRATE_NAME.rmeta`.
- `mir` — Generates a file containing rustc's mid-level intermediate
representation. The default output filename is `CRATE_NAME.mir`.
- `obj` — Generates a native object file. The default output filename is
`CRATE_NAME.o`.
The output filename can be set with the `-o` flag. A suffix may be added to
the filename with the `-C extra-filename` flag. The files are written to the
current directory unless the `--out-dir` flag is used. Each emission type may
also specify the output filename with the form `KIND=PATH`, which takes
precedence over the `-o` flag.
[LLVM bitcode]: https://llvm.org/docs/BitCodeFormat.html
[LLVM IR]: https://llvm.org/docs/LangRef.html
## `--print`: print compiler information
This flag prints out various information about the compiler.
This flag prints out various information about the compiler. This flag may be
specified multiple times, and the information is printed in the order the
flags are specified. Specifying a `--print` flag will usually disable the
`--emit` step and will only print the requested information. The valid types
of print values are:
- `crate-name` — The name of the crate.
- `file-names` — The names of the files created by the `link` emit kind.
- `sysroot` — Path to the sysroot.
- `cfg` — List of cfg values. See [conditional compilation] for more
information about cfg values.
- `target-list` — List of known targets. The target may be selected with the
`--target` flag.
- `target-cpus` — List of available CPU values for the current target. The
target CPU may be selected with the `-C target-cpu=val` flag.
- `target-features` — List of available target features for the current
target. Target features may be enabled with the `-C target-feature=val`
flag.
- `relocation-models` — List of relocation models. Relocation models may be
selected with the `-C relocation-model=val` flag.
- `code-models` — List of code models. Code models may be selected with the
`-C code-model=val` flag.
- `tls-models` — List of Thread Local Storage models supported. The model may
be selected with the `-Z tls-model=val` flag.
- `native-static-libs` — This may be used when creating a `staticlib` crate
type. If this is the only flag, it will perform a full compilation and
include a diagnostic note that indicates the linker flags to use when
linking the resulting static library. The note starts with the text
`native-static-libs:` to make it easier to fetch the output.
[conditional compilation]: ../reference/conditional-compilation.html
## `-g`: include debug information
@ -54,7 +173,8 @@ This flag controls the output filename.
## `--out-dir`: directory to write the output in
The outputted crate will be written to this directory.
The outputted crate will be written to this directory. This flag is ignored if
the `-o` flag is used.
## `--explain`: provide a detailed explanation of an error message
@ -111,8 +231,9 @@ This flag, when combined with other flags, makes them produce extra output.
## `--extern`: specify where an external library is located
This flag allows you to pass the name and location of an external crate that will
be linked into the crate you're buildling.
This flag allows you to pass the name and location of an external crate that
will be linked into the crate you are building. This flag may be specified
multiple times. The format of the value should be `CRATENAME=PATH`.
## `--sysroot`: Override the system root
@ -121,8 +242,32 @@ distribution; this flag allows that to be overridden.
## `--error-format`: control how errors are produced
This flag lets you control the format of errors.
This flag lets you control the format of messages. Messages are printed to
stderr. The valid options are:
- `human` — Human-readable output. This is the default.
- `json` — Structured JSON output.
- `short` — Short, one-line messages.
## `--color`: configure coloring of output
This flag lets you control color settings of the output.
This flag lets you control color settings of the output. The valid options
are:
- `auto` — Use colors if output goes to a tty. This is the default.
- `always` Always use colors.
- `never` Never colorize output.
## `--remap-path-prefix`: remap source names in output
Remap source path prefixes in all output, including compiler diagnostics,
debug information, macro expansions, etc. It takes a value of the form
`FROM=TO` where a path prefix equal to `FROM` is rewritten to the value `TO`.
The `FROM` may itself contain an `=` symbol, but the `TO` value may not. This
flag may be specified multiple times.
This is useful for normalizing build products, for example by removing the
current directory out of pathnames emitted into the object files. The
replacement is purely textual, with no consideration of the current system's
pathname syntax. For example `--remap-path-prefix foo=bar` will match
`foo/lib.rs` but not `./foo/lib.rs`.

View File

@ -21,9 +21,9 @@ Here's a list of each lint group, and the lints that they are made up of:
| edition-2018 | Lints that will be turned into errors in Rust 2018 | tyvar-behind-raw-pointer |
| rust-2018-idioms | Lints to nudge you toward idiomatic features of Rust 2018 | bare-trait-object, unreachable-pub |
| unused | These lints detect things being declared but not used | unused-imports, unused-variables, unused-assignments, dead-code, unused-mut, unreachable-code, unreachable-patterns, unused-must-use, unused-unsafe, path-statements, unused-attributes, unused-macros, unused-allocation, unused-doc-comment, unused-extern-crates, unused-features, unused-parens |
| future-incompatible | Lints that detect code that has future-compatibility problems | private-in-public, pub-use-of-private-extern-crate, patterns-in-fns-without-body, safe-extern-statics, invalid-type-param-default, legacy-directory-ownership, legacy-imports, legacy-constructor-visibility, missing-fragment-specifier, illegal-floating-point-literal-pattern, anonymous-parameters, parenthesized-params-in-types-and-modules, late-bound-lifetime-arguments, safe-packed-borrows, incoherent-fundamental-impls, tyvar-behind-raw-pointer, unstable-name-collision |
| future-incompatible | Lints that detect code that has future-compatibility problems | private-in-public, pub-use-of-private-extern-crate, patterns-in-fns-without-body, safe-extern-statics, invalid-type-param-default, legacy-directory-ownership, legacy-imports, legacy-constructor-visibility, missing-fragment-specifier, illegal-floating-point-literal-pattern, anonymous-parameters, parenthesized-params-in-types-and-modules, late-bound-lifetime-arguments, safe-packed-borrows, tyvar-behind-raw-pointer, unstable-name-collision |
Additionally, there's a `bad-style` lint group that's a deprecated alias for `nonstandard-style`.
Finally, you can also see the table above by invoking `rustc -W help`. This will give you the exact values for the specific
compiler you have installed.
compiler you have installed.

View File

@ -222,44 +222,3 @@ error: invalid `crate_type` value
| ^^^^^^^^^^^^^^^^^^^^
|
```
## incoherent-fundamental-impls
This lint detects potentially-conflicting impls that were erroneously allowed. Some
example code that triggers this lint:
```rust,ignore
pub trait Trait1<X> {
type Output;
}
pub trait Trait2<X> {}
pub struct A;
impl<X, T> Trait1<X> for T where T: Trait2<X> {
type Output = ();
}
impl<X> Trait1<Box<X>> for A {
type Output = i32;
}
```
This will produce:
```text
error: conflicting implementations of trait `Trait1<std::boxed::Box<_>>` for type `A`: (E0119)
--> src/main.rs:13:1
|
9 | impl<X, T> Trait1<X> for T where T: Trait2<X> {
| --------------------------------------------- first implementation here
...
13 | impl<X> Trait1<Box<X>> for A {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation for `A`
|
= note: #[deny(incoherent_fundamental_impls)] on by default
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
= note: for more information, see issue #46205 <https://github.com/rust-lang/rust/issues/46205>
= note: downstream crates may implement trait `Trait2<std::boxed::Box<_>>` for type `A`
```

View File

@ -92,6 +92,21 @@ the tracking issue.
#![doc(issue_tracker_base_url = "https://github.com/rust-lang/rust/issues/")]
```
### `html_root_url`
The `#[doc(html_root_url = "…")]` attribute value indicates the URL for
generating links to external crates. When rustdoc needs to generate a link to
an item in an external crate, it will first check if the extern crate has been
documented locally on-disk, and if so link directly to it. Failing that, it
will use the URL given by the `--extern-html-root-url` command-line flag if
available. If that is not available, then it will use the `html_root_url`
value in the extern crate if it is available. If that is not available, then
the extern items will not be linked.
```rust,ignore
#![doc(html_root_url = "https://docs.rs/serde/1.0")]
```
### `html_no_source`
By default, `rustdoc` will include the source code of your program, with links

View File

@ -98,21 +98,21 @@ documentation for them as well!
`rustdoc` can also generate HTML from standalone Markdown files. Let's
give it a try: create a `README.md` file with these contents:
```text
# Docs
````text
# Docs
This is a project to test out `rustdoc`.
This is a project to test out `rustdoc`.
[Here is a link!](https://www.rust-lang.org)
[Here is a link!](https://www.rust-lang.org)
## Subheading
## Subheading
```rust
fn foo() -> i32 {
1 + 1
}
```
```rust
fn foo() -> i32 {
1 + 1
}
```
````
And call `rustdoc` on it:

View File

@ -7,11 +7,11 @@
<Item Name="[capacity]" ExcludeView="simple">buf.cap</Item>
<ArrayItems>
<Size>len</Size>
<ValuePointer>buf.ptr.pointer.__0</ValuePointer>
<ValuePointer>buf.ptr.pointer</ValuePointer>
</ArrayItems>
</Expand>
</Type>
<Type Name="alloc::vec_deque::VecDeque&lt;*&gt;">
<Type Name="alloc::collections::vec_deque::VecDeque&lt;*&gt;">
<DisplayString>{{ size={tail &lt;= head ? head - tail : buf.cap - tail + head} }}</DisplayString>
<Expand>
<Item Name="[size]" ExcludeView="simple">tail &lt;= head ? head - tail : buf.cap - tail + head</Item>
@ -24,19 +24,19 @@
<If Condition="i == head">
<Break/>
</If>
<Item>buf.ptr.pointer.__0 + i</Item>
<Item>buf.ptr.pointer[i]</Item>
<Exec>i = (i + 1 == buf.cap ? 0 : i + 1)</Exec>
</Loop>
</CustomListItems>
</Expand>
</Type>
<Type Name="alloc::linked_list::LinkedList&lt;*&gt;">
<Type Name="alloc::collections::linked_list::LinkedList&lt;*&gt;">
<DisplayString>{{ size={len} }}</DisplayString>
<Expand>
<LinkedListItems>
<Size>len</Size>
<HeadPointer>*(alloc::linked_list::Node&lt;$T1&gt; **)&amp;head</HeadPointer>
<NextPointer>*(alloc::linked_list::Node&lt;$T1&gt; **)&amp;next</NextPointer>
<HeadPointer>*(alloc::collections::linked_list::Node&lt;$T1&gt; **)&amp;head</HeadPointer>
<NextPointer>*(alloc::collections::linked_list::Node&lt;$T1&gt; **)&amp;next</NextPointer>
<ValueNode>element</ValueNode>
</LinkedListItems>
</Expand>

View File

@ -1,15 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
<Type Name="core::ptr::Unique&lt;*&gt;">
<DisplayString>{{ Unique {*pointer.__0} }}</DisplayString>
<DisplayString>{{ Unique {pointer} }}</DisplayString>
<Expand>
<Item Name="[ptr]">pointer.__0</Item>
<Item Name="[ptr]">pointer</Item>
</Expand>
</Type>
<Type Name="core::ptr::Shared&lt;*&gt;">
<DisplayString>{{ Shared {*pointer.__0} }}</DisplayString>
<DisplayString>{{ Shared {pointer} }}</DisplayString>
<Expand>
<Item Name="[ptr]">pointer.__0</Item>
<Item Name="[ptr]">pointer</Item>
</Expand>
</Type>
<Type Name="core::option::Option&lt;*&gt;">

View File

@ -33,3 +33,4 @@ harness = false
[features]
compiler-builtins-mem = ['compiler_builtins/mem']
compiler-builtins-c = ["compiler_builtins/c"]

View File

@ -37,6 +37,8 @@ extern "Rust" {
///
/// Note: while this type is unstable, the functionality it provides can be
/// accessed through the [free functions in `alloc`](index.html#functions).
///
/// [`Alloc`]: trait.Alloc.html
#[unstable(feature = "allocator_api", issue = "32838")]
#[derive(Copy, Clone, Default, Debug)]
pub struct Global;
@ -54,6 +56,10 @@ pub struct Global;
///
/// See [`GlobalAlloc::alloc`].
///
/// [`Global`]: struct.Global.html
/// [`Alloc`]: trait.Alloc.html
/// [`GlobalAlloc::alloc`]: trait.GlobalAlloc.html#tymethod.alloc
///
/// # Examples
///
/// ```
@ -87,6 +93,10 @@ pub unsafe fn alloc(layout: Layout) -> *mut u8 {
/// # Safety
///
/// See [`GlobalAlloc::dealloc`].
///
/// [`Global`]: struct.Global.html
/// [`Alloc`]: trait.Alloc.html
/// [`GlobalAlloc::dealloc`]: trait.GlobalAlloc.html#tymethod.dealloc
#[stable(feature = "global_alloc", since = "1.28.0")]
#[inline]
pub unsafe fn dealloc(ptr: *mut u8, layout: Layout) {
@ -105,6 +115,10 @@ pub unsafe fn dealloc(ptr: *mut u8, layout: Layout) {
/// # Safety
///
/// See [`GlobalAlloc::realloc`].
///
/// [`Global`]: struct.Global.html
/// [`Alloc`]: trait.Alloc.html
/// [`GlobalAlloc::realloc`]: trait.GlobalAlloc.html#method.realloc
#[stable(feature = "global_alloc", since = "1.28.0")]
#[inline]
pub unsafe fn realloc(ptr: *mut u8, layout: Layout, new_size: usize) -> *mut u8 {
@ -124,6 +138,10 @@ pub unsafe fn realloc(ptr: *mut u8, layout: Layout, new_size: usize) -> *mut u8
///
/// See [`GlobalAlloc::alloc_zeroed`].
///
/// [`Global`]: struct.Global.html
/// [`Alloc`]: trait.Alloc.html
/// [`GlobalAlloc::alloc_zeroed`]: trait.GlobalAlloc.html#method.alloc_zeroed
///
/// # Examples
///
/// ```

View File

@ -231,6 +231,20 @@ use super::SpecExtend;
/// assert_eq!(heap.pop(), Some(Reverse(5)));
/// assert_eq!(heap.pop(), None);
/// ```
///
/// # Time complexity
///
/// | [push] | [pop] | [peek]/[peek\_mut] |
/// |--------|----------|--------------------|
/// | O(1)~ | O(log n) | O(1) |
///
/// The value for `push` is an expected cost; the method documentation gives a
/// more detailed analysis.
///
/// [push]: #method.push
/// [pop]: #method.pop
/// [peek]: #method.peek
/// [peek\_mut]: #method.peek_mut
#[stable(feature = "rust1", since = "1.0.0")]
pub struct BinaryHeap<T> {
data: Vec<T>,
@ -384,6 +398,10 @@ impl<T: Ord> BinaryHeap<T> {
/// }
/// assert_eq!(heap.peek(), Some(&2));
/// ```
///
/// # Time complexity
///
/// Cost is O(1) in the worst case.
#[stable(feature = "binary_heap_peek_mut", since = "1.12.0")]
pub fn peek_mut(&mut self) -> Option<PeekMut<'_, T>> {
if self.is_empty() {
@ -411,6 +429,11 @@ impl<T: Ord> BinaryHeap<T> {
/// assert_eq!(heap.pop(), Some(1));
/// assert_eq!(heap.pop(), None);
/// ```
///
/// # Time complexity
///
/// The worst case cost of `pop` on a heap containing *n* elements is O(log
/// n).
#[stable(feature = "rust1", since = "1.0.0")]
pub fn pop(&mut self) -> Option<T> {
self.data.pop().map(|mut item| {
@ -438,6 +461,22 @@ impl<T: Ord> BinaryHeap<T> {
/// assert_eq!(heap.len(), 3);
/// assert_eq!(heap.peek(), Some(&5));
/// ```
///
/// # Time complexity
///
/// The expected cost of `push`, averaged over every possible ordering of
/// the elements being pushed, and over a sufficiently large number of
/// pushes, is O(1). This is the most meaningful cost metric when pushing
/// elements that are *not* already in any sorted pattern.
///
/// The time complexity degrades if elements are pushed in predominantly
/// ascending order. In the worst case, elements are pushed in ascending
/// sorted order and the amortized cost per push is O(log n) against a heap
/// containing *n* elements.
///
/// The worst case cost of a *single* call to `push` is O(n). The worst case
/// occurs when capacity is exhausted and needs a resize. The resize cost
/// has been amortized in the previous figures.
#[stable(feature = "rust1", since = "1.0.0")]
pub fn push(&mut self, item: T) {
let old_len = self.len();
@ -650,6 +689,10 @@ impl<T> BinaryHeap<T> {
/// assert_eq!(heap.peek(), Some(&5));
///
/// ```
///
/// # Time complexity
///
/// Cost is O(1) in the worst case.
#[stable(feature = "rust1", since = "1.0.0")]
pub fn peek(&self) -> Option<&T> {
self.data.get(0)
@ -992,6 +1035,11 @@ impl<'a, T> Iterator for Iter<'a, T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<&'a T> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1047,6 +1095,11 @@ impl<T> Iterator for IntoIter<T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<T> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1093,6 +1146,11 @@ impl<T> Iterator for Drain<'_, T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<T> {
self.next_back()
}
}
#[stable(feature = "drain", since = "1.6.0")]

View File

@ -1193,6 +1193,11 @@ impl<'a, K: 'a, V: 'a> Iterator for Iter<'a, K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
(self.length, Some(self.length))
}
#[inline]
fn last(mut self) -> Option<(&'a K, &'a V)> {
self.next_back()
}
}
#[stable(feature = "fused", since = "1.26.0")]
@ -1253,6 +1258,11 @@ impl<'a, K: 'a, V: 'a> Iterator for IterMut<'a, K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
(self.length, Some(self.length))
}
#[inline]
fn last(mut self) -> Option<(&'a K, &'a mut V)> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1359,6 +1369,11 @@ impl<K, V> Iterator for IntoIter<K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
(self.length, Some(self.length))
}
#[inline]
fn last(mut self) -> Option<(K, V)> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1421,6 +1436,11 @@ impl<'a, K, V> Iterator for Keys<'a, K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<&'a K> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1458,6 +1478,11 @@ impl<'a, K, V> Iterator for Values<'a, K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<&'a V> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1495,6 +1520,11 @@ impl<'a, K, V> Iterator for Range<'a, K, V> {
unsafe { Some(self.next_unchecked()) }
}
}
#[inline]
fn last(mut self) -> Option<(&'a K, &'a V)> {
self.next_back()
}
}
#[stable(feature = "map_values_mut", since = "1.10.0")]
@ -1508,6 +1538,11 @@ impl<'a, K, V> Iterator for ValuesMut<'a, K, V> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<&'a mut V> {
self.next_back()
}
}
#[stable(feature = "map_values_mut", since = "1.10.0")]
@ -1626,6 +1661,11 @@ impl<'a, K, V> Iterator for RangeMut<'a, K, V> {
unsafe { Some(self.next_unchecked()) }
}
}
#[inline]
fn last(mut self) -> Option<(&'a K, &'a mut V)> {
self.next_back()
}
}
impl<'a, K, V> RangeMut<'a, K, V> {

View File

@ -1019,6 +1019,11 @@ impl<'a, T> Iterator for Iter<'a, T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<&'a T> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<'a, T> DoubleEndedIterator for Iter<'a, T> {
@ -1044,6 +1049,11 @@ impl<T> Iterator for IntoIter<T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<T> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
impl<T> DoubleEndedIterator for IntoIter<T> {
@ -1073,6 +1083,11 @@ impl<'a, T> Iterator for Range<'a, T> {
fn next(&mut self) -> Option<&'a T> {
self.iter.next().map(|(k, _)| k)
}
#[inline]
fn last(mut self) -> Option<&'a T> {
self.next_back()
}
}
#[stable(feature = "btree_range", since = "1.17.0")]

View File

@ -1835,8 +1835,8 @@ impl<T> VecDeque<T> {
/// Retains only the elements specified by the predicate.
///
/// In other words, remove all elements `e` such that `f(&e)` returns false.
/// This method operates in place and preserves the order of the retained
/// elements.
/// This method operates in place, visiting each element exactly once in the
/// original order, and preserves the order of the retained elements.
///
/// # Examples
///
@ -1848,6 +1848,20 @@ impl<T> VecDeque<T> {
/// buf.retain(|&x| x%2 == 0);
/// assert_eq!(buf, [2, 4]);
/// ```
///
/// The exact order may be useful for tracking external state, like an index.
///
/// ```
/// use std::collections::VecDeque;
///
/// let mut buf = VecDeque::new();
/// buf.extend(1..6);
///
/// let keep = [false, true, true, false, true];
/// let mut i = 0;
/// buf.retain(|_| (keep[i], i += 1).0);
/// assert_eq!(buf, [2, 3, 5]);
/// ```
#[stable(feature = "vec_deque_retain", since = "1.4.0")]
pub fn retain<F>(&mut self, mut f: F)
where F: FnMut(&T) -> bool
@ -1934,8 +1948,6 @@ impl<T> VecDeque<T> {
/// # Examples
///
/// ```
/// #![feature(vecdeque_rotate)]
///
/// use std::collections::VecDeque;
///
/// let mut buf: VecDeque<_> = (0..10).collect();
@ -1949,7 +1961,7 @@ impl<T> VecDeque<T> {
/// }
/// assert_eq!(buf, [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
/// ```
#[unstable(feature = "vecdeque_rotate", issue = "56686")]
#[stable(feature = "vecdeque_rotate", since = "1.36.0")]
pub fn rotate_left(&mut self, mid: usize) {
assert!(mid <= self.len());
let k = self.len() - mid;
@ -1979,8 +1991,6 @@ impl<T> VecDeque<T> {
/// # Examples
///
/// ```
/// #![feature(vecdeque_rotate)]
///
/// use std::collections::VecDeque;
///
/// let mut buf: VecDeque<_> = (0..10).collect();
@ -1994,7 +2004,7 @@ impl<T> VecDeque<T> {
/// }
/// assert_eq!(buf, [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
/// ```
#[unstable(feature = "vecdeque_rotate", issue = "56686")]
#[stable(feature = "vecdeque_rotate", since = "1.36.0")]
pub fn rotate_right(&mut self, k: usize) {
assert!(k <= self.len());
let mid = self.len() - k;

View File

@ -109,7 +109,7 @@
#![feature(rustc_const_unstable)]
#![feature(const_vec_new)]
#![feature(slice_partition_dedup)]
#![feature(maybe_uninit, maybe_uninit_slice, maybe_uninit_array)]
#![feature(maybe_uninit_extra, maybe_uninit_slice, maybe_uninit_array)]
#![feature(alloc_layout_extra)]
#![feature(try_trait)]
#![feature(iter_nth_back)]

View File

@ -932,6 +932,11 @@ impl<T: ?Sized + PartialEq> RcEqIdent<T> for Rc<T> {
}
}
/// We're doing this specialization here, and not as a more general optimization on `&T`, because it
/// would otherwise add a cost to all equality checks on refs. We assume that `Rc`s are used to
/// store large values, that are slow to clone, but also heavy to check for equality, causing this
/// cost to pay off more easily. It's also more likely to have two `Rc` clones, that point to
/// the same value, than two `&T`s.
#[stable(feature = "rust1", since = "1.0.0")]
impl<T: ?Sized + Eq> RcEqIdent<T> for Rc<T> {
#[inline]

View File

@ -1200,8 +1200,8 @@ impl String {
/// Retains only the characters specified by the predicate.
///
/// In other words, remove all characters `c` such that `f(c)` returns `false`.
/// This method operates in place and preserves the order of the retained
/// characters.
/// This method operates in place, visiting each character exactly once in the
/// original order, and preserves the order of the retained characters.
///
/// # Examples
///
@ -1212,6 +1212,16 @@ impl String {
///
/// assert_eq!(s, "foobar");
/// ```
///
/// The exact order may be useful for tracking external state, like an index.
///
/// ```
/// let mut s = String::from("abcde");
/// let keep = [false, true, true, false, true];
/// let mut i = 0;
/// s.retain(|_| (keep[i], i += 1).0);
/// assert_eq!(s, "bce");
/// ```
#[inline]
#[stable(feature = "string_retain", since = "1.26.0")]
pub fn retain<F>(&mut self, mut f: F)
@ -2179,6 +2189,14 @@ impl From<&str> for String {
}
}
#[stable(feature = "from_ref_string", since = "1.35.0")]
impl From<&String> for String {
#[inline]
fn from(s: &String) -> String {
s.clone()
}
}
// note: test pulls in libstd, which causes errors here
#[cfg(not(test))]
#[stable(feature = "string_from_box", since = "1.18.0")]
@ -2367,6 +2385,10 @@ impl Iterator for Drain<'_> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<char> {
self.next_back()
}
}
#[stable(feature = "drain", since = "1.6.0")]

View File

@ -1377,6 +1377,11 @@ impl<T: ?Sized + PartialEq> ArcEqIdent<T> for Arc<T> {
}
}
/// We're doing this specialization here, and not as a more general optimization on `&T`, because it
/// would otherwise add a cost to all equality checks on refs. We assume that `Arc`s are used to
/// store large values, that are slow to clone, but also heavy to check for equality, causing this
/// cost to pay off more easily. It's also more likely to have two `Arc` clones, that point to
/// the same value, than two `&T`s.
#[stable(feature = "rust1", since = "1.0.0")]
impl<T: ?Sized + Eq> ArcEqIdent<T> for Arc<T> {
#[inline]

View File

@ -143,8 +143,8 @@ fn test_union() {
#[test]
// Only tests the simple function definition with respect to intersection
fn test_is_disjoint() {
let one = [1].into_iter().collect::<BTreeSet<_>>();
let two = [2].into_iter().collect::<BTreeSet<_>>();
let one = [1].iter().collect::<BTreeSet<_>>();
let two = [2].iter().collect::<BTreeSet<_>>();
assert!(one.is_disjoint(&two));
}

View File

@ -6,7 +6,6 @@
#![feature(repeat_generic_slice)]
#![feature(try_reserve)]
#![feature(unboxed_closures)]
#![feature(vecdeque_rotate)]
#![deny(rust_2018_idioms)]
use std::hash::{Hash, Hasher};

View File

@ -937,8 +937,8 @@ impl<T> Vec<T> {
/// Retains only the elements specified by the predicate.
///
/// In other words, remove all elements `e` such that `f(&e)` returns `false`.
/// This method operates in place and preserves the order of the retained
/// elements.
/// This method operates in place, visiting each element exactly once in the
/// original order, and preserves the order of the retained elements.
///
/// # Examples
///
@ -947,6 +947,16 @@ impl<T> Vec<T> {
/// vec.retain(|&x| x%2 == 0);
/// assert_eq!(vec, [2, 4]);
/// ```
///
/// The exact order may be useful for tracking external state, like an index.
///
/// ```
/// let mut vec = vec![1, 2, 3, 4, 5];
/// let keep = [false, true, true, false, true];
/// let mut i = 0;
/// vec.retain(|_| (keep[i], i += 1).0);
/// assert_eq!(vec, [2, 3, 5]);
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
pub fn retain<F>(&mut self, mut f: F)
where F: FnMut(&T) -> bool
@ -2385,6 +2395,11 @@ impl<T> Iterator for IntoIter<T> {
fn count(self) -> usize {
self.len()
}
#[inline]
fn last(mut self) -> Option<T> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -2504,6 +2519,11 @@ impl<T> Iterator for Drain<'_, T> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
#[inline]
fn last(mut self) -> Option<T> {
self.next_back()
}
}
#[stable(feature = "drain", since = "1.6.0")]
@ -2573,6 +2593,10 @@ impl<I: Iterator> Iterator for Splice<'_, I> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.drain.size_hint()
}
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "vec_splice", since = "1.21.0")]

View File

@ -99,7 +99,7 @@ impl Layout {
/// [`Layout::from_size_align`](#method.from_size_align).
#[stable(feature = "alloc_layout", since = "1.28.0")]
#[inline]
pub unsafe fn from_size_align_unchecked(size: usize, align: usize) -> Self {
pub const unsafe fn from_size_align_unchecked(size: usize, align: usize) -> Self {
Layout { size_: size, align_: NonZeroUsize::new_unchecked(align) }
}
@ -480,7 +480,7 @@ pub unsafe trait GlobalAlloc {
/// this allocator,
///
/// * `layout` must be the same layout that was used
/// to allocated that block of memory,
/// to allocate that block of memory,
#[stable(feature = "global_alloc", since = "1.28.0")]
unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout);
@ -535,7 +535,7 @@ pub unsafe trait GlobalAlloc {
/// * `ptr` must be currently allocated via this allocator,
///
/// * `layout` must be the same layout that was used
/// to allocated that block of memory,
/// to allocate that block of memory,
///
/// * `new_size` must be greater than zero.
///

View File

@ -8,7 +8,7 @@
use crate::borrow::{Borrow, BorrowMut};
use crate::cmp::Ordering;
use crate::convert::TryFrom;
use crate::convert::{Infallible, TryFrom};
use crate::fmt;
use crate::hash::{Hash, self};
use crate::marker::Unsize;
@ -74,6 +74,13 @@ impl TryFromSliceError {
}
}
#[stable(feature = "try_from_slice_error", since = "1.36.0")]
impl From<Infallible> for TryFromSliceError {
fn from(x: Infallible) -> TryFromSliceError {
match x {}
}
}
macro_rules! __impl_slice_eq1 {
($Lhs: ty, $Rhs: ty) => {
__impl_slice_eq1! { $Lhs, $Rhs, Sized }

View File

@ -117,6 +117,8 @@ impl Iterator for EscapeDefault {
type Item = u8;
fn next(&mut self) -> Option<u8> { self.range.next().map(|i| self.data[i]) }
fn size_hint(&self) -> (usize, Option<usize>) { self.range.size_hint() }
#[inline]
fn last(mut self) -> Option<u8> { self.next_back() }
}
#[stable(feature = "rust1", since = "1.0.0")]
impl DoubleEndedIterator for EscapeDefault {

View File

@ -104,7 +104,6 @@ pub const fn identity<T>(x: T) -> T { x }
/// If you need to do a costly conversion it is better to implement [`From`] with type
/// `&T` or write a custom function.
///
///
/// `AsRef` has the same signature as [`Borrow`], but `Borrow` is different in few aspects:
///
/// - Unlike `AsRef`, `Borrow` has a blanket impl for any `T`, and can be used to accept either
@ -133,7 +132,7 @@ pub const fn identity<T>(x: T) -> T { x }
/// converted a the specified type `T`.
///
/// For example: By creating a generic function that takes an `AsRef<str>` we express that we
/// want to accept all references that can be converted to &str as an argument.
/// want to accept all references that can be converted to `&str` as an argument.
/// Since both [`String`] and `&str` implement `AsRef<str>` we can accept both as input argument.
///
/// [`String`]: ../../std/string/struct.String.html
@ -149,7 +148,6 @@ pub const fn identity<T>(x: T) -> T { x }
/// let s = "hello".to_string();
/// is_hello(s);
/// ```
///
#[stable(feature = "rust1", since = "1.0.0")]
pub trait AsRef<T: ?Sized> {
/// Performs the conversion.
@ -182,6 +180,7 @@ pub trait AsRef<T: ?Sized> {
/// write a function `add_one`that takes all arguments that can be converted to `&mut u64`.
/// Because [`Box<T>`] implements `AsMut<T>` `add_one` accepts arguments of type
/// `&mut Box<u64>` as well:
///
/// ```
/// fn add_one<T: AsMut<u64>>(num: &mut T) {
/// *num.as_mut() += 1;
@ -191,8 +190,8 @@ pub trait AsRef<T: ?Sized> {
/// add_one(&mut boxed_num);
/// assert_eq!(*boxed_num, 1);
/// ```
/// [`Box<T>`]: ../../std/boxed/struct.Box.html
///
/// [`Box<T>`]: ../../std/boxed/struct.Box.html
#[stable(feature = "rust1", since = "1.0.0")]
pub trait AsMut<T: ?Sized> {
/// Performs the conversion.
@ -203,9 +202,9 @@ pub trait AsMut<T: ?Sized> {
/// A value-to-value conversion that consumes the input value. The
/// opposite of [`From`].
///
/// One should only implement [`Into`] if a conversion to a type outside the current crate is
/// required. Otherwise one should always prefer implementing [`From`] over [`Into`] because
/// implementing [`From`] automatically provides one with a implementation of [`Into`] thanks to
/// One should only implement `Into` if a conversion to a type outside the current crate is
/// required. Otherwise one should always prefer implementing [`From`] over `Into` because
/// implementing [`From`] automatically provides one with a implementation of `Into` thanks to
/// the blanket implementation in the standard library. [`From`] cannot do these type of
/// conversions because of Rust's orphaning rules.
///
@ -213,8 +212,8 @@ pub trait AsMut<T: ?Sized> {
///
/// # Generic Implementations
///
/// - [`From<T>`]` for U` implies `Into<U> for T`
/// - [`Into`]` is reflexive, which means that `Into<T> for T` is implemented
/// - [`From`]`<T> for U` implies `Into<U> for T`
/// - `Into` is reflexive, which means that `Into<T> for T` is implemented
///
/// # Implementing `Into` for conversions to external types
///
@ -273,7 +272,7 @@ pub trait AsMut<T: ?Sized> {
/// [`Option<T>`]: ../../std/option/enum.Option.html
/// [`Result<T, E>`]: ../../std/result/enum.Result.html
/// [`String`]: ../../std/string/struct.String.html
/// [From]: trait.From.html
/// [`From`]: trait.From.html
/// [`into`]: trait.Into.html#tymethod.into
#[stable(feature = "rust1", since = "1.0.0")]
pub trait Into<T>: Sized {
@ -285,18 +284,18 @@ pub trait Into<T>: Sized {
/// Used to do value-to-value conversions while consuming the input value. It is the reciprocal of
/// [`Into`].
///
/// One should always prefer implementing [`From`] over [`Into`]
/// because implementing [`From`] automatically provides one with a implementation of [`Into`]
/// One should always prefer implementing `From` over [`Into`]
/// because implementing `From` automatically provides one with a implementation of [`Into`]
/// thanks to the blanket implementation in the standard library.
///
/// Only implement [`Into`] if a conversion to a type outside the current crate is required.
/// [`From`] cannot do these type of conversions because of Rust's orphaning rules.
/// `From` cannot do these type of conversions because of Rust's orphaning rules.
/// See [`Into`] for more details.
///
/// Prefer using [`Into`] over using [`From`] when specifying trait bounds on a generic function.
/// Prefer using [`Into`] over using `From` when specifying trait bounds on a generic function.
/// This way, types that directly implement [`Into`] can be used as arguments as well.
///
/// The [`From`] is also very useful when performing error handling. When constructing a function
/// The `From` is also very useful when performing error handling. When constructing a function
/// that is capable of failing, the return type will generally be of the form `Result<T, E>`.
/// The `From` trait simplifies error handling by allowing a function to return a single error type
/// that encapsulate multiple error types. See the "Examples" section and [the book][book] for more
@ -306,14 +305,15 @@ pub trait Into<T>: Sized {
///
/// # Generic Implementations
///
/// - [`From<T>`]` for U` implies [`Into<U>`]` for T`
/// - [`From`] is reflexive, which means that `From<T> for T` is implemented
/// - `From<T> for U` implies [`Into`]`<U> for T`
/// - `From` is reflexive, which means that `From<T> for T` is implemented
///
/// # Examples
///
/// [`String`] implements `From<&str>`:
///
/// An explicit conversion from a &str to a String is done as follows:
/// An explicit conversion from a `&str` to a String is done as follows:
///
/// ```
/// let string = "hello".to_string();
/// let other_string = String::from("hello");
@ -361,7 +361,7 @@ pub trait Into<T>: Sized {
/// [`Option<T>`]: ../../std/option/enum.Option.html
/// [`Result<T, E>`]: ../../std/result/enum.Result.html
/// [`String`]: ../../std/string/struct.String.html
/// [`Into<U>`]: trait.Into.html
/// [`Into`]: trait.Into.html
/// [`from`]: trait.From.html#tymethod.from
/// [book]: ../../book/ch09-00-error-handling.html
#[stable(feature = "rust1", since = "1.0.0")]
@ -422,7 +422,7 @@ pub trait TryInto<T>: Sized {
///
/// # Generic Implementations
///
/// - `TryFrom<T> for U` implies [`TryInto<U>`]` for T`
/// - `TryFrom<T> for U` implies [`TryInto`]`<U> for T`
/// - [`try_from`] is reflexive, which means that `TryFrom<T> for T`
/// is implemented and cannot fail -- the associated `Error` type for
/// calling `T::try_from()` on a value of type `T` is `Infallible`.

View File

@ -886,7 +886,7 @@ pub trait Pointer {
///
/// # Examples
///
/// Basic usage with `i32`:
/// Basic usage with `f64`:
///
/// ```
/// let x = 42.0; // 42.0 is '4.2e1' in scientific notation
@ -929,7 +929,7 @@ pub trait LowerExp {
///
/// # Examples
///
/// Basic usage with `f32`:
/// Basic usage with `f64`:
///
/// ```
/// let x = 42.0; // 42.0 is '4.2E1' in scientific notation

View File

@ -23,7 +23,7 @@ use crate::task::{Context, Poll};
/// When using a future, you generally won't call `poll` directly, but instead
/// `await!` the value.
#[doc(spotlight)]
#[must_use = "futures do nothing unless polled"]
#[must_use = "futures do nothing unless you `.await` or poll them"]
#[stable(feature = "futures_api", since = "1.36.0")]
pub trait Future {
/// The type of value produced on completion.

View File

@ -73,6 +73,11 @@ impl<I> Iterator for Rev<I> where I: DoubleEndedIterator {
{
self.iter.position(predicate)
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]

View File

@ -356,7 +356,7 @@ pub trait Iterator {
///
/// ```
/// let a = [0, 1, 2, 3, 4, 5];
/// let mut iter = a.into_iter().step_by(2);
/// let mut iter = a.iter().step_by(2);
///
/// assert_eq!(iter.next(), Some(&0));
/// assert_eq!(iter.next(), Some(&2));
@ -531,7 +531,7 @@ pub trait Iterator {
/// ```
/// let a = [1, 2, 3];
///
/// let mut iter = a.into_iter().map(|x| 2 * x);
/// let mut iter = a.iter().map(|x| 2 * x);
///
/// assert_eq!(iter.next(), Some(2));
/// assert_eq!(iter.next(), Some(4));
@ -620,7 +620,7 @@ pub trait Iterator {
/// ```
/// let a = [0i32, 1, 2];
///
/// let mut iter = a.into_iter().filter(|x| x.is_positive());
/// let mut iter = a.iter().filter(|x| x.is_positive());
///
/// assert_eq!(iter.next(), Some(&1));
/// assert_eq!(iter.next(), Some(&2));
@ -634,7 +634,7 @@ pub trait Iterator {
/// ```
/// let a = [0, 1, 2];
///
/// let mut iter = a.into_iter().filter(|x| **x > 1); // need two *s!
/// let mut iter = a.iter().filter(|x| **x > 1); // need two *s!
///
/// assert_eq!(iter.next(), Some(&2));
/// assert_eq!(iter.next(), None);
@ -646,7 +646,7 @@ pub trait Iterator {
/// ```
/// let a = [0, 1, 2];
///
/// let mut iter = a.into_iter().filter(|&x| *x > 1); // both & and *
/// let mut iter = a.iter().filter(|&x| *x > 1); // both & and *
///
/// assert_eq!(iter.next(), Some(&2));
/// assert_eq!(iter.next(), None);
@ -657,7 +657,7 @@ pub trait Iterator {
/// ```
/// let a = [0, 1, 2];
///
/// let mut iter = a.into_iter().filter(|&&x| x > 1); // two &s
/// let mut iter = a.iter().filter(|&&x| x > 1); // two &s
///
/// assert_eq!(iter.next(), Some(&2));
/// assert_eq!(iter.next(), None);
@ -837,7 +837,7 @@ pub trait Iterator {
/// ```
/// let a = [-1i32, 0, 1];
///
/// let mut iter = a.into_iter().skip_while(|x| x.is_negative());
/// let mut iter = a.iter().skip_while(|x| x.is_negative());
///
/// assert_eq!(iter.next(), Some(&0));
/// assert_eq!(iter.next(), Some(&1));
@ -851,7 +851,7 @@ pub trait Iterator {
/// ```
/// let a = [-1, 0, 1];
///
/// let mut iter = a.into_iter().skip_while(|x| **x < 0); // need two *s!
/// let mut iter = a.iter().skip_while(|x| **x < 0); // need two *s!
///
/// assert_eq!(iter.next(), Some(&0));
/// assert_eq!(iter.next(), Some(&1));
@ -863,7 +863,7 @@ pub trait Iterator {
/// ```
/// let a = [-1, 0, 1, -2];
///
/// let mut iter = a.into_iter().skip_while(|x| **x < 0);
/// let mut iter = a.iter().skip_while(|x| **x < 0);
///
/// assert_eq!(iter.next(), Some(&0));
/// assert_eq!(iter.next(), Some(&1));
@ -898,7 +898,7 @@ pub trait Iterator {
/// ```
/// let a = [-1i32, 0, 1];
///
/// let mut iter = a.into_iter().take_while(|x| x.is_negative());
/// let mut iter = a.iter().take_while(|x| x.is_negative());
///
/// assert_eq!(iter.next(), Some(&-1));
/// assert_eq!(iter.next(), None);
@ -911,7 +911,7 @@ pub trait Iterator {
/// ```
/// let a = [-1, 0, 1];
///
/// let mut iter = a.into_iter().take_while(|x| **x < 0); // need two *s!
/// let mut iter = a.iter().take_while(|x| **x < 0); // need two *s!
///
/// assert_eq!(iter.next(), Some(&-1));
/// assert_eq!(iter.next(), None);
@ -922,7 +922,7 @@ pub trait Iterator {
/// ```
/// let a = [-1, 0, 1, -2];
///
/// let mut iter = a.into_iter().take_while(|x| **x < 0);
/// let mut iter = a.iter().take_while(|x| **x < 0);
///
/// assert_eq!(iter.next(), Some(&-1));
///
@ -937,7 +937,7 @@ pub trait Iterator {
///
/// ```
/// let a = [1, 2, 3, 4];
/// let mut iter = a.into_iter();
/// let mut iter = a.iter();
///
/// let result: Vec<i32> = iter.by_ref()
/// .take_while(|n| **n != 3)
@ -1321,7 +1321,7 @@ pub trait Iterator {
/// ```
/// let a = [1, 2, 3];
///
/// let iter = a.into_iter();
/// let iter = a.iter();
///
/// let sum: i32 = iter.take(5).fold(0, |acc, i| acc + i );
///
@ -1334,7 +1334,7 @@ pub trait Iterator {
/// // let's try that again
/// let a = [1, 2, 3];
///
/// let mut iter = a.into_iter();
/// let mut iter = a.iter();
///
/// // instead, we add in a .by_ref()
/// let sum: i32 = iter.by_ref().take(2).fold(0, |acc, i| acc + i );
@ -1479,7 +1479,7 @@ pub trait Iterator {
/// let a = [1, 2, 3];
///
/// let (even, odd): (Vec<i32>, Vec<i32>) = a
/// .into_iter()
/// .iter()
/// .partition(|&n| n % 2 == 0);
///
/// assert_eq!(even, vec![2]);

View File

@ -125,7 +125,7 @@
#![feature(structural_match)]
#![feature(abi_unadjusted)]
#![feature(adx_target_feature)]
#![feature(maybe_uninit, maybe_uninit_slice, maybe_uninit_array)]
#![feature(maybe_uninit_slice, maybe_uninit_array)]
#![feature(external_doc)]
#[prelude_import]

View File

@ -63,62 +63,6 @@ pub use crate::intrinsics::transmute;
/// The practical use cases for `forget` are rather specialized and mainly come
/// up in unsafe or FFI code.
///
/// ## Use case 1
///
/// You have created an uninitialized value using [`mem::uninitialized`][uninit].
/// You must either initialize or `forget` it on every computation path before
/// Rust drops it automatically, like at the end of a scope or after a panic.
/// Running the destructor on an uninitialized value would be [undefined behavior][ub].
///
/// ```
/// use std::mem;
/// use std::ptr;
///
/// # let some_condition = false;
/// unsafe {
/// let mut uninit_vec: Vec<u32> = mem::uninitialized();
///
/// if some_condition {
/// // Initialize the variable.
/// ptr::write(&mut uninit_vec, Vec::new());
/// } else {
/// // Forget the uninitialized value so its destructor doesn't run.
/// mem::forget(uninit_vec);
/// }
/// }
/// ```
///
/// ## Use case 2
///
/// You have duplicated the bytes making up a value, without doing a proper
/// [`Clone`][clone]. You need the value's destructor to run only once,
/// because a double `free` is undefined behavior.
///
/// An example is a possible implementation of [`mem::swap`][swap]:
///
/// ```
/// use std::mem;
/// use std::ptr;
///
/// # #[allow(dead_code)]
/// fn swap<T>(x: &mut T, y: &mut T) {
/// unsafe {
/// // Give ourselves some scratch space to work with
/// let mut t: T = mem::uninitialized();
///
/// // Perform the swap, `&mut` pointers never alias
/// ptr::copy_nonoverlapping(&*x, &mut t, 1);
/// ptr::copy_nonoverlapping(&*y, x, 1);
/// ptr::copy_nonoverlapping(&t, y, 1);
///
/// // y and t now point to the same thing, but we need to completely
/// // forget `t` because we do not want to run the destructor for `T`
/// // on its value, which is still owned somewhere outside this function.
/// mem::forget(t);
/// }
/// }
/// ```
///
/// [drop]: fn.drop.html
/// [uninit]: fn.uninitialized.html
/// [clone]: ../clone/trait.Clone.html
@ -465,29 +409,37 @@ pub const fn needs_drop<T>() -> bool {
/// Creates a value whose bytes are all zero.
///
/// This has the same effect as allocating space with
/// [`mem::uninitialized`][uninit] and then zeroing it out. It is useful for
/// FFI sometimes, but should generally be avoided.
/// This has the same effect as [`MaybeUninit::zeroed().assume_init()`][zeroed].
/// It is useful for FFI sometimes, but should generally be avoided.
///
/// There is no guarantee that an all-zero byte-pattern represents a valid value of
/// some type `T`. If `T` has a destructor and the value is destroyed (due to
/// a panic or the end of a scope) before being initialized, then the destructor
/// will run on zeroed data, likely leading to [undefined behavior][ub].
/// some type `T`. For example, the all-zero byte-pattern is not a valid value
/// for reference types (`&T` and `&mut T`). Using `zeroed` on such types
/// causes immediate [undefined behavior][ub] because [the Rust compiler assumes][inv]
/// that there always is a valid value in a variable it considers initialized.
///
/// See also the documentation for [`mem::uninitialized`][uninit], which has
/// many of the same caveats.
///
/// [uninit]: fn.uninitialized.html
/// [zeroed]: union.MaybeUninit.html#method.zeroed
/// [ub]: ../../reference/behavior-considered-undefined.html
/// [inv]: union.MaybeUninit.html#initialization-invariant
///
/// # Examples
///
/// Correct usage of this function: initializing an integer with zero.
///
/// ```
/// use std::mem;
///
/// let x: i32 = unsafe { mem::zeroed() };
/// assert_eq!(0, x);
/// ```
///
/// *Incorrect* usage of this function: initializing a reference with zero.
///
/// ```no_run
/// use std::mem;
///
/// let _x: &i32 = unsafe { mem::zeroed() }; // Undefined behavior!
/// ```
#[inline]
#[stable(feature = "rust1", since = "1.0.0")]
pub unsafe fn zeroed<T>() -> T {
@ -498,130 +450,23 @@ pub unsafe fn zeroed<T>() -> T {
/// Bypasses Rust's normal memory-initialization checks by pretending to
/// produce a value of type `T`, while doing nothing at all.
///
/// **This is incredibly dangerous and should not be done lightly. Deeply
/// consider initializing your memory with a default value instead.**
/// **This functon is deprecated.** Use [`MaybeUninit<T>`] instead.
///
/// This is useful for FFI functions and initializing arrays sometimes,
/// but should generally be avoided.
/// The reason for deprecation is that the function basically cannot be used
/// correctly: [the Rust compiler assumes][inv] that values are properly initialized.
/// As a consequence, calling e.g. `mem::uninitialized::<bool>()` causes immediate
/// undefined behavior for returning a `bool` that is not definitely either `true`
/// or `false`. Worse, truly uninitialized memory like what gets returned here
/// is special in that the compiler knows that it does not have a fixed value.
/// This makes it undefined behavior to have uninitialized data in a variable even
/// if that variable has an integer type.
/// (Notice that the rules around uninitialized integers are not finalized yet, but
/// until they are, it is advisable to avoid them.)
///
/// # Undefined behavior
///
/// It is [undefined behavior][ub] to read uninitialized memory, even just an
/// uninitialized boolean. For instance, if you branch on the value of such
/// a boolean, your program may take one, both, or neither of the branches.
///
/// Writing to the uninitialized value is similarly dangerous. Rust believes the
/// value is initialized, and will therefore try to [`Drop`] the uninitialized
/// value and its fields if you try to overwrite it in a normal manner. The only way
/// to safely initialize an uninitialized value is with [`ptr::write`][write],
/// [`ptr::copy`][copy], or [`ptr::copy_nonoverlapping`][copy_no].
///
/// If the value does implement [`Drop`], it must be initialized before
/// it goes out of scope (and therefore would be dropped). Note that this
/// includes a `panic` occurring and unwinding the stack suddenly.
///
/// If you partially initialize an array, you may need to use
/// [`ptr::drop_in_place`][drop_in_place] to remove the elements you have fully
/// initialized followed by [`mem::forget`][mem_forget] to prevent drop running
/// on the array. If a partially allocated array is dropped this will lead to
/// undefined behaviour.
///
/// # Examples
///
/// Here's how to safely initialize an array of [`Vec`]s.
///
/// ```
/// use std::mem;
/// use std::ptr;
///
/// // Only declare the array. This safely leaves it
/// // uninitialized in a way that Rust will track for us.
/// // However we can't initialize it element-by-element
/// // safely, and we can't use the `[value; 1000]`
/// // constructor because it only works with `Copy` data.
/// let mut data: [Vec<u32>; 1000];
///
/// unsafe {
/// // So we need to do this to initialize it.
/// data = mem::uninitialized();
///
/// // DANGER ZONE: if anything panics or otherwise
/// // incorrectly reads the array here, we will have
/// // Undefined Behavior.
///
/// // It's ok to mutably iterate the data, since this
/// // doesn't involve reading it at all.
/// // (ptr and len are statically known for arrays)
/// for elem in &mut data[..] {
/// // *elem = Vec::new() would try to drop the
/// // uninitialized memory at `elem` -- bad!
/// //
/// // Vec::new doesn't allocate or do really
/// // anything. It's only safe to call here
/// // because we know it won't panic.
/// ptr::write(elem, Vec::new());
/// }
///
/// // SAFE ZONE: everything is initialized.
/// }
///
/// println!("{:?}", &data[0]);
/// ```
///
/// This example emphasizes exactly how delicate and dangerous using `mem::uninitialized`
/// can be. Note that the [`vec!`] macro *does* let you initialize every element with a
/// value that is only [`Clone`], so the following is semantically equivalent and
/// vastly less dangerous, as long as you can live with an extra heap
/// allocation:
///
/// ```
/// let data: Vec<Vec<u32>> = vec![Vec::new(); 1000];
/// println!("{:?}", &data[0]);
/// ```
///
/// This example shows how to handle partially initialized arrays, which could
/// be found in low-level datastructures.
///
/// ```
/// use std::mem;
/// use std::ptr;
///
/// // Count the number of elements we have assigned.
/// let mut data_len: usize = 0;
/// let mut data: [String; 1000];
///
/// unsafe {
/// data = mem::uninitialized();
///
/// for elem in &mut data[0..500] {
/// ptr::write(elem, String::from("hello"));
/// data_len += 1;
/// }
///
/// // For each item in the array, drop if we allocated it.
/// for i in &mut data[0..data_len] {
/// ptr::drop_in_place(i);
/// }
/// }
/// // Forget the data. If this is allowed to drop, you may see a crash such as:
/// // 'mem_uninit_test(2457,0x7fffb55dd380) malloc: *** error for object
/// // 0x7ff3b8402920: pointer being freed was not allocated'
/// mem::forget(data);
/// ```
///
/// [`Vec`]: ../../std/vec/struct.Vec.html
/// [`vec!`]: ../../std/macro.vec.html
/// [`Clone`]: ../../std/clone/trait.Clone.html
/// [ub]: ../../reference/behavior-considered-undefined.html
/// [write]: ../ptr/fn.write.html
/// [drop_in_place]: ../ptr/fn.drop_in_place.html
/// [mem_zeroed]: fn.zeroed.html
/// [mem_forget]: fn.forget.html
/// [copy]: ../intrinsics/fn.copy.html
/// [copy_no]: ../intrinsics/fn.copy_nonoverlapping.html
/// [`Drop`]: ../ops/trait.Drop.html
/// [`MaybeUninit<T>`]: union.MaybeUninit.html
/// [inv]: union.MaybeUninit.html#initialization-invariant
#[inline]
#[rustc_deprecated(since = "2.0.0", reason = "use `mem::MaybeUninit::uninit` instead")]
#[rustc_deprecated(since = "1.40.0", reason = "use `mem::MaybeUninit` instead")]
#[stable(feature = "rust1", since = "1.0.0")]
pub unsafe fn uninitialized<T>() -> T {
intrinsics::panic_if_uninhabited::<T>();
@ -899,7 +744,6 @@ pub fn discriminant<T>(v: &T) -> Discriminant<T> {
}
}
// FIXME: Reference `MaybeUninit` from these docs, once that is stable.
/// A wrapper to inhibit compiler from automatically calling `T`s destructor.
///
/// This wrapper is 0-cost.
@ -908,6 +752,7 @@ pub fn discriminant<T>(v: &T) -> Discriminant<T> {
/// As a consequence, it has *no effect* on the assumptions that the compiler makes
/// about all values being initialized at their type. In particular, initializing
/// a `ManuallyDrop<&mut T>` with [`mem::zeroed`] is undefined behavior.
/// If you need to handle uninitialized data, use [`MaybeUninit<T>`] instead.
///
/// # Examples
///
@ -942,6 +787,7 @@ pub fn discriminant<T>(v: &T) -> Discriminant<T> {
/// ```
///
/// [`mem::zeroed`]: fn.zeroed.html
/// [`MaybeUninit<T>`]: union.MaybeUninit.html
#[stable(feature = "manually_drop", since = "1.20.0")]
#[lang = "manually_drop"]
#[derive(Copy, Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)]
@ -1042,17 +888,18 @@ impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
}
}
/// A wrapper to construct uninitialized instances of `T`.
/// A wrapper type to construct uninitialized instances of `T`.
///
/// # Initialization invariant
///
/// The compiler, in general, assumes that variables are properly initialized
/// at their respective type. For example, a variable of reference type must
/// be aligned and non-NULL. This is an invariant that must *always* be upheld,
/// even in unsafe code. As a consequence, zero-initializing a variable of reference
/// type causes instantaneous undefined behavior, no matter whether that reference
/// type causes instantaneous [undefined behavior][ub], no matter whether that reference
/// ever gets used to access memory:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::{self, MaybeUninit};
///
/// let x: &i32 = unsafe { mem::zeroed() }; // undefined behavior!
@ -1067,7 +914,6 @@ impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
/// always be `true` or `false`. Hence, creating an uninitialized `bool` is undefined behavior:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::{self, MaybeUninit};
///
/// let b: bool = unsafe { mem::uninitialized() }; // undefined behavior!
@ -1078,10 +924,9 @@ impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
/// Moreover, uninitialized memory is special in that the compiler knows that
/// it does not have a fixed value. This makes it undefined behavior to have
/// uninitialized data in a variable even if that variable has an integer type,
/// which otherwise can hold any bit pattern:
/// which otherwise can hold any *fixed* bit pattern:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::{self, MaybeUninit};
///
/// let x: i32 = unsafe { mem::uninitialized() }; // undefined behavior!
@ -1091,37 +936,154 @@ impl<T: ?Sized> DerefMut for ManuallyDrop<T> {
/// (Notice that the rules around uninitialized integers are not finalized yet, but
/// until they are, it is advisable to avoid them.)
///
/// On top of that, remember that most types have additional invariants beyond merely
/// being considered initialized at the type level. For example, a `1`-initialized [`Vec<T>`]
/// is considered initialized because the only requirement the compiler knows about it
/// is that the data pointer must be non-null. Creating such a `Vec<T>` does not cause
/// *immediate* undefined behavior, but will cause undefined behavior with most
/// safe operations (including dropping it).
///
/// [`Vec<T>`]: ../../std/vec/struct.Vec.html
///
/// # Examples
///
/// `MaybeUninit<T>` serves to enable unsafe code to deal with uninitialized data.
/// It is a signal to the compiler indicating that the data here might *not*
/// be initialized:
///
/// ```rust
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// // Create an explicitly uninitialized reference. The compiler knows that data inside
/// // a `MaybeUninit<T>` may be invalid, and hence this is not UB:
/// let mut x = MaybeUninit::<&i32>::uninit();
/// // Set it to a valid value.
/// x.write(&0);
/// unsafe { x.as_mut_ptr().write(&0); }
/// // Extract the initialized data -- this is only allowed *after* properly
/// // initializing `x`!
/// let x = unsafe { x.assume_init() };
/// ```
///
/// The compiler then knows to not make any incorrect assumptions or optimizations on this code.
//
// FIXME before stabilizing, explain how to initialize a struct field-by-field.
///
/// ## out-pointers
///
/// You can use `MaybeUninit<T>` to implement "out-pointers": instead of returning data
/// from a function, pass it a pointer to some (uninitialized) memory to put the
/// result into. This can be useful when it is important for the caller to control
/// how the memory the result is stored in gets allocated, and you want to avoid
/// unnecessary moves.
///
/// ```
/// use std::mem::MaybeUninit;
///
/// unsafe fn make_vec(out: *mut Vec<i32>) {
/// // `write` does not drop the old contents, which is important.
/// out.write(vec![1, 2, 3]);
/// }
///
/// let mut v: MaybeUninit<Vec<i32>> = MaybeUninit::uninit();
/// unsafe { make_vec(v.as_mut_ptr()); }
/// // Now we know `v` is initialized! This also makes sure the vector gets
/// // properly dropped.
/// let v = unsafe { v.assume_init() };
/// assert_eq!(&v, &[1, 2, 3]);
/// ```
///
/// ## Initializing an array element-by-element
///
/// `MaybeUninit<T>` can be used to initialize a large array element-by-element:
///
/// ```
/// use std::mem::{self, MaybeUninit};
/// use std::ptr;
///
/// let data = {
/// // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
/// // safe because the type we are claiming to have initialized here is a
/// // bunch of `MaybeUninit`s, which do not require initialization.
/// let mut data: [MaybeUninit<Vec<u32>>; 1000] = unsafe {
/// MaybeUninit::uninit().assume_init()
/// };
///
/// // Dropping a `MaybeUninit` does nothing, so if there is a panic during this loop,
/// // we have a memory leak, but there is no memory safety issue.
/// for elem in &mut data[..] {
/// unsafe { ptr::write(elem.as_mut_ptr(), vec![42]); }
/// }
///
/// // Everything is initialized. Transmute the array to the
/// // initialized type.
/// unsafe { mem::transmute::<_, [Vec<u32>; 1000]>(data) }
/// };
///
/// assert_eq!(&data[0], &[42]);
/// ```
///
/// You can also work with partially initialized arrays, which could
/// be found in low-level datastructures.
///
/// ```
/// use std::mem::MaybeUninit;
/// use std::ptr;
///
/// // Create an uninitialized array of `MaybeUninit`. The `assume_init` is
/// // safe because the type we are claiming to have initialized here is a
/// // bunch of `MaybeUninit`s, which do not require initialization.
/// let mut data: [MaybeUninit<String>; 1000] = unsafe { MaybeUninit::uninit().assume_init() };
/// // Count the number of elements we have assigned.
/// let mut data_len: usize = 0;
///
/// for elem in &mut data[0..500] {
/// unsafe { ptr::write(elem.as_mut_ptr(), String::from("hello")); }
/// data_len += 1;
/// }
///
/// // For each item in the array, drop if we allocated it.
/// for elem in &mut data[0..data_len] {
/// unsafe { ptr::drop_in_place(elem.as_mut_ptr()); }
/// }
/// ```
///
/// ## Initializing a struct field-by-field
///
/// There is currently no supported way to create a raw pointer or reference
/// to a field of a struct inside `MaybeUninit<Struct>`. That means it is not possible
/// to create a struct by calling `MaybeUninit::uninit::<Struct>()` and then writing
/// to its fields.
///
/// [ub]: ../../reference/behavior-considered-undefined.html
///
/// # Layout
///
/// `MaybeUninit<T>` is guaranteed to have the same size and alignment as `T`:
///
/// ```rust
/// use std::mem::{MaybeUninit, size_of, align_of};
/// assert_eq!(size_of::<MaybeUninit<u64>>(), size_of::<u64>());
/// assert_eq!(align_of::<MaybeUninit<u64>>(), align_of::<u64>());
/// ```
///
/// However remember that a type *containing* a `MaybeUninit<T>` is not necessarily the same
/// layout; Rust does not in general guarantee that the fields of a `Foo<T>` have the same order as
/// a `Foo<U>` even if `T` and `U` have the same size and alignment. Furthermore because any bit
/// value is valid for a `MaybeUninit<T>` the compiler can't apply non-zero/niche-filling
/// optimizations, potentially resulting in a larger size:
///
/// ```rust
/// # use std::mem::{MaybeUninit, size_of, align_of};
/// assert_eq!(size_of::<Option<bool>>(), 1);
/// assert_eq!(size_of::<Option<MaybeUninit<bool>>>(), 2);
/// ```
#[allow(missing_debug_implementations)]
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[derive(Copy)]
// NOTE: after stabilizing `MaybeUninit`, proceed to deprecate `mem::uninitialized`.
pub union MaybeUninit<T> {
uninit: (),
value: ManuallyDrop<T>,
}
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
impl<T: Copy> Clone for MaybeUninit<T> {
#[inline(always)]
fn clone(&self) -> Self {
@ -1132,10 +1094,13 @@ impl<T: Copy> Clone for MaybeUninit<T> {
impl<T> MaybeUninit<T> {
/// Creates a new `MaybeUninit<T>` initialized with the given value.
/// It is safe to call [`assume_init`] on the return value of this function.
///
/// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
/// It is your responsibility to make sure `T` gets dropped if it got initialized.
#[unstable(feature = "maybe_uninit", issue = "53491")]
///
/// [`assume_init`]: #method.assume_init
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline(always)]
pub const fn new(val: T) -> MaybeUninit<T> {
MaybeUninit { value: ManuallyDrop::new(val) }
@ -1145,7 +1110,11 @@ impl<T> MaybeUninit<T> {
///
/// Note that dropping a `MaybeUninit<T>` will never call `T`'s drop code.
/// It is your responsibility to make sure `T` gets dropped if it got initialized.
#[unstable(feature = "maybe_uninit", issue = "53491")]
///
/// See the [type-level documentation][type] for some examples.
///
/// [type]: union.MaybeUninit.html
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline(always)]
pub const fn uninit() -> MaybeUninit<T> {
MaybeUninit { uninit: () }
@ -1166,7 +1135,6 @@ impl<T> MaybeUninit<T> {
/// fields of the struct can hold the bit-pattern 0 as a valid value.
///
/// ```rust
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let x = MaybeUninit::<(u8, bool)>::zeroed();
@ -1178,7 +1146,6 @@ impl<T> MaybeUninit<T> {
/// cannot hold 0 as a valid value.
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// enum NotZero { One = 1, Two = 2 };
@ -1188,7 +1155,7 @@ impl<T> MaybeUninit<T> {
/// // Inside a pair, we create a `NotZero` that does not have a valid discriminant.
/// // This is undefined behavior.
/// ```
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline]
pub fn zeroed() -> MaybeUninit<T> {
let mut u = MaybeUninit::<T>::uninit();
@ -1202,7 +1169,7 @@ impl<T> MaybeUninit<T> {
/// without dropping it, so be careful not to use this twice unless you want to
/// skip running the destructor. For your convenience, this also returns a mutable
/// reference to the (now safely initialized) contents of `self`.
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[unstable(feature = "maybe_uninit_extra", issue = "53491")]
#[inline(always)]
pub fn write(&mut self, val: T) -> &mut T {
unsafe {
@ -1213,13 +1180,14 @@ impl<T> MaybeUninit<T> {
/// Gets a pointer to the contained value. Reading from this pointer or turning it
/// into a reference is undefined behavior unless the `MaybeUninit<T>` is initialized.
/// Writing to memory that this pointer (non-transitively) points to is undefined behavior
/// (except inside an `UnsafeCell<T>`).
///
/// # Examples
///
/// Correct usage of this method:
///
/// ```rust
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<Vec<u32>>::uninit();
@ -1232,7 +1200,6 @@ impl<T> MaybeUninit<T> {
/// *Incorrect* usage of this method:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let x = MaybeUninit::<Vec<u32>>::uninit();
@ -1242,7 +1209,7 @@ impl<T> MaybeUninit<T> {
///
/// (Notice that the rules around references to uninitialized data are not finalized yet, but
/// until they are, it is advisable to avoid them.)
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline(always)]
pub fn as_ptr(&self) -> *const T {
unsafe { &*self.value as *const T }
@ -1256,7 +1223,6 @@ impl<T> MaybeUninit<T> {
/// Correct usage of this method:
///
/// ```rust
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<Vec<u32>>::uninit();
@ -1271,7 +1237,6 @@ impl<T> MaybeUninit<T> {
/// *Incorrect* usage of this method:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<Vec<u32>>::uninit();
@ -1281,7 +1246,7 @@ impl<T> MaybeUninit<T> {
///
/// (Notice that the rules around references to uninitialized data are not finalized yet, but
/// until they are, it is advisable to avoid them.)
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline(always)]
pub fn as_mut_ptr(&mut self) -> *mut T {
unsafe { &mut *self.value as *mut T }
@ -1294,15 +1259,17 @@ impl<T> MaybeUninit<T> {
/// # Safety
///
/// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
/// state. Calling this when the content is not yet fully initialized causes undefined
/// behavior.
/// state. Calling this when the content is not yet fully initialized causes immediate undefined
/// behavior. The [type-level documentation][inv] contains more information about
/// this initialization invariant.
///
/// [inv]: #initialization-invariant
///
/// # Examples
///
/// Correct usage of this method:
///
/// ```rust
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<bool>::uninit();
@ -1314,14 +1281,13 @@ impl<T> MaybeUninit<T> {
/// *Incorrect* usage of this method:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// use std::mem::MaybeUninit;
///
/// let x = MaybeUninit::<Vec<u32>>::uninit();
/// let x_init = unsafe { x.assume_init() };
/// // `x` had not been initialized yet, so this last line caused undefined behavior.
/// ```
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[stable(feature = "maybe_uninit", since = "1.36.0")]
#[inline(always)]
pub unsafe fn assume_init(self) -> T {
intrinsics::panic_if_uninhabited::<T>();
@ -1338,13 +1304,15 @@ impl<T> MaybeUninit<T> {
///
/// It is up to the caller to guarantee that the `MaybeUninit<T>` really is in an initialized
/// state. Calling this when the content is not yet fully initialized causes undefined
/// behavior.
/// behavior. The [type-level documentation][inv] contains more information about
/// this initialization invariant.
///
/// Moreover, this leaves a copy of the same data behind in the `MaybeUninit<T>`. When using
/// multiple copies of the data (by calling `read` multiple times, or first
/// calling `read` and then [`assume_init`]), it is your responsibility
/// to ensure that that data may indeed be duplicated.
///
/// [inv]: #initialization-invariant
/// [`assume_init`]: #method.assume_init
///
/// # Examples
@ -1352,7 +1320,7 @@ impl<T> MaybeUninit<T> {
/// Correct usage of this method:
///
/// ```rust
/// #![feature(maybe_uninit)]
/// #![feature(maybe_uninit_extra)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<u32>::uninit();
@ -1373,7 +1341,7 @@ impl<T> MaybeUninit<T> {
/// *Incorrect* usage of this method:
///
/// ```rust,no_run
/// #![feature(maybe_uninit)]
/// #![feature(maybe_uninit_extra)]
/// use std::mem::MaybeUninit;
///
/// let mut x = MaybeUninit::<Option<Vec<u32>>>::uninit();
@ -1383,7 +1351,7 @@ impl<T> MaybeUninit<T> {
/// // We now created two copies of the same vector, leading to a double-free when
/// // they both get dropped!
/// ```
#[unstable(feature = "maybe_uninit", issue = "53491")]
#[unstable(feature = "maybe_uninit_extra", issue = "53491")]
#[inline(always)]
pub unsafe fn read(&self) -> T {
intrinsics::panic_if_uninhabited::<T>();

View File

@ -155,12 +155,12 @@ pub use crate::intrinsics::write_bytes;
/// location first:
/// ```
/// use std::ptr;
/// use std::mem;
/// use std::mem::{self, MaybeUninit};
///
/// unsafe fn drop_after_copy<T>(to_drop: *mut T) {
/// let mut copy: T = mem::uninitialized();
/// ptr::copy(to_drop, &mut copy, 1);
/// drop(copy);
/// let mut copy: MaybeUninit<T> = MaybeUninit::uninit();
/// ptr::copy(to_drop, copy.as_mut_ptr(), 1);
/// drop(copy.assume_init());
/// }
///
/// #[repr(packed, C)]
@ -374,10 +374,7 @@ unsafe fn swap_nonoverlapping_bytes(x: *mut u8, y: *mut u8, len: usize) {
// #[repr(simd)], even if we don't actually use this struct directly.
//
// FIXME repr(simd) broken on emscripten and redox
// It's also broken on big-endian powerpc64 and s390x. #42778
#[cfg_attr(not(any(target_os = "emscripten", target_os = "redox",
target_endian = "big")),
repr(simd))]
#[cfg_attr(not(any(target_os = "emscripten", target_os = "redox")), repr(simd))]
struct Block(u64, u64, u64, u64);
struct UnalignedBlock(u64, u64, u64, u64);
@ -813,9 +810,6 @@ pub unsafe fn write_unaligned<T>(dst: *mut T, src: T) {
/// to not be elided or reordered by the compiler across other volatile
/// operations.
///
/// Memory accessed with `read_volatile` or [`write_volatile`] should not be
/// accessed with non-volatile operations.
///
/// [`write_volatile`]: ./fn.write_volatile.html
///
/// # Notes
@ -840,7 +834,7 @@ pub unsafe fn write_unaligned<T>(dst: *mut T, src: T) {
///
/// * `src` must be properly aligned.
///
/// Like [`read`], `read_unaligned` creates a bitwise copy of `T`, regardless of
/// Like [`read`], `read_volatile` creates a bitwise copy of `T`, regardless of
/// whether `T` is [`Copy`]. If `T` is not [`Copy`], using both the returned
/// value and the value at `*src` can [violate memory safety][read-ownership].
/// However, storing non-[`Copy`] types in volatile memory is almost certainly
@ -884,9 +878,6 @@ pub unsafe fn read_volatile<T>(src: *const T) -> T {
/// to not be elided or reordered by the compiler across other volatile
/// operations.
///
/// Memory accessed with [`read_volatile`] or `write_volatile` should not be
/// accessed with non-volatile operations.
///
/// `write_volatile` does not drop the contents of `dst`. This is safe, but it
/// could leak allocations or resources, so care should be taken not to overwrite
/// an object that should be dropped.
@ -2973,7 +2964,6 @@ impl<T: Sized> NonNull<T> {
/// some other means.
#[stable(feature = "nonnull", since = "1.25.0")]
#[inline]
#[rustc_const_unstable(feature = "const_ptr_nonnull")]
pub const fn dangling() -> Self {
unsafe {
let ptr = mem::align_of::<T>() as *mut T;
@ -3037,7 +3027,6 @@ impl<T: ?Sized> NonNull<T> {
/// Cast to a pointer of another type
#[stable(feature = "nonnull_cast", since = "1.27.0")]
#[inline]
#[rustc_const_unstable(feature = "const_ptr_nonnull")]
pub const fn cast<U>(self) -> NonNull<U> {
unsafe {
NonNull::new_unchecked(self.as_ptr() as *mut U)

View File

@ -359,6 +359,10 @@ impl<T> [T] {
/// The caller must ensure that the slice outlives the pointer this
/// function returns, or else it will end up pointing to garbage.
///
/// The caller must also ensure that the memory the pointer (non-transitively) points to
/// is never written to (except inside an `UnsafeCell`) using this pointer or any pointer
/// derived from it. If you need to mutate the contents of the slice, use [`as_mut_ptr`].
///
/// Modifying the container referenced by this slice may cause its buffer
/// to be reallocated, which would also make any pointers to it invalid.
///
@ -374,6 +378,8 @@ impl<T> [T] {
/// }
/// }
/// ```
///
/// [`as_mut_ptr`]: #method.as_mut_ptr
#[stable(feature = "rust1", since = "1.0.0")]
#[inline]
pub const fn as_ptr(&self) -> *const T {
@ -3541,6 +3547,11 @@ impl<'a, T, P> Iterator for Split<'a, T, P> where P: FnMut(&T) -> bool {
(1, Some(self.v.len() + 1))
}
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -3639,6 +3650,11 @@ impl<'a, T, P> Iterator for SplitMut<'a, T, P> where P: FnMut(&T) -> bool {
(1, Some(self.v.len() + 1))
}
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -3704,6 +3720,11 @@ impl<'a, T, P> Iterator for RSplit<'a, T, P> where P: FnMut(&T) -> bool {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "slice_rsplit", since = "1.27.0")]
@ -3768,6 +3789,11 @@ impl<'a, T, P> Iterator for RSplitMut<'a, T, P> where P: FnMut(&T) -> bool {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "slice_rsplit", since = "1.27.0")]

View File

@ -1333,6 +1333,11 @@ impl<'a> Iterator for Lines<'a> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.0.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -1379,6 +1384,11 @@ impl<'a> Iterator for LinesAny<'a> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.0.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "rust1", since = "1.0.0")]
@ -2188,7 +2198,11 @@ impl str {
/// [`u8`]. This pointer will be pointing to the first byte of the string
/// slice.
///
/// The caller must ensure that the returned pointer is never written to.
/// If you need to mutate the contents of the string slice, use [`as_mut_ptr`].
///
/// [`u8`]: primitive.u8.html
/// [`as_mut_ptr`]: #method.as_mut_ptr
///
/// # Examples
///
@ -4217,6 +4231,11 @@ impl<'a> Iterator for SplitWhitespace<'a> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "split_whitespace", since = "1.1.0")]
@ -4243,6 +4262,11 @@ impl<'a> Iterator for SplitAsciiWhitespace<'a> {
fn size_hint(&self) -> (usize, Option<usize>) {
self.inner.size_hint()
}
#[inline]
fn last(mut self) -> Option<Self::Item> {
self.next_back()
}
}
#[stable(feature = "split_ascii_whitespace", since = "1.34.0")]

View File

@ -10,6 +10,8 @@ use crate::marker::{PhantomData, Unpin};
///
/// It consists of a data pointer and a [virtual function pointer table (vtable)][vtable] that
/// customizes the behavior of the `RawWaker`.
///
/// [`Waker`]: struct.Waker.html
#[derive(PartialEq, Debug)]
#[stable(feature = "futures_api", since = "1.36.0")]
pub struct RawWaker {
@ -55,6 +57,8 @@ impl RawWaker {
/// pointer of a properly constructed [`RawWaker`] object from inside the
/// [`RawWaker`] implementation. Calling one of the contained functions using
/// any other `data` pointer will cause undefined behavior.
///
/// [`RawWaker`]: struct.RawWaker.html
#[stable(feature = "futures_api", since = "1.36.0")]
#[derive(PartialEq, Copy, Clone, Debug)]
pub struct RawWakerVTable {
@ -65,6 +69,9 @@ pub struct RawWakerVTable {
/// required for this additional instance of a [`RawWaker`] and associated
/// task. Calling `wake` on the resulting [`RawWaker`] should result in a wakeup
/// of the same task that would have been awoken by the original [`RawWaker`].
///
/// [`Waker`]: struct.Waker.html
/// [`RawWaker`]: struct.RawWaker.html
clone: unsafe fn(*const ()) -> RawWaker,
/// This function will be called when `wake` is called on the [`Waker`].
@ -73,6 +80,9 @@ pub struct RawWakerVTable {
/// The implementation of this function must make sure to release any
/// resources that are associated with this instance of a [`RawWaker`] and
/// associated task.
///
/// [`Waker`]: struct.Waker.html
/// [`RawWaker`]: struct.RawWaker.html
wake: unsafe fn(*const ()),
/// This function will be called when `wake_by_ref` is called on the [`Waker`].
@ -80,6 +90,9 @@ pub struct RawWakerVTable {
///
/// This function is similar to `wake`, but must not consume the provided data
/// pointer.
///
/// [`Waker`]: struct.Waker.html
/// [`RawWaker`]: struct.RawWaker.html
wake_by_ref: unsafe fn(*const ()),
/// This function gets called when a [`RawWaker`] gets dropped.
@ -87,6 +100,8 @@ pub struct RawWakerVTable {
/// The implementation of this function must make sure to release any
/// resources that are associated with this instance of a [`RawWaker`] and
/// associated task.
///
/// [`RawWaker`]: struct.RawWaker.html
drop: unsafe fn(*const ()),
}
@ -128,6 +143,9 @@ impl RawWakerVTable {
/// The implementation of this function must make sure to release any
/// resources that are associated with this instance of a [`RawWaker`] and
/// associated task.
///
/// [`Waker`]: struct.Waker.html
/// [`RawWaker`]: struct.RawWaker.html
#[rustc_promotable]
#[cfg_attr(stage0, unstable(feature = "futures_api_const_fn_ptr", issue = "50547"))]
#[cfg_attr(not(stage0), stable(feature = "futures_api", since = "1.36.0"))]
@ -201,6 +219,8 @@ impl fmt::Debug for Context<'_> {
/// executor-specific wakeup behavior.
///
/// Implements [`Clone`], [`Send`], and [`Sync`].
///
/// [`RawWaker`]: struct.RawWaker.html
#[repr(transparent)]
#[stable(feature = "futures_api", since = "1.36.0")]
pub struct Waker {
@ -266,6 +286,9 @@ impl Waker {
/// The behavior of the returned `Waker` is undefined if the contract defined
/// in [`RawWaker`]'s and [`RawWakerVTable`]'s documentation is not upheld.
/// Therefore this method is unsafe.
///
/// [`RawWaker`]: struct.RawWaker.html
/// [`RawWakerVTable`]: struct.RawWakerVTable.html
#[inline]
#[stable(feature = "futures_api", since = "1.36.0")]
pub unsafe fn from_raw(waker: RawWaker) -> Waker {

View File

@ -0,0 +1,10 @@
use core::alloc::Layout;
#[test]
fn const_unchecked_layout() {
const SIZE: usize = 0x2000;
const ALIGN: usize = 0x1000;
const LAYOUT: Layout = unsafe { Layout::from_size_align_unchecked(SIZE, ALIGN) };
assert_eq!(LAYOUT.size(), SIZE);
assert_eq!(LAYOUT.align(), ALIGN);
}

View File

@ -31,10 +31,12 @@
#![feature(slice_partition_dedup)]
#![feature(copy_within)]
#![feature(int_error_matching)]
#![deny(rust_2018_idioms)]
#![feature(const_fn)]
#![warn(rust_2018_idioms)]
extern crate test;
mod alloc;
mod any;
mod array;
mod ascii;

View File

@ -36,7 +36,7 @@ byteorder = { version = "1.1", features = ["i128"]}
chalk-engine = { version = "0.9.0", default-features=false }
rustc_fs_util = { path = "../librustc_fs_util" }
smallvec = { version = "0.6.7", features = ["union", "may_dangle"] }
measureme = "0.2.1"
measureme = "0.3"
# Note that these dependencies are a lie, they're just here to get linkage to
# work.

View File

@ -166,47 +166,6 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
self.add_ast_node(expr.hir_id.local_id, &[blk_exit])
}
hir::ExprKind::If(ref cond, ref then, None) => {
//
// [pred]
// |
// v 1
// [cond]
// |
// / \
// / \
// v 2 *
// [then] |
// | |
// v 3 v 4
// [..expr..]
//
let cond_exit = self.expr(&cond, pred); // 1
let then_exit = self.expr(&then, cond_exit); // 2
self.add_ast_node(expr.hir_id.local_id, &[cond_exit, then_exit]) // 3,4
}
hir::ExprKind::If(ref cond, ref then, Some(ref otherwise)) => {
//
// [pred]
// |
// v 1
// [cond]
// |
// / \
// / \
// v 2 v 3
// [then][otherwise]
// | |
// v 4 v 5
// [..expr..]
//
let cond_exit = self.expr(&cond, pred); // 1
let then_exit = self.expr(&then, cond_exit); // 2
let else_exit = self.expr(&otherwise, cond_exit); // 3
self.add_ast_node(expr.hir_id.local_id, &[then_exit, else_exit]) // 4, 5
}
hir::ExprKind::While(ref cond, ref body, _) => {
//
// [pred]

View File

@ -12,6 +12,7 @@ use crate::hir;
use crate::hir::def_id::DefId;
use crate::hir::intravisit::{self, Visitor, NestedVisitorMap};
use std::fmt::{self, Display};
use syntax::symbol::sym;
use syntax_pos::Span;
#[derive(Copy, Clone, PartialEq)]
@ -95,18 +96,18 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
fn check_attributes(&self, item: &hir::Item, target: Target) {
if target == Target::Fn || target == Target::Const {
self.tcx.codegen_fn_attrs(self.tcx.hir().local_def_id_from_hir_id(item.hir_id));
} else if let Some(a) = item.attrs.iter().find(|a| a.check_name("target_feature")) {
} else if let Some(a) = item.attrs.iter().find(|a| a.check_name(sym::target_feature)) {
self.tcx.sess.struct_span_err(a.span, "attribute should be applied to a function")
.span_label(item.span, "not a function")
.emit();
}
for attr in &item.attrs {
if attr.check_name("inline") {
if attr.check_name(sym::inline) {
self.check_inline(attr, &item.span, target)
} else if attr.check_name("non_exhaustive") {
} else if attr.check_name(sym::non_exhaustive) {
self.check_non_exhaustive(attr, item, target)
} else if attr.check_name("marker") {
} else if attr.check_name(sym::marker) {
self.check_marker(attr, item, target)
}
}
@ -166,7 +167,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
// ```
let hints: Vec<_> = item.attrs
.iter()
.filter(|attr| attr.check_name("repr"))
.filter(|attr| attr.check_name(sym::repr))
.filter_map(|attr| attr.meta_item_list())
.flatten()
.collect();
@ -177,9 +178,9 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
let mut is_transparent = false;
for hint in &hints {
let (article, allowed_targets) = match hint.name_or_empty().get() {
name @ "C" | name @ "align" => {
is_c |= name == "C";
let (article, allowed_targets) = match hint.name_or_empty() {
name @ sym::C | name @ sym::align => {
is_c |= name == sym::C;
if target != Target::Struct &&
target != Target::Union &&
target != Target::Enum {
@ -188,7 +189,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
continue
}
}
"packed" => {
sym::packed => {
if target != Target::Struct &&
target != Target::Union {
("a", "struct or union")
@ -196,7 +197,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
continue
}
}
"simd" => {
sym::simd => {
is_simd = true;
if target != Target::Struct {
("a", "struct")
@ -204,7 +205,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
continue
}
}
"transparent" => {
sym::transparent => {
is_transparent = true;
if target != Target::Struct {
("a", "struct")
@ -212,9 +213,9 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
continue
}
}
"i8" | "u8" | "i16" | "u16" |
"i32" | "u32" | "i64" | "u64" |
"isize" | "usize" => {
sym::i8 | sym::u8 | sym::i16 | sym::u16 |
sym::i32 | sym::u32 | sym::i64 | sym::u64 |
sym::isize | sym::usize => {
int_reprs += 1;
if target != Target::Enum {
("an", "enum")
@ -268,10 +269,10 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
// When checking statements ignore expressions, they will be checked later
if let hir::StmtKind::Local(ref l) = stmt.node {
for attr in l.attrs.iter() {
if attr.check_name("inline") {
if attr.check_name(sym::inline) {
self.check_inline(attr, &stmt.span, Target::Statement);
}
if attr.check_name("repr") {
if attr.check_name(sym::repr) {
self.emit_repr_error(
attr.span,
stmt.span,
@ -289,10 +290,10 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
_ => Target::Expression,
};
for attr in expr.attrs.iter() {
if attr.check_name("inline") {
if attr.check_name(sym::inline) {
self.check_inline(attr, &expr.span, target);
}
if attr.check_name("repr") {
if attr.check_name(sym::repr) {
self.emit_repr_error(
attr.span,
expr.span,
@ -305,7 +306,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
fn check_used(&self, item: &hir::Item, target: Target) {
for attr in &item.attrs {
if attr.check_name("used") && target != Target::Static {
if attr.check_name(sym::used) && target != Target::Static {
self.tcx.sess
.span_err(attr.span, "attribute must be applied to a `static` variable");
}

View File

@ -96,34 +96,20 @@ impl fmt::Display for CrateNum {
impl serialize::UseSpecializedEncodable for CrateNum {}
impl serialize::UseSpecializedDecodable for CrateNum {}
/// A DefIndex is an index into the hir-map for a crate, identifying a
/// particular definition. It should really be considered an interned
/// shorthand for a particular DefPath.
#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Copy)]
pub struct DefIndex(u32);
newtype_index! {
/// A DefIndex is an index into the hir-map for a crate, identifying a
/// particular definition. It should really be considered an interned
/// shorthand for a particular DefPath.
pub struct DefIndex {
DEBUG_FORMAT = "DefIndex({})",
/// The crate root is always assigned index 0 by the AST Map code,
/// thanks to `NodeCollector::new`.
pub const CRATE_DEF_INDEX: DefIndex = DefIndex(0);
impl fmt::Debug for DefIndex {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "DefIndex({})", self.as_array_index())
/// The crate root is always assigned index 0 by the AST Map code,
/// thanks to `NodeCollector::new`.
const CRATE_DEF_INDEX = 0,
}
}
impl DefIndex {
/// Converts this DefIndex into a zero-based array index.
#[inline]
pub fn as_array_index(&self) -> usize {
self.0 as usize
}
#[inline]
pub fn from_array_index(i: usize) -> DefIndex {
DefIndex(i as u32)
}
// Proc macros from a proc-macro crate have a kind of virtual DefIndex. This
// function maps the index of the macro within the crate (which is also the
// index of the macro in the CrateMetadata::proc_macros array) to the
@ -132,7 +118,7 @@ impl DefIndex {
// DefIndex for proc macros start from FIRST_FREE_DEF_INDEX,
// because the first FIRST_FREE_DEF_INDEX indexes are reserved
// for internal use.
let def_index = DefIndex::from_array_index(
let def_index = DefIndex::from(
proc_macro_index.checked_add(FIRST_FREE_DEF_INDEX)
.expect("integer overflow adding `proc_macro_index`"));
assert!(def_index != CRATE_DEF_INDEX);
@ -141,19 +127,11 @@ impl DefIndex {
// This function is the reverse of from_proc_macro_index() above.
pub fn to_proc_macro_index(self: DefIndex) -> usize {
self.as_array_index().checked_sub(FIRST_FREE_DEF_INDEX)
self.index().checked_sub(FIRST_FREE_DEF_INDEX)
.unwrap_or_else(|| {
bug!("using local index {:?} as proc-macro index", self)
})
}
pub fn from_raw_u32(x: u32) -> DefIndex {
DefIndex(x)
}
pub fn as_raw_u32(&self) -> u32 {
self.0
}
}
impl serialize::UseSpecializedEncodable for DefIndex {}
@ -169,7 +147,7 @@ pub struct DefId {
impl fmt::Debug for DefId {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "DefId({}:{}", self.krate, self.index.as_array_index())?;
write!(f, "DefId({}:{}", self.krate, self.index.index())?;
ty::tls::with_opt(|opt_tcx| {
if let Some(tcx) = opt_tcx {

View File

@ -1032,11 +1032,6 @@ pub fn walk_expr<'v, V: Visitor<'v>>(visitor: &mut V, expression: &'v Expr) {
ExprKind::DropTemps(ref subexpression) => {
visitor.visit_expr(subexpression);
}
ExprKind::If(ref head_expression, ref if_block, ref optional_else) => {
visitor.visit_expr(head_expression);
visitor.visit_expr(if_block);
walk_list!(visitor, visit_expr, optional_else);
}
ExprKind::While(ref subexpression, ref block, ref opt_label) => {
walk_list!(visitor, visit_label, opt_label);
visitor.visit_expr(subexpression);

View File

@ -62,8 +62,9 @@ use syntax::ext::hygiene::Mark;
use syntax::print::pprust;
use syntax::ptr::P;
use syntax::source_map::{respan, CompilerDesugaringKind, Spanned};
use syntax::source_map::CompilerDesugaringKind::IfTemporary;
use syntax::std_inject;
use syntax::symbol::{keywords, Symbol};
use syntax::symbol::{keywords, Symbol, sym};
use syntax::tokenstream::{TokenStream, TokenTree};
use syntax::parse::token::Token;
use syntax::visit::{self, Visitor};
@ -72,7 +73,7 @@ use syntax_pos::Span;
const HIR_ID_COUNTER_LOCKED: u32 = 0xFFFFFFFF;
pub struct LoweringContext<'a> {
crate_root: Option<&'static str>,
crate_root: Option<Symbol>,
/// Used to assign ids to HIR nodes that do not directly correspond to an AST node.
sess: &'a Session,
@ -96,6 +97,10 @@ pub struct LoweringContext<'a> {
is_generator: bool,
is_async_body: bool,
/// Used to get the current `fn`'s def span to point to when using `await`
/// outside of an `async fn`.
current_item: Option<Span>,
catch_scopes: Vec<NodeId>,
loop_scopes: Vec<NodeId>,
is_in_loop_condition: bool,
@ -163,8 +168,8 @@ pub trait Resolver {
fn resolve_str_path(
&mut self,
span: Span,
crate_root: Option<&str>,
components: &[&str],
crate_root: Option<Symbol>,
components: &[Symbol],
is_value: bool,
) -> hir::Path;
}
@ -227,7 +232,7 @@ pub fn lower_crate(
dep_graph.assert_ignored();
LoweringContext {
crate_root: std_inject::injected_crate_name(),
crate_root: std_inject::injected_crate_name().map(Symbol::intern),
sess,
cstore,
resolver,
@ -249,6 +254,7 @@ pub fn lower_crate(
node_id_to_hir_id: IndexVec::new(),
is_generator: false,
is_async_body: false,
current_item: None,
is_in_trait_impl: false,
lifetimes_to_define: Vec::new(),
is_collecting_in_band_lifetimes: false,
@ -849,10 +855,6 @@ impl<'a> LoweringContext<'a> {
self.sess.diagnostic()
}
fn str_to_ident(&self, s: &'static str) -> Ident {
Ident::with_empty_ctxt(Symbol::gensym(s))
}
fn with_anonymous_lifetime_mode<R>(
&mut self,
anonymous_lifetime_mode: AnonymousLifetimeMode,
@ -1148,7 +1150,7 @@ impl<'a> LoweringContext<'a> {
].into()),
);
let gen_future = self.expr_std_path(
unstable_span, &["future", "from_generator"], None, ThinVec::new());
unstable_span, &[sym::future, sym::from_generator], None, ThinVec::new());
hir::ExprKind::Call(P(gen_future), hir_vec![generator])
}
@ -2212,7 +2214,7 @@ impl<'a> LoweringContext<'a> {
bindings: hir_vec![
hir::TypeBinding {
hir_id: this.next_id(),
ident: Ident::from_str(FN_OUTPUT_NAME),
ident: Ident::with_empty_ctxt(FN_OUTPUT_NAME),
ty: output
.as_ref()
.map(|ty| this.lower_ty(&ty, ImplTraitContext::disallowed()))
@ -2537,7 +2539,7 @@ impl<'a> LoweringContext<'a> {
let future_params = P(hir::GenericArgs {
args: hir_vec![],
bindings: hir_vec![hir::TypeBinding {
ident: Ident::from_str(FN_OUTPUT_NAME),
ident: Ident::with_empty_ctxt(FN_OUTPUT_NAME),
ty: output_ty,
hir_id: self.next_id(),
span,
@ -2547,7 +2549,7 @@ impl<'a> LoweringContext<'a> {
// ::std::future::Future<future_params>
let future_path =
self.std_path(span, &["future", "Future"], Some(future_params), false);
self.std_path(span, &[sym::future, sym::Future], Some(future_params), false);
hir::GenericBound::Trait(
hir::PolyTraitRef {
@ -2726,7 +2728,7 @@ impl<'a> LoweringContext<'a> {
self.lower_ty(x, ImplTraitContext::disallowed())
}),
synthetic: param.attrs.iter()
.filter(|attr| attr.check_name("rustc_synthetic"))
.filter(|attr| attr.check_name(sym::rustc_synthetic))
.map(|_| hir::SyntheticTyParamKind::ImplTrait)
.next(),
};
@ -2744,7 +2746,7 @@ impl<'a> LoweringContext<'a> {
hir_id: self.lower_node_id(param.id),
name,
span: param.ident.span,
pure_wrt_drop: attr::contains_name(&param.attrs, "may_dangle"),
pure_wrt_drop: attr::contains_name(&param.attrs, sym::may_dangle),
attrs: self.lower_attrs(&param.attrs),
bounds,
kind,
@ -3115,6 +3117,7 @@ impl<'a> LoweringContext<'a> {
ItemKind::Fn(ref decl, ref header, ref generics, ref body) => {
let fn_def_id = self.resolver.definitions().local_def_id(id);
self.with_new_scopes(|this| {
this.current_item = Some(ident.span);
let mut lower_fn = |decl: &FnDecl| {
// Note: we don't need to change the return type from `T` to
// `impl Future<Output = T>` here because lower_body
@ -3653,6 +3656,7 @@ impl<'a> LoweringContext<'a> {
} else {
lower_method(sig)
};
self.current_item = Some(i.span);
(generics, hir::ImplItemKind::Method(sig, body_id))
}
@ -3772,8 +3776,8 @@ impl<'a> LoweringContext<'a> {
let mut vis = self.lower_visibility(&i.vis, None);
let attrs = self.lower_attrs(&i.attrs);
if let ItemKind::MacroDef(ref def) = i.node {
if !def.legacy || attr::contains_name(&i.attrs, "macro_export") ||
attr::contains_name(&i.attrs, "rustc_doc_only_macro") {
if !def.legacy || attr::contains_name(&i.attrs, sym::macro_export) ||
attr::contains_name(&i.attrs, sym::rustc_doc_only_macro) {
let body = self.lower_token_stream(def.stream());
let hir_id = self.lower_node_id(i.id);
self.exported_macros.push(hir::MacroDef {
@ -4099,7 +4103,7 @@ impl<'a> LoweringContext<'a> {
let ohs = P(self.lower_expr(ohs));
hir::ExprKind::Unary(op, ohs)
}
ExprKind::Lit(ref l) => hir::ExprKind::Lit((*l).clone()),
ExprKind::Lit(ref l) => hir::ExprKind::Lit(respan(l.span, l.node.clone())),
ExprKind::Cast(ref expr, ref ty) => {
let expr = P(self.lower_expr(expr));
hir::ExprKind::Cast(expr, self.lower_ty(ty, ImplTraitContext::disallowed()))
@ -4115,31 +4119,46 @@ impl<'a> LoweringContext<'a> {
}
// More complicated than you might expect because the else branch
// might be `if let`.
ExprKind::If(ref cond, ref blk, ref else_opt) => {
let else_opt = else_opt.as_ref().map(|els| {
match els.node {
ExprKind::If(ref cond, ref then, ref else_opt) => {
// `true => then`:
let then_pat = self.pat_bool(e.span, true);
let then_blk = self.lower_block(then, false);
let then_expr = self.expr_block(then_blk, ThinVec::new());
let then_arm = self.arm(hir_vec![then_pat], P(then_expr));
// `_ => else_block` where `else_block` is `{}` if there's `None`:
let else_pat = self.pat_wild(e.span);
let else_expr = match else_opt {
None => self.expr_block_empty(e.span),
Some(els) => match els.node {
ExprKind::IfLet(..) => {
// Wrap the `if let` expr in a block.
let span = els.span;
let els = P(self.lower_expr(els));
let blk = P(hir::Block {
stmts: hir_vec![],
expr: Some(els),
hir_id: self.next_id(),
rules: hir::DefaultBlock,
span,
targeted_by_break: false,
});
P(self.expr_block(blk, ThinVec::new()))
let els = self.lower_expr(els);
let blk = self.block_all(els.span, hir_vec![], Some(P(els)));
self.expr_block(P(blk), ThinVec::new())
}
_ => P(self.lower_expr(els)),
_ => self.lower_expr(els),
}
});
};
let else_arm = self.arm(hir_vec![else_pat], P(else_expr));
let then_blk = self.lower_block(blk, false);
let then_expr = self.expr_block(then_blk, ThinVec::new());
// Lower condition:
let span_block = self
.sess
.source_map()
.mark_span_with_reason(IfTemporary, cond.span, None);
let cond = self.lower_expr(cond);
// Wrap in a construct equivalent to `{ let _t = $cond; _t }` to preserve drop
// semantics since `if cond { ... }` don't let temporaries live outside of `cond`.
let cond = self.expr_drop_temps(span_block, P(cond), ThinVec::new());
hir::ExprKind::If(P(self.lower_expr(cond)), P(then_expr), else_opt)
hir::ExprKind::Match(
P(cond),
vec![then_arm, else_arm].into(),
hir::MatchSource::IfDesugar {
contains_else_clause: else_opt.is_some()
},
)
}
ExprKind::While(ref cond, ref body, opt_label) => self.with_loop_scope(e.id, |this| {
hir::ExprKind::While(
@ -4178,7 +4197,7 @@ impl<'a> LoweringContext<'a> {
|x: P<hir::Expr>| x.into_inner(),
);
block.expr = Some(this.wrap_in_try_constructor(
"from_ok", tail, unstable_span));
sym::from_ok, tail, unstable_span));
hir::ExprKind::Block(P(block), None)
})
}
@ -4254,6 +4273,7 @@ impl<'a> LoweringContext<'a> {
let fn_decl = self.lower_fn_decl(decl, None, false, None);
self.with_new_scopes(|this| {
this.current_item = Some(fn_decl_span);
let mut is_generator = false;
let body_id = this.lower_body(Some(decl), |this| {
let e = this.lower_expr(body);
@ -4320,7 +4340,7 @@ impl<'a> LoweringContext<'a> {
self.expr_call_std_assoc_fn(
id,
e.span,
&["ops", "RangeInclusive"],
&[sym::ops, sym::RangeInclusive],
"new",
hir_vec![e1, e2],
)
@ -4329,11 +4349,11 @@ impl<'a> LoweringContext<'a> {
use syntax::ast::RangeLimits::*;
let path = match (e1, e2, lims) {
(&None, &None, HalfOpen) => "RangeFull",
(&Some(..), &None, HalfOpen) => "RangeFrom",
(&None, &Some(..), HalfOpen) => "RangeTo",
(&Some(..), &Some(..), HalfOpen) => "Range",
(&None, &Some(..), Closed) => "RangeToInclusive",
(&None, &None, HalfOpen) => sym::RangeFull,
(&Some(..), &None, HalfOpen) => sym::RangeFrom,
(&None, &Some(..), HalfOpen) => sym::RangeTo,
(&Some(..), &Some(..), HalfOpen) => sym::Range,
(&None, &Some(..), Closed) => sym::RangeToInclusive,
(&Some(..), &Some(..), Closed) => unreachable!(),
(_, &None, Closed) => self.diagnostic()
.span_fatal(e.span, "inclusive range with no end")
@ -4351,7 +4371,7 @@ impl<'a> LoweringContext<'a> {
.collect::<P<[hir::Field]>>();
let is_unit = fields.is_empty();
let struct_path = ["ops", path];
let struct_path = [sym::ops, path];
let struct_path = self.std_path(e.span, &struct_path, None, is_unit);
let struct_path = hir::QPath::Resolved(None, P(struct_path));
@ -4486,16 +4506,16 @@ impl<'a> LoweringContext<'a> {
arms.push(self.arm(pats, body_expr));
}
// _ => [<else_opt>|()]
// _ => [<else_opt>|{}]
{
let wildcard_arm: Option<&Expr> = else_opt.as_ref().map(|p| &**p);
let wildcard_pattern = self.pat_wild(e.span);
let body = if let Some(else_expr) = wildcard_arm {
P(self.lower_expr(else_expr))
self.lower_expr(else_expr)
} else {
P(self.expr_tuple(e.span, hir_vec![]))
self.expr_block_empty(e.span)
};
arms.push(self.arm(hir_vec![wildcard_pattern], body));
arms.push(self.arm(hir_vec![wildcard_pattern], P(body)));
}
let contains_else_clause = else_opt.is_some();
@ -4597,18 +4617,18 @@ impl<'a> LoweringContext<'a> {
);
head.span = desugared_span;
let iter = self.str_to_ident("iter");
let iter = Ident::with_empty_ctxt(sym::iter);
let next_ident = self.str_to_ident("__next");
let next_ident = Ident::with_empty_ctxt(sym::__next);
let (next_pat, next_pat_hid) = self.pat_ident_binding_mode(
desugared_span,
next_ident,
hir::BindingAnnotation::Mutable,
);
// `::std::option::Option::Some(val) => next = val`
// `::std::option::Option::Some(val) => __next = val`
let pat_arm = {
let val_ident = self.str_to_ident("val");
let val_ident = Ident::with_empty_ctxt(sym::val);
let (val_pat, val_pat_hid) = self.pat_ident(pat.span, val_ident);
let val_expr = P(self.expr_ident(pat.span, val_ident, val_pat_hid));
let next_expr = P(self.expr_ident(pat.span, next_ident, next_pat_hid));
@ -4640,7 +4660,7 @@ impl<'a> LoweringContext<'a> {
let match_expr = {
let iter = P(self.expr_ident(head_sp, iter, iter_pat_nid));
let ref_mut_iter = self.expr_mut_addr_of(head_sp, iter);
let next_path = &["iter", "Iterator", "next"];
let next_path = &[sym::iter, sym::Iterator, sym::next];
let next_expr = P(self.expr_call_std_path(
head_sp,
next_path,
@ -4658,11 +4678,7 @@ impl<'a> LoweringContext<'a> {
ThinVec::new(),
))
};
let match_stmt = hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Expr(match_expr),
span: head_sp,
};
let match_stmt = self.stmt(head_sp, hir::StmtKind::Expr(match_expr));
let next_expr = P(self.expr_ident(head_sp, next_ident, next_pat_hid));
@ -4685,11 +4701,7 @@ impl<'a> LoweringContext<'a> {
let body_block = self.with_loop_scope(e.id, |this| this.lower_block(body, false));
let body_expr = P(self.expr_block(body_block, ThinVec::new()));
let body_stmt = hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Expr(body_expr),
span: body.span,
};
let body_stmt = self.stmt(body.span, hir::StmtKind::Expr(body_expr));
let loop_block = P(self.block_all(
e.span,
@ -4715,7 +4727,8 @@ impl<'a> LoweringContext<'a> {
// `match ::std::iter::IntoIterator::into_iter(<head>) { ... }`
let into_iter_expr = {
let into_iter_path = &["iter", "IntoIterator", "into_iter"];
let into_iter_path =
&[sym::iter, sym::IntoIterator, sym::into_iter];
P(self.expr_call_std_path(
head_sp,
into_iter_path,
@ -4754,17 +4767,13 @@ impl<'a> LoweringContext<'a> {
let unstable_span = self.sess.source_map().mark_span_with_reason(
CompilerDesugaringKind::QuestionMark,
e.span,
Some(vec![
Symbol::intern("try_trait")
].into()),
Some(vec![sym::try_trait].into()),
);
let try_span = self.sess.source_map().end_point(e.span);
let try_span = self.sess.source_map().mark_span_with_reason(
CompilerDesugaringKind::QuestionMark,
try_span,
Some(vec![
Symbol::intern("try_trait")
].into()),
Some(vec![sym::try_trait].into()),
);
// `Try::into_result(<expr>)`
@ -4772,7 +4781,7 @@ impl<'a> LoweringContext<'a> {
// expand <expr>
let sub_expr = self.lower_expr(sub_expr);
let path = &["ops", "Try", "into_result"];
let path = &[sym::ops, sym::Try, sym::into_result];
P(self.expr_call_std_path(
unstable_span,
path,
@ -4784,8 +4793,9 @@ impl<'a> LoweringContext<'a> {
let attr = {
// `allow(unreachable_code)`
let allow = {
let allow_ident = Ident::from_str("allow").with_span_pos(e.span);
let uc_ident = Ident::from_str("unreachable_code").with_span_pos(e.span);
let allow_ident = Ident::with_empty_ctxt(sym::allow).with_span_pos(e.span);
let uc_ident = Ident::with_empty_ctxt(sym::unreachable_code)
.with_span_pos(e.span);
let uc_nested = attr::mk_nested_word_item(uc_ident);
attr::mk_list_item(e.span, allow_ident, vec![uc_nested])
};
@ -4795,7 +4805,7 @@ impl<'a> LoweringContext<'a> {
// `Ok(val) => #[allow(unreachable_code)] val,`
let ok_arm = {
let val_ident = self.str_to_ident("val");
let val_ident = Ident::with_empty_ctxt(sym::val);
let (val_pat, val_pat_nid) = self.pat_ident(e.span, val_ident);
let val_expr = P(self.expr_ident_with_attrs(
e.span,
@ -4811,15 +4821,15 @@ impl<'a> LoweringContext<'a> {
// `Err(err) => #[allow(unreachable_code)]
// return Try::from_error(From::from(err)),`
let err_arm = {
let err_ident = self.str_to_ident("err");
let err_ident = Ident::with_empty_ctxt(sym::err);
let (err_local, err_local_nid) = self.pat_ident(try_span, err_ident);
let from_expr = {
let from_path = &["convert", "From", "from"];
let from_path = &[sym::convert, sym::From, sym::from];
let err_expr = self.expr_ident(try_span, err_ident, err_local_nid);
self.expr_call_std_path(try_span, from_path, hir_vec![err_expr])
};
let from_err_expr =
self.wrap_in_try_constructor("from_error", from_expr, unstable_span);
self.wrap_in_try_constructor(sym::from_error, from_expr, unstable_span);
let thin_attrs = ThinVec::from(attrs);
let catch_scope = self.catch_scopes.last().map(|x| *x);
let ret_expr = if let Some(catch_node) = catch_scope {
@ -4869,12 +4879,7 @@ impl<'a> LoweringContext<'a> {
.into_iter()
.map(|item_id| {
let item_id = hir::ItemId { id: self.lower_node_id(item_id) };
hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Item(item_id),
span: s.span,
}
self.stmt(s.span, hir::StmtKind::Item(item_id))
})
.collect();
ids.push({
@ -5054,7 +5059,7 @@ impl<'a> LoweringContext<'a> {
fn expr_call_std_path(
&mut self,
span: Span,
path_components: &[&str],
path_components: &[Symbol],
args: hir::HirVec<hir::Expr>,
) -> hir::Expr {
let path = P(self.expr_std_path(span, path_components, None, ThinVec::new()));
@ -5074,7 +5079,7 @@ impl<'a> LoweringContext<'a> {
&mut self,
ty_path_id: hir::HirId,
span: Span,
ty_path_components: &[&str],
ty_path_components: &[Symbol],
assoc_fn_name: &str,
args: hir::HirVec<hir::Expr>,
) -> hir::ExprKind {
@ -5116,7 +5121,7 @@ impl<'a> LoweringContext<'a> {
fn expr_std_path(
&mut self,
span: Span,
components: &[&str],
components: &[Symbol],
params: Option<P<hir::GenericArgs>>,
attrs: ThinVec<Attribute>,
) -> hir::Expr {
@ -5174,28 +5179,32 @@ impl<'a> LoweringContext<'a> {
}
}
fn stmt(&mut self, span: Span, node: hir::StmtKind) -> hir::Stmt {
hir::Stmt { span, node, hir_id: self.next_id() }
}
fn stmt_let_pat(
&mut self,
sp: Span,
ex: Option<P<hir::Expr>>,
span: Span,
init: Option<P<hir::Expr>>,
pat: P<hir::Pat>,
source: hir::LocalSource,
) -> hir::Stmt {
let local = hir::Local {
pat,
ty: None,
init: ex,
init,
hir_id: self.next_id(),
span: sp,
attrs: ThinVec::new(),
span,
source,
attrs: ThinVec::new()
};
self.stmt(span, hir::StmtKind::Local(P(local)))
}
hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Local(P(local)),
span: sp
}
fn expr_block_empty(&mut self, span: Span) -> hir::Expr {
let blk = self.block_all(span, hir_vec![], None);
self.expr_block(P(blk), ThinVec::new())
}
fn block_expr(&mut self, expr: P<hir::Expr>) -> hir::Block {
@ -5235,26 +5244,33 @@ impl<'a> LoweringContext<'a> {
)
}
/// Constructs a `true` or `false` literal pattern.
fn pat_bool(&mut self, span: Span, val: bool) -> P<hir::Pat> {
let lit = Spanned { span, node: LitKind::Bool(val) };
let expr = self.expr(span, hir::ExprKind::Lit(lit), ThinVec::new());
self.pat(span, hir::PatKind::Lit(P(expr)))
}
fn pat_ok(&mut self, span: Span, pat: P<hir::Pat>) -> P<hir::Pat> {
self.pat_std_enum(span, &["result", "Result", "Ok"], hir_vec![pat])
self.pat_std_enum(span, &[sym::result, sym::Result, sym::Ok], hir_vec![pat])
}
fn pat_err(&mut self, span: Span, pat: P<hir::Pat>) -> P<hir::Pat> {
self.pat_std_enum(span, &["result", "Result", "Err"], hir_vec![pat])
self.pat_std_enum(span, &[sym::result, sym::Result, sym::Err], hir_vec![pat])
}
fn pat_some(&mut self, span: Span, pat: P<hir::Pat>) -> P<hir::Pat> {
self.pat_std_enum(span, &["option", "Option", "Some"], hir_vec![pat])
self.pat_std_enum(span, &[sym::option, sym::Option, sym::Some], hir_vec![pat])
}
fn pat_none(&mut self, span: Span) -> P<hir::Pat> {
self.pat_std_enum(span, &["option", "Option", "None"], hir_vec![])
self.pat_std_enum(span, &[sym::option, sym::Option, sym::None], hir_vec![])
}
fn pat_std_enum(
&mut self,
span: Span,
components: &[&str],
components: &[Symbol],
subpats: hir::HirVec<P<hir::Pat>>,
) -> P<hir::Pat> {
let path = self.std_path(span, components, None, true);
@ -5307,7 +5323,7 @@ impl<'a> LoweringContext<'a> {
fn std_path(
&mut self,
span: Span,
components: &[&str],
components: &[Symbol],
params: Option<P<hir::GenericArgs>>,
is_value: bool,
) -> hir::Path {
@ -5506,11 +5522,11 @@ impl<'a> LoweringContext<'a> {
fn wrap_in_try_constructor(
&mut self,
method: &'static str,
method: Symbol,
e: hir::Expr,
unstable_span: Span,
) -> P<hir::Expr> {
let path = &["ops", "Try", method];
let path = &[sym::ops, sym::Try, method];
let from_err = P(self.expr_std_path(unstable_span, path, None,
ThinVec::new()));
P(self.expr_call(e.span, from_err, hir_vec![e]))
@ -5529,20 +5545,25 @@ impl<'a> LoweringContext<'a> {
// match ::std::future::poll_with_tls_context(unsafe {
// ::std::pin::Pin::new_unchecked(&mut pinned)
// }) {
// ::std::task::Poll::Ready(x) => break x,
// ::std::task::Poll::Ready(result) => break result,
// ::std::task::Poll::Pending => {},
// }
// yield ();
// }
// }
if !self.is_async_body {
span_err!(
let mut err = struct_span_err!(
self.sess,
await_span,
E0728,
"`await` is only allowed inside `async` functions and blocks"
);
self.sess.abort_if_errors();
err.span_label(await_span, "only allowed inside `async` functions and blocks");
if let Some(item_sp) = self.current_item {
err.span_label(item_sp, "this is not `async`");
}
err.emit();
return hir::ExprKind::Err;
}
let span = self.sess.source_map().mark_span_with_reason(
CompilerDesugaringKind::Await,
@ -5552,12 +5573,12 @@ impl<'a> LoweringContext<'a> {
let gen_future_span = self.sess.source_map().mark_span_with_reason(
CompilerDesugaringKind::Await,
await_span,
Some(vec![Symbol::intern("gen_future")].into()),
Some(vec![sym::gen_future].into()),
);
// let mut pinned = <expr>;
let expr = P(self.lower_expr(expr));
let pinned_ident = self.str_to_ident("pinned");
let pinned_ident = Ident::with_empty_ctxt(sym::pinned);
let (pinned_pat, pinned_pat_hid) = self.pat_ident_binding_mode(
span,
pinned_ident,
@ -5580,7 +5601,7 @@ impl<'a> LoweringContext<'a> {
let new_unchecked_expr_kind = self.expr_call_std_assoc_fn(
pin_ty_id,
span,
&["pin", "Pin"],
&[sym::pin, sym::Pin],
"new_unchecked",
hir_vec![ref_mut_pinned],
);
@ -5588,21 +5609,21 @@ impl<'a> LoweringContext<'a> {
let unsafe_expr = self.expr_unsafe(new_unchecked);
P(self.expr_call_std_path(
gen_future_span,
&["future", "poll_with_tls_context"],
&[sym::future, sym::poll_with_tls_context],
hir_vec![unsafe_expr],
))
};
// `::std::task::Poll::Ready(x) => break x`
// `::std::task::Poll::Ready(result) => break result`
let loop_node_id = self.sess.next_node_id();
let loop_hir_id = self.lower_node_id(loop_node_id);
let ready_arm = {
let x_ident = self.str_to_ident("x");
let x_ident = Ident::with_empty_ctxt(sym::result);
let (x_pat, x_pat_hid) = self.pat_ident(span, x_ident);
let x_expr = P(self.expr_ident(span, x_ident, x_pat_hid));
let ready_pat = self.pat_std_enum(
span,
&["task", "Poll", "Ready"],
&[sym::task, sym::Poll, sym::Ready],
hir_vec![x_pat],
);
let break_x = self.with_loop_scope(loop_node_id, |this| {
@ -5619,18 +5640,10 @@ impl<'a> LoweringContext<'a> {
let pending_arm = {
let pending_pat = self.pat_std_enum(
span,
&["task", "Poll", "Pending"],
&[sym::task, sym::Poll, sym::Pending],
hir_vec![],
);
let empty_block = P(hir::Block {
stmts: hir_vec![],
expr: None,
hir_id: self.next_id(),
rules: hir::DefaultBlock,
span,
targeted_by_break: false,
});
let empty_block = P(self.expr_block(empty_block, ThinVec::new()));
let empty_block = P(self.expr_block_empty(span));
self.arm(hir_vec![pending_pat], empty_block)
};
@ -5641,11 +5654,7 @@ impl<'a> LoweringContext<'a> {
hir_vec![ready_arm, pending_arm],
hir::MatchSource::AwaitDesugar,
));
hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Expr(match_expr),
span,
}
self.stmt(span, hir::StmtKind::Expr(match_expr))
};
let yield_stmt = {
@ -5655,11 +5664,7 @@ impl<'a> LoweringContext<'a> {
hir::ExprKind::Yield(P(unit)),
ThinVec::new(),
));
hir::Stmt {
hir_id: self.next_id(),
node: hir::StmtKind::Expr(yield_expr),
span,
}
self.stmt(span, hir::StmtKind::Expr(yield_expr))
};
let loop_block = P(self.block_all(

View File

@ -226,7 +226,7 @@ impl<'a, 'hir> NodeCollector<'a, 'hir> {
fn insert_entry(&mut self, id: HirId, entry: Entry<'hir>) {
debug!("hir_map: {:?} => {:?}", id, entry);
let local_map = &mut self.map[id.owner.as_array_index()];
let local_map = &mut self.map[id.owner.index()];
let i = id.local_id.as_u32() as usize;
if local_map.is_none() {
*local_map = Some(IndexVec::with_capacity(i + 1));

View File

@ -17,7 +17,7 @@ use std::fmt::Write;
use std::hash::Hash;
use syntax::ast;
use syntax::ext::hygiene::Mark;
use syntax::symbol::{Symbol, InternedString};
use syntax::symbol::{Symbol, sym, InternedString};
use syntax_pos::{Span, DUMMY_SP};
use crate::util::nodemap::NodeMap;
@ -38,7 +38,7 @@ impl DefPathTable {
def_path_hash: DefPathHash)
-> DefIndex {
let index = {
let index = DefIndex::from_array_index(self.index_to_key.len());
let index = DefIndex::from(self.index_to_key.len());
debug!("DefPathTable::insert() - {:?} <-> {:?}", key, index);
self.index_to_key.push(key);
index
@ -49,17 +49,17 @@ impl DefPathTable {
}
pub fn next_id(&self) -> DefIndex {
DefIndex::from_array_index(self.index_to_key.len())
DefIndex::from(self.index_to_key.len())
}
#[inline(always)]
pub fn def_key(&self, index: DefIndex) -> DefKey {
self.index_to_key[index.as_array_index()].clone()
self.index_to_key[index.index()].clone()
}
#[inline(always)]
pub fn def_path_hash(&self, index: DefIndex) -> DefPathHash {
let ret = self.def_path_hashes[index.as_array_index()];
let ret = self.def_path_hashes[index.index()];
debug!("def_path_hash({:?}) = {:?}", index, ret);
return ret
}
@ -74,7 +74,7 @@ impl DefPathTable {
.map(|(index, &hash)| {
let def_id = DefId {
krate: cnum,
index: DefIndex::from_array_index(index),
index: DefIndex::from(index),
};
(hash, def_id)
})
@ -387,7 +387,7 @@ impl Definitions {
#[inline]
pub fn as_local_node_id(&self, def_id: DefId) -> Option<ast::NodeId> {
if def_id.krate == LOCAL_CRATE {
let node_id = self.def_index_to_node[def_id.index.as_array_index()];
let node_id = self.def_index_to_node[def_id.index.index()];
if node_id != ast::DUMMY_NODE_ID {
return Some(node_id);
}
@ -417,7 +417,7 @@ impl Definitions {
#[inline]
pub fn def_index_to_hir_id(&self, def_index: DefIndex) -> hir::HirId {
let node_id = self.def_index_to_node[def_index.as_array_index()];
let node_id = self.def_index_to_node[def_index.index()];
self.node_to_hir_id[node_id]
}
@ -508,7 +508,7 @@ impl Definitions {
// Create the definition.
let index = self.table.allocate(key, def_path_hash);
assert_eq!(index.as_array_index(), self.def_index_to_node.len());
assert_eq!(index.index(), self.def_index_to_node.len());
self.def_index_to_node.push(node_id);
// Some things for which we allocate DefIndices don't correspond to
@ -584,16 +584,16 @@ impl DefPathData {
return name
}
// note that this does not show up in user printouts
CrateRoot => "{{crate}}",
Impl => "{{impl}}",
Misc => "{{misc}}",
ClosureExpr => "{{closure}}",
Ctor => "{{constructor}}",
AnonConst => "{{constant}}",
ImplTrait => "{{opaque}}",
CrateRoot => sym::double_braced_crate,
Impl => sym::double_braced_impl,
Misc => sym::double_braced_misc,
ClosureExpr => sym::double_braced_closure,
Ctor => sym::double_braced_constructor,
AnonConst => sym::double_braced_constant,
ImplTrait => sym::double_braced_opaque,
};
Symbol::intern(s).as_interned_str()
s.as_interned_str()
}
pub fn to_string(&self) -> String {
@ -653,7 +653,7 @@ macro_rules! define_global_metadata_kind {
.position(|k| *k == def_key)
.unwrap();
DefIndex::from_array_index(index)
DefIndex::from(index)
}
fn name(&self) -> Symbol {

View File

@ -189,7 +189,7 @@ pub struct Map<'hir> {
impl<'hir> Map<'hir> {
#[inline]
fn lookup(&self, id: HirId) -> Option<&Entry<'hir>> {
let local_map = self.map.get(id.owner.as_array_index())?;
let local_map = self.map.get(id.owner.index())?;
local_map.as_ref()?.get(id.local_id)?.as_ref()
}
@ -1023,7 +1023,7 @@ impl<'hir> Map<'hir> {
local_map.iter_enumerated().filter_map(move |(i, entry)| entry.map(move |_| {
// Reconstruct the HirId based on the 3 indices we used to find it
HirId {
owner: DefIndex::from_array_index(array_index),
owner: DefIndex::from(array_index),
local_id: i,
}
}))
@ -1146,7 +1146,7 @@ impl<'a> NodesMatchingSuffix<'a> {
None => return false,
Some((node_id, name)) => (node_id, name),
};
if mod_name != &**part {
if mod_name.as_str() != *part {
return false;
}
cursor = self.map.get_parent_item(mod_id);
@ -1183,7 +1183,7 @@ impl<'a> NodesMatchingSuffix<'a> {
// We are looking at some node `n` with a given name and parent
// id; do their names match what I am seeking?
fn matches_names(&self, parent_of_n: HirId, name: Name) -> bool {
name == &**self.item_name && self.suffix_matches(parent_of_n)
name.as_str() == *self.item_name && self.suffix_matches(parent_of_n)
}
fn matches_suffix(&self, hir: HirId) -> bool {

View File

@ -20,7 +20,7 @@ use syntax_pos::{Span, DUMMY_SP, symbol::InternedString};
use syntax::source_map::Spanned;
use rustc_target::spec::abi::Abi;
use syntax::ast::{self, CrateSugar, Ident, Name, NodeId, AsmDialect};
use syntax::ast::{Attribute, Label, Lit, StrStyle, FloatTy, IntTy, UintTy};
use syntax::ast::{Attribute, Label, LitKind, StrStyle, FloatTy, IntTy, UintTy};
use syntax::attr::{InlineAttr, OptimizeAttr};
use syntax::ext::hygiene::SyntaxContext;
use syntax::ptr::P;
@ -126,12 +126,12 @@ mod item_local_id_inner {
use rustc_macros::HashStable;
newtype_index! {
/// An `ItemLocalId` uniquely identifies something within a given "item-like",
/// that is within a hir::Item, hir::TraitItem, or hir::ImplItem. There is no
/// that is, within a hir::Item, hir::TraitItem, or hir::ImplItem. There is no
/// guarantee that the numerical value of a given `ItemLocalId` corresponds to
/// the node's position within the owning item in any way, but there is a
/// guarantee that the `LocalItemId`s within an owner occupy a dense range of
/// integers starting at zero, so a mapping that maps all or most nodes within
/// an "item-like" to something else can be implement by a `Vec` instead of a
/// an "item-like" to something else can be implemented by a `Vec` instead of a
/// tree or hash map.
pub struct ItemLocalId {
derive [HashStable]
@ -609,9 +609,9 @@ impl Generics {
own_counts
}
pub fn get_named(&self, name: &InternedString) -> Option<&GenericParam> {
pub fn get_named(&self, name: InternedString) -> Option<&GenericParam> {
for param in &self.params {
if *name == param.name.ident().as_interned_str() {
if name == param.name.ident().as_interned_str() {
return Some(param);
}
}
@ -1331,6 +1331,9 @@ impl BodyOwnerKind {
}
}
/// A literal.
pub type Lit = Spanned<LitKind>;
/// A constant (expression) that's not an item or associated item,
/// but needs its own `DefId` for type-checking, const-eval, etc.
/// These are usually found nested inside types (e.g., array lengths)
@ -1353,7 +1356,7 @@ pub struct Expr {
// `Expr` is used a lot. Make sure it doesn't unintentionally get bigger.
#[cfg(target_arch = "x86_64")]
static_assert!(MEM_SIZE_OF_EXPR: std::mem::size_of::<Expr>() == 72);
static_assert_size!(Expr, 72);
impl Expr {
pub fn precedence(&self) -> ExprPrecedence {
@ -1368,7 +1371,6 @@ impl Expr {
ExprKind::Lit(_) => ExprPrecedence::Lit,
ExprKind::Type(..) | ExprKind::Cast(..) => ExprPrecedence::Cast,
ExprKind::DropTemps(ref expr, ..) => expr.precedence(),
ExprKind::If(..) => ExprPrecedence::If,
ExprKind::While(..) => ExprPrecedence::While,
ExprKind::Loop(..) => ExprPrecedence::Loop,
ExprKind::Match(..) => ExprPrecedence::Match,
@ -1421,7 +1423,6 @@ impl Expr {
ExprKind::MethodCall(..) |
ExprKind::Struct(..) |
ExprKind::Tup(..) |
ExprKind::If(..) |
ExprKind::Match(..) |
ExprKind::Closure(..) |
ExprKind::Block(..) |
@ -1498,10 +1499,6 @@ pub enum ExprKind {
/// This construct only exists to tweak the drop order in HIR lowering.
/// An example of that is the desugaring of `for` loops.
DropTemps(P<Expr>),
/// An `if` block, with an optional else block.
///
/// I.e., `if <expr> { <expr> } else { <expr> }`.
If(P<Expr>, P<Expr>, Option<P<Expr>>),
/// A while loop, with an optional label
///
/// I.e., `'label: while expr { <block> }`.
@ -1615,6 +1612,10 @@ pub enum LocalSource {
pub enum MatchSource {
/// A `match _ { .. }`.
Normal,
/// An `if _ { .. }` (optionally with `else { .. }`).
IfDesugar {
contains_else_clause: bool,
},
/// An `if let _ = _ { .. }` (optionally with `else { .. }`).
IfLetDesugar {
contains_else_clause: bool,

View File

@ -5,7 +5,7 @@ use syntax::parse::ParseSess;
use syntax::parse::lexer::comments;
use syntax::print::pp::{self, Breaks};
use syntax::print::pp::Breaks::{Consistent, Inconsistent};
use syntax::print::pprust::PrintState;
use syntax::print::pprust::{self, PrintState};
use syntax::ptr::P;
use syntax::symbol::keywords;
use syntax::util::parser::{self, AssocOp, Fixity};
@ -18,7 +18,6 @@ use crate::hir::{GenericParam, GenericParamKind, GenericArg};
use std::borrow::Cow;
use std::cell::Cell;
use std::io::{self, Write, Read};
use std::iter::Peekable;
use std::vec;
pub enum AnnNode<'a> {
@ -76,7 +75,6 @@ pub struct State<'a> {
pub s: pp::Printer<'a>,
cm: Option<&'a SourceMap>,
comments: Option<Vec<comments::Comment>>,
literals: Peekable<vec::IntoIter<comments::Literal>>,
cur_cmnt: usize,
boxes: Vec<pp::Breaks>,
ann: &'a (dyn PpAnn + 'a),
@ -98,14 +96,6 @@ impl<'a> PrintState<'a> for State<'a> {
fn cur_cmnt(&mut self) -> &mut usize {
&mut self.cur_cmnt
}
fn cur_lit(&mut self) -> Option<&comments::Literal> {
self.literals.peek()
}
fn bump_lit(&mut self) -> Option<comments::Literal> {
self.literals.next()
}
}
#[allow(non_upper_case_globals)]
@ -116,18 +106,16 @@ pub const default_columns: usize = 78;
/// Requires you to pass an input filename and reader so that
/// it can scan the input text for comments and literals to
/// copy forward.
/// it can scan the input text for comments to copy forward.
pub fn print_crate<'a>(cm: &'a SourceMap,
sess: &ParseSess,
krate: &hir::Crate,
filename: FileName,
input: &mut dyn Read,
out: Box<dyn Write + 'a>,
ann: &'a dyn PpAnn,
is_expanded: bool)
ann: &'a dyn PpAnn)
-> io::Result<()> {
let mut s = State::new_from_input(cm, sess, filename, input, out, ann, is_expanded);
let mut s = State::new_from_input(cm, sess, filename, input, out, ann);
// When printing the AST, we sometimes need to inject `#[no_std]` here.
// Since you can't compile the HIR, it's not necessary.
@ -143,36 +131,21 @@ impl<'a> State<'a> {
filename: FileName,
input: &mut dyn Read,
out: Box<dyn Write + 'a>,
ann: &'a dyn PpAnn,
is_expanded: bool)
ann: &'a dyn PpAnn)
-> State<'a> {
let (cmnts, lits) = comments::gather_comments_and_literals(sess, filename, input);
State::new(cm,
out,
ann,
Some(cmnts),
// If the code is post expansion, don't use the table of
// literals, since it doesn't correspond with the literals
// in the AST anymore.
if is_expanded {
None
} else {
Some(lits)
})
let comments = comments::gather_comments(sess, filename, input);
State::new(cm, out, ann, Some(comments))
}
pub fn new(cm: &'a SourceMap,
out: Box<dyn Write + 'a>,
ann: &'a dyn PpAnn,
comments: Option<Vec<comments::Comment>>,
literals: Option<Vec<comments::Literal>>)
comments: Option<Vec<comments::Comment>>)
-> State<'a> {
State {
s: pp::mk_printer(out, default_columns),
cm: Some(cm),
comments,
literals: literals.unwrap_or_default().into_iter().peekable(),
cur_cmnt: 0,
boxes: Vec::new(),
ann,
@ -189,7 +162,6 @@ pub fn to_string<F>(ann: &dyn PpAnn, f: F) -> String
s: pp::mk_printer(Box::new(&mut wr), default_columns),
cm: None,
comments: None,
literals: vec![].into_iter().peekable(),
cur_cmnt: 0,
boxes: Vec::new(),
ann,
@ -646,7 +618,6 @@ impl<'a> State<'a> {
self.print_where_clause(&exist.generics.where_clause)?;
self.s.space()?;
self.word_space(":")?;
let mut real_bounds = Vec::with_capacity(exist.bounds.len());
for b in exist.bounds.iter() {
if let GenericBound::Trait(ref ptr, hir::TraitBoundModifier::Maybe) = *b {
@ -1093,65 +1064,6 @@ impl<'a> State<'a> {
self.ann.post(self, AnnNode::Block(blk))
}
fn print_else(&mut self, els: Option<&hir::Expr>) -> io::Result<()> {
match els {
Some(_else) => {
match _else.node {
// "another else-if"
hir::ExprKind::If(ref i, ref then, ref e) => {
self.cbox(indent_unit - 1)?;
self.ibox(0)?;
self.s.word(" else if ")?;
self.print_expr_as_cond(&i)?;
self.s.space()?;
self.print_expr(&then)?;
self.print_else(e.as_ref().map(|e| &**e))
}
// "final else"
hir::ExprKind::Block(ref b, _) => {
self.cbox(indent_unit - 1)?;
self.ibox(0)?;
self.s.word(" else ")?;
self.print_block(&b)
}
// BLEAH, constraints would be great here
_ => {
panic!("print_if saw if with weird alternative");
}
}
}
_ => Ok(()),
}
}
pub fn print_if(&mut self,
test: &hir::Expr,
blk: &hir::Expr,
elseopt: Option<&hir::Expr>)
-> io::Result<()> {
self.head("if")?;
self.print_expr_as_cond(test)?;
self.s.space()?;
self.print_expr(blk)?;
self.print_else(elseopt)
}
pub fn print_if_let(&mut self,
pat: &hir::Pat,
expr: &hir::Expr,
blk: &hir::Block,
elseopt: Option<&hir::Expr>)
-> io::Result<()> {
self.head("if let")?;
self.print_pat(pat)?;
self.s.space()?;
self.word_space("=")?;
self.print_expr_as_cond(expr)?;
self.s.space()?;
self.print_block(blk)?;
self.print_else(elseopt)
}
pub fn print_anon_const(&mut self, constant: &hir::AnonConst) -> io::Result<()> {
self.ann.nested(self, Nested::Body(constant.body))
}
@ -1335,6 +1247,12 @@ impl<'a> State<'a> {
self.print_expr_maybe_paren(expr, parser::PREC_PREFIX)
}
fn print_literal(&mut self, lit: &hir::Lit) -> io::Result<()> {
self.maybe_print_comment(lit.span.lo())?;
let (token, suffix) = lit.node.to_lit_token();
self.writer().word(pprust::literal_to_string(token, suffix))
}
pub fn print_expr(&mut self, expr: &hir::Expr) -> io::Result<()> {
self.maybe_print_comment(expr.span.lo())?;
self.print_outer_attributes(&expr.attrs)?;
@ -1406,9 +1324,6 @@ impl<'a> State<'a> {
// Print `}`:
self.bclose_maybe_open(expr.span, indent_unit, true)?;
}
hir::ExprKind::If(ref test, ref blk, ref elseopt) => {
self.print_if(&test, &blk, elseopt.as_ref().map(|e| &**e))?;
}
hir::ExprKind::While(ref test, ref blk, opt_label) => {
if let Some(label) = opt_label {
self.print_ident(label.ident)?;
@ -2414,7 +2329,6 @@ impl<'a> State<'a> {
/// isn't parsed as (if true {...} else {...} | x) | 5
fn expr_requires_semi_to_be_stmt(e: &hir::Expr) -> bool {
match e.node {
hir::ExprKind::If(..) |
hir::ExprKind::Match(..) |
hir::ExprKind::Block(..) |
hir::ExprKind::While(..) |

View File

@ -28,7 +28,7 @@ use smallvec::SmallVec;
fn compute_ignored_attr_names() -> FxHashSet<Symbol> {
debug_assert!(ich::IGNORED_ATTRIBUTES.len() > 0);
ich::IGNORED_ATTRIBUTES.iter().map(|&s| Symbol::intern(s)).collect()
ich::IGNORED_ATTRIBUTES.iter().map(|&s| s).collect()
}
/// This is the context state available during incr. comp. hashing. It contains

View File

@ -162,7 +162,13 @@ impl_stable_hash_for!(enum ::syntax::ast::LitIntType {
Unsuffixed
});
impl_stable_hash_for_spanned!(::syntax::ast::LitKind);
impl_stable_hash_for!(struct ::syntax::ast::Lit {
node,
token,
suffix,
span
});
impl_stable_hash_for!(enum ::syntax::ast::LitKind {
Str(value, style),
Err(value),
@ -175,6 +181,8 @@ impl_stable_hash_for!(enum ::syntax::ast::LitKind {
Bool(value)
});
impl_stable_hash_for_spanned!(::syntax::ast::LitKind);
impl_stable_hash_for!(enum ::syntax::ast::IntTy { Isize, I8, I16, I32, I64, I128 });
impl_stable_hash_for!(enum ::syntax::ast::UintTy { Usize, U8, U16, U32, U64, U128 });
impl_stable_hash_for!(enum ::syntax::ast::FloatTy { F32, F64 });
@ -280,6 +288,19 @@ for tokenstream::TokenStream {
}
}
impl_stable_hash_for!(enum token::Lit {
Bool(val),
Byte(val),
Char(val),
Err(val),
Integer(val),
Float(val),
Str_(val),
ByteStr(val),
StrRaw(val, n),
ByteStrRaw(val, n)
});
fn hash_token<'a, 'gcx, W: StableHasherResult>(
token: &token::Token,
hcx: &mut StableHashingContext<'a>,
@ -327,22 +348,8 @@ fn hash_token<'a, 'gcx, W: StableHasherResult>(
token::Token::CloseDelim(delim_token) => {
std_hash::Hash::hash(&delim_token, hasher);
}
token::Token::Literal(ref lit, ref opt_name) => {
mem::discriminant(lit).hash_stable(hcx, hasher);
match *lit {
token::Lit::Byte(val) |
token::Lit::Char(val) |
token::Lit::Err(val) |
token::Lit::Integer(val) |
token::Lit::Float(val) |
token::Lit::Str_(val) |
token::Lit::ByteStr(val) => val.hash_stable(hcx, hasher),
token::Lit::StrRaw(val, n) |
token::Lit::ByteStrRaw(val, n) => {
val.hash_stable(hcx, hasher);
n.hash_stable(hcx, hasher);
}
};
token::Token::Literal(lit, opt_name) => {
lit.hash_stable(hcx, hasher);
opt_name.hash_stable(hcx, hasher);
}
@ -395,6 +402,7 @@ impl_stable_hash_for!(enum ::syntax_pos::hygiene::ExpnFormat {
});
impl_stable_hash_for!(enum ::syntax_pos::hygiene::CompilerDesugaringKind {
IfTemporary,
Async,
Await,
QuestionMark,

View File

@ -4,6 +4,8 @@ crate use rustc_data_structures::fingerprint::Fingerprint;
pub use self::caching_source_map_view::CachingSourceMapView;
pub use self::hcx::{StableHashingContextProvider, StableHashingContext, NodeIdHashingMode,
hash_stable_trait_impls};
use syntax::symbol::{Symbol, sym};
mod caching_source_map_view;
mod hcx;
@ -12,16 +14,16 @@ mod impls_misc;
mod impls_ty;
mod impls_syntax;
pub const ATTR_DIRTY: &str = "rustc_dirty";
pub const ATTR_CLEAN: &str = "rustc_clean";
pub const ATTR_IF_THIS_CHANGED: &str = "rustc_if_this_changed";
pub const ATTR_THEN_THIS_WOULD_NEED: &str = "rustc_then_this_would_need";
pub const ATTR_PARTITION_REUSED: &str = "rustc_partition_reused";
pub const ATTR_PARTITION_CODEGENED: &str = "rustc_partition_codegened";
pub const ATTR_EXPECTED_CGU_REUSE: &str = "rustc_expected_cgu_reuse";
pub const ATTR_DIRTY: Symbol = sym::rustc_dirty;
pub const ATTR_CLEAN: Symbol = sym::rustc_clean;
pub const ATTR_IF_THIS_CHANGED: Symbol = sym::rustc_if_this_changed;
pub const ATTR_THEN_THIS_WOULD_NEED: Symbol = sym::rustc_then_this_would_need;
pub const ATTR_PARTITION_REUSED: Symbol = sym::rustc_partition_reused;
pub const ATTR_PARTITION_CODEGENED: Symbol = sym::rustc_partition_codegened;
pub const ATTR_EXPECTED_CGU_REUSE: Symbol = sym::rustc_expected_cgu_reuse;
pub const IGNORED_ATTRIBUTES: &[&str] = &[
"cfg",
pub const IGNORED_ATTRIBUTES: &[Symbol] = &[
sym::cfg,
ATTR_IF_THIS_CHANGED,
ATTR_THEN_THIS_WOULD_NEED,
ATTR_DIRTY,

View File

@ -194,20 +194,20 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
let mut sp = cm.def_span(self.hir().span_by_hir_id(node));
if let Some(param) = self.hir()
.get_generics(scope)
.and_then(|generics| generics.get_named(&br.name))
.and_then(|generics| generics.get_named(br.name))
{
sp = param.span;
}
(format!("the lifetime {} as defined on", br.name), sp)
}
ty::ReFree(ty::FreeRegion {
bound_region: ty::BoundRegion::BrNamed(_, ref name),
bound_region: ty::BoundRegion::BrNamed(_, name),
..
}) => {
let mut sp = cm.def_span(self.hir().span_by_hir_id(node));
if let Some(param) = self.hir()
.get_generics(scope)
.and_then(|generics| generics.get_named(&name))
.and_then(|generics| generics.get_named(name))
{
sp = param.span;
}

View File

@ -43,7 +43,7 @@ impl<'a, 'gcx, 'tcx> NiceRegionError<'a, 'gcx, 'tcx> {
) -> Option<AnonymousArgInfo<'_>> {
let (id, bound_region) = match *anon_region {
ty::ReFree(ref free_region) => (free_region.scope, free_region.bound_region),
ty::ReEarlyBound(ref ebr) => (
ty::ReEarlyBound(ebr) => (
self.tcx().parent(ebr.def_id).unwrap(),
ty::BoundRegion::BrNamed(ebr.def_id, ebr.name),
),

View File

@ -56,7 +56,7 @@ pub fn maybe_print_constraints_for<'a, 'gcx, 'tcx>(
}
let requested_node = env::var("RUST_REGION_GRAPH_NODE")
.ok().and_then(|s| s.parse().map(DefIndex::from_raw_u32).ok());
.ok().and_then(|s| s.parse().map(DefIndex::from_u32).ok());
if requested_node.is_some() && requested_node != Some(context.index) {
return;
@ -90,7 +90,7 @@ pub fn maybe_print_constraints_for<'a, 'gcx, 'tcx>(
let mut new_str = String::new();
for c in output_template.chars() {
if c == '%' {
new_str.push_str(&context.index.as_raw_u32().to_string());
new_str.push_str(&context.index.as_u32().to_string());
} else {
new_str.push(c);
}

View File

@ -284,18 +284,40 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
debug!("constrain_opaque_type: def_id={:?}", def_id);
debug!("constrain_opaque_type: opaque_defn={:#?}", opaque_defn);
let tcx = self.tcx;
let concrete_ty = self.resolve_type_vars_if_possible(&opaque_defn.concrete_ty);
debug!("constrain_opaque_type: concrete_ty={:?}", concrete_ty);
let abstract_type_generics = self.tcx.generics_of(def_id);
let abstract_type_generics = tcx.generics_of(def_id);
let span = self.tcx.def_span(def_id);
let span = tcx.def_span(def_id);
// If there are required region bounds, we can just skip
// ahead. There will already be a registered region
// obligation related `concrete_ty` to those regions.
// If there are required region bounds, we can use them.
if opaque_defn.has_required_region_bounds {
let predicates_of = tcx.predicates_of(def_id);
debug!(
"constrain_opaque_type: predicates: {:#?}",
predicates_of,
);
let bounds = predicates_of.instantiate(tcx, opaque_defn.substs);
debug!("constrain_opaque_type: bounds={:#?}", bounds);
let opaque_type = tcx.mk_opaque(def_id, opaque_defn.substs);
let required_region_bounds = tcx.required_region_bounds(
opaque_type,
bounds.predicates.clone(),
);
debug_assert!(!required_region_bounds.is_empty());
for region in required_region_bounds {
concrete_ty.visit_with(&mut OpaqueTypeOutlivesVisitor {
infcx: self,
least_region: region,
span,
});
}
return;
}
@ -371,7 +393,7 @@ impl<'a, 'gcx, 'tcx> InferCtxt<'a, 'gcx, 'tcx> {
}
}
let least_region = least_region.unwrap_or(self.tcx.lifetimes.re_static);
let least_region = least_region.unwrap_or(tcx.lifetimes.re_static);
debug!("constrain_opaque_types: least_region={:?}", least_region);
concrete_ty.visit_with(&mut OpaqueTypeOutlivesVisitor {
@ -589,10 +611,7 @@ impl<'cx, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for ReverseMapper<'cx, 'gcx, 'tcx>
ty::ReLateBound(..) |
// ignore `'static`, as that can appear anywhere
ty::ReStatic |
// ignore `ReScope`, which may appear in impl Trait in bindings.
ty::ReScope(..) => return r,
ty::ReStatic => return r,
_ => { }
}
@ -683,6 +702,23 @@ impl<'cx, 'gcx, 'tcx> TypeFolder<'gcx, 'tcx> for ReverseMapper<'cx, 'gcx, 'tcx>
self.tcx.mk_closure(def_id, ty::ClosureSubsts { substs })
}
ty::Generator(def_id, substs, movability) => {
let generics = self.tcx.generics_of(def_id);
let substs = self.tcx.mk_substs(substs.substs.iter().enumerate().map(
|(index, &kind)| {
if index < generics.parent_count {
// Accommodate missing regions in the parent kinds...
self.fold_kind_mapping_missing_regions_to_empty(kind)
} else {
// ...but not elsewhere.
self.fold_kind_normally(kind)
}
},
));
self.tcx.mk_generator(def_id, ty::GeneratorSubsts { substs }, movability)
}
_ => ty.super_fold_with(self),
}
}

View File

@ -198,12 +198,6 @@ declare_lint! {
"detects generic lifetime arguments in path segments with late bound lifetime parameters"
}
declare_lint! {
pub INCOHERENT_FUNDAMENTAL_IMPLS,
Deny,
"potentially-conflicting impls were erroneously allowed"
}
declare_lint! {
pub ORDER_DEPENDENT_TRAIT_OBJECTS,
Deny,
@ -428,7 +422,6 @@ declare_lint_pass! {
MISSING_FRAGMENT_SPECIFIER,
PARENTHESIZED_PARAMS_IN_TYPES_AND_MODULES,
LATE_BOUND_LIFETIME_ARGUMENTS,
INCOHERENT_FUNDAMENTAL_IMPLS,
ORDER_DEPENDENT_TRAIT_OBJECTS,
DEPRECATED,
UNUSED_UNSAFE,

View File

@ -828,8 +828,8 @@ impl<'a, 'tcx> LateContext<'a, 'tcx> {
// This shouldn't ever be needed, but just in case:
Ok(vec![match trait_ref {
Some(trait_ref) => Symbol::intern(&format!("{:?}", trait_ref)).as_str(),
None => Symbol::intern(&format!("<{}>", self_ty)).as_str(),
Some(trait_ref) => LocalInternedString::intern(&format!("{:?}", trait_ref)),
None => LocalInternedString::intern(&format!("<{}>", self_ty)),
}])
}
@ -845,9 +845,10 @@ impl<'a, 'tcx> LateContext<'a, 'tcx> {
// This shouldn't ever be needed, but just in case:
path.push(match trait_ref {
Some(trait_ref) => {
Symbol::intern(&format!("<impl {} for {}>", trait_ref, self_ty)).as_str()
LocalInternedString::intern(&format!("<impl {} for {}>", trait_ref,
self_ty))
},
None => Symbol::intern(&format!("<impl {}>", self_ty)).as_str(),
None => LocalInternedString::intern(&format!("<impl {}>", self_ty)),
});
Ok(path)

View File

@ -14,7 +14,7 @@ use syntax::ast;
use syntax::attr;
use syntax::feature_gate;
use syntax::source_map::MultiSpan;
use syntax::symbol::Symbol;
use syntax::symbol::{Symbol, sym};
pub struct LintLevelSets {
list: Vec<LintSet>,
@ -194,7 +194,7 @@ impl<'a> LintLevelsBuilder<'a> {
struct_span_err!(sess, span, E0452, "malformed lint attribute")
};
for attr in attrs {
let level = match Level::from_str(&attr.name_or_empty()) {
let level = match Level::from_symbol(attr.name_or_empty()) {
None => continue,
Some(lvl) => lvl,
};
@ -221,7 +221,7 @@ impl<'a> LintLevelsBuilder<'a> {
match item.node {
ast::MetaItemKind::Word => {} // actual lint names handled later
ast::MetaItemKind::NameValue(ref name_value) => {
if item.path == "reason" {
if item.path == sym::reason {
// found reason, reslice meta list to exclude it
metas = &metas[0..metas.len()-1];
// FIXME (#55112): issue unused-attributes lint if we thereby
@ -230,7 +230,7 @@ impl<'a> LintLevelsBuilder<'a> {
if !self.sess.features_untracked().lint_reasons {
feature_gate::emit_feature_err(
&self.sess.parse_sess,
"lint_reasons",
sym::lint_reasons,
item.span,
feature_gate::GateIssue::Language,
"lint reasons are experimental"
@ -261,7 +261,7 @@ impl<'a> LintLevelsBuilder<'a> {
let mut err = bad_attr(li.span());
if let Some(item) = li.meta_item() {
if let ast::MetaItemKind::NameValue(_) = item.node {
if item.path == "reason" {
if item.path == sym::reason {
err.help("reason in lint attribute must come last");
}
}

View File

@ -38,7 +38,7 @@ use syntax::ast;
use syntax::source_map::{MultiSpan, ExpnFormat};
use syntax::early_buffered_lints::BufferedEarlyLintId;
use syntax::edition::Edition;
use syntax::symbol::Symbol;
use syntax::symbol::{Symbol, sym};
use syntax_pos::Span;
pub use crate::lint::context::{LateContext, EarlyContext, LintContext, LintStore,
@ -570,6 +570,17 @@ impl Level {
_ => None,
}
}
/// Converts a symbol to a level.
pub fn from_symbol(x: Symbol) -> Option<Level> {
match x {
sym::allow => Some(Allow),
sym::warn => Some(Warn),
sym::deny => Some(Deny),
sym::forbid => Some(Forbid),
_ => None,
}
}
}
/// How a lint level was set.
@ -752,7 +763,7 @@ pub fn struct_lint_level<'a>(sess: &'a Session,
pub fn maybe_lint_level_root(tcx: TyCtxt<'_, '_, '_>, id: hir::HirId) -> bool {
let attrs = tcx.hir().attrs_by_hir_id(id);
attrs.iter().any(|attr| Level::from_str(&attr.name_or_empty()).is_some())
attrs.iter().any(|attr| Level::from_symbol(attr.name_or_empty()).is_some())
}
fn lint_levels<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, cnum: CrateNum)
@ -767,6 +778,9 @@ fn lint_levels<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, cnum: CrateNum)
let push = builder.levels.push(&krate.attrs);
builder.levels.register_id(hir::CRATE_HIR_ID);
for macro_def in &krate.exported_macros {
builder.levels.register_id(macro_def.hir_id);
}
intravisit::walk_crate(&mut builder, krate);
builder.levels.pop(push);

View File

@ -19,6 +19,7 @@ use rustc_data_structures::fx::FxHashMap;
use syntax::{ast, source_map};
use syntax::attr;
use syntax::symbol::sym;
use syntax_pos;
// Any local node that may call something in its body block should be
@ -304,22 +305,22 @@ impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
fn has_allow_dead_code_or_lang_attr(tcx: TyCtxt<'_, '_, '_>,
id: hir::HirId,
attrs: &[ast::Attribute]) -> bool {
if attr::contains_name(attrs, "lang") {
if attr::contains_name(attrs, sym::lang) {
return true;
}
// Stable attribute for #[lang = "panic_impl"]
if attr::contains_name(attrs, "panic_handler") {
if attr::contains_name(attrs, sym::panic_handler) {
return true;
}
// (To be) stable attribute for #[lang = "oom"]
if attr::contains_name(attrs, "alloc_error_handler") {
if attr::contains_name(attrs, sym::alloc_error_handler) {
return true;
}
// Don't lint about global allocators
if attr::contains_name(attrs, "global_allocator") {
if attr::contains_name(attrs, sym::global_allocator) {
return true;
}

View File

@ -4,6 +4,7 @@ use crate::session::{config, Session};
use crate::session::config::EntryFnType;
use syntax::attr;
use syntax::entry::EntryPointType;
use syntax::symbol::sym;
use syntax_pos::Span;
use crate::hir::{HirId, Item, ItemKind, ImplItem, TraitItem};
use crate::hir::itemlikevisit::ItemLikeVisitor;
@ -58,7 +59,7 @@ fn entry_fn(tcx: TyCtxt<'_, '_, '_>, cnum: CrateNum) -> Option<(DefId, EntryFnTy
}
// If the user wants no main function at all, then stop here.
if attr::contains_name(&tcx.hir().krate().attrs, "no_main") {
if attr::contains_name(&tcx.hir().krate().attrs, sym::no_main) {
return None;
}
@ -81,11 +82,11 @@ fn entry_fn(tcx: TyCtxt<'_, '_, '_>, cnum: CrateNum) -> Option<(DefId, EntryFnTy
fn entry_point_type(item: &Item, at_root: bool) -> EntryPointType {
match item.node {
ItemKind::Fn(..) => {
if attr::contains_name(&item.attrs, "start") {
if attr::contains_name(&item.attrs, sym::start) {
EntryPointType::Start
} else if attr::contains_name(&item.attrs, "main") {
} else if attr::contains_name(&item.attrs, sym::main) {
EntryPointType::MainAttr
} else if item.ident.name == "main" {
} else if item.ident.name == sym::main {
if at_root {
// This is a top-level function so can be 'main'.
EntryPointType::MainNamed

View File

@ -424,14 +424,6 @@ impl<'a, 'gcx, 'tcx> ExprUseVisitor<'a, 'gcx, 'tcx> {
self.consume_exprs(exprs);
}
hir::ExprKind::If(ref cond_expr, ref then_expr, ref opt_else_expr) => {
self.consume_expr(&cond_expr);
self.walk_expr(&then_expr);
if let Some(ref else_expr) = *opt_else_expr {
self.consume_expr(&else_expr);
}
}
hir::ExprKind::Match(ref discr, ref arms, _) => {
let discr_cmt = Rc::new(return_if_err!(self.mc.cat_expr(&discr)));
let r = self.tcx().lifetimes.re_empty;

View File

@ -18,7 +18,7 @@ use crate::middle::weak_lang_items;
use crate::util::nodemap::FxHashMap;
use syntax::ast;
use syntax::symbol::Symbol;
use syntax::symbol::{Symbol, sym};
use syntax_pos::Span;
use rustc_macros::HashStable;
use crate::hir::itemlikevisit::ItemLikeVisitor;
@ -209,9 +209,9 @@ impl<'a, 'tcx> LanguageItemCollector<'a, 'tcx> {
/// are also extracted out when found.
pub fn extract(attrs: &[ast::Attribute]) -> Option<(Symbol, Span)> {
attrs.iter().find_map(|attr| Some(match attr {
_ if attr.check_name("lang") => (attr.value_str()?, attr.span),
_ if attr.check_name("panic_handler") => (Symbol::intern("panic_impl"), attr.span),
_ if attr.check_name("alloc_error_handler") => (Symbol::intern("oom"), attr.span),
_ if attr.check_name(sym::lang) => (attr.value_str()?, attr.span),
_ if attr.check_name(sym::panic_handler) => (Symbol::intern("panic_impl"), attr.span),
_ if attr.check_name(sym::alloc_error_handler) => (Symbol::intern("oom"), attr.span),
_ => return None,
}))
}

View File

@ -8,7 +8,7 @@ use crate::ty::TyCtxt;
use crate::hir::intravisit::{self, NestedVisitorMap, Visitor};
use syntax::symbol::Symbol;
use syntax::ast::{Attribute, MetaItem, MetaItemKind};
use syntax_pos::{Span, symbols};
use syntax_pos::{Span, sym};
use rustc_data_structures::fx::{FxHashSet, FxHashMap};
use rustc_macros::HashStable;
use errors::DiagnosticId;
@ -51,7 +51,7 @@ impl<'a, 'tcx> LibFeatureCollector<'a, 'tcx> {
}
fn extract(&self, attr: &Attribute) -> Option<(Symbol, Option<Symbol>, Span)> {
let stab_attrs = [symbols::stable, symbols::unstable, symbols::rustc_const_unstable];
let stab_attrs = [sym::stable, sym::unstable, sym::rustc_const_unstable];
// Find a stability attribute (i.e., `#[stable (..)]`, `#[unstable (..)]`,
// `#[rustc_const_unstable (..)]`).
@ -65,9 +65,9 @@ impl<'a, 'tcx> LibFeatureCollector<'a, 'tcx> {
for meta in metas {
if let Some(mi) = meta.meta_item() {
// Find the `feature = ".."` meta-item.
match (mi.name_or_empty().get(), mi.value_str()) {
("feature", val) => feature = val,
("since", val) => since = val,
match (mi.name_or_empty(), mi.value_str()) {
(sym::feature, val) => feature = val,
(sym::since, val) => since = val,
_ => {}
}
}
@ -76,7 +76,7 @@ impl<'a, 'tcx> LibFeatureCollector<'a, 'tcx> {
// This additional check for stability is to make sure we
// don't emit additional, irrelevant errors for malformed
// attributes.
if *stab_attr != "stable" || since.is_some() {
if *stab_attr != sym::stable || since.is_some() {
return Some((feature, since, attr.span));
}
}

View File

@ -112,7 +112,7 @@ use std::io;
use std::rc::Rc;
use syntax::ast::{self, NodeId};
use syntax::ptr::P;
use syntax::symbol::keywords;
use syntax::symbol::{keywords, sym};
use syntax_pos::Span;
use crate::hir;
@ -362,7 +362,7 @@ fn visit_fn<'a, 'tcx: 'a>(ir: &mut IrMaps<'a, 'tcx>,
if let FnKind::Method(..) = fk {
let parent = ir.tcx.hir().get_parent_item(id);
if let Some(Node::Item(i)) = ir.tcx.hir().find_by_hir_id(parent) {
if i.attrs.iter().any(|a| a.check_name("automatically_derived")) {
if i.attrs.iter().any(|a| a.check_name(sym::automatically_derived)) {
return;
}
}
@ -500,7 +500,6 @@ fn visit_expr<'a, 'tcx>(ir: &mut IrMaps<'a, 'tcx>, expr: &'tcx Expr) {
}
// live nodes required for interesting control flow:
hir::ExprKind::If(..) |
hir::ExprKind::Match(..) |
hir::ExprKind::While(..) |
hir::ExprKind::Loop(..) => {
@ -1040,28 +1039,6 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
})
}
hir::ExprKind::If(ref cond, ref then, ref els) => {
//
// (cond)
// |
// v
// (expr)
// / \
// | |
// v v
// (then)(els)
// | |
// v v
// ( succ )
//
let else_ln = self.propagate_through_opt_expr(els.as_ref().map(|e| &**e), succ);
let then_ln = self.propagate_through_expr(&then, succ);
let ln = self.live_node(expr.hir_id, expr.span);
self.init_from_succ(ln, else_ln);
self.merge_from_succ(ln, then_ln, false);
self.propagate_through_expr(&cond, ln)
}
hir::ExprKind::While(ref cond, ref blk, _) => {
self.propagate_through_loop(expr, WhileLoop(&cond), &blk, succ)
}
@ -1523,7 +1500,7 @@ fn check_expr<'a, 'tcx>(this: &mut Liveness<'a, 'tcx>, expr: &'tcx Expr) {
}
// no correctness conditions related to liveness
hir::ExprKind::Call(..) | hir::ExprKind::MethodCall(..) | hir::ExprKind::If(..) |
hir::ExprKind::Call(..) | hir::ExprKind::MethodCall(..) |
hir::ExprKind::Match(..) | hir::ExprKind::While(..) | hir::ExprKind::Loop(..) |
hir::ExprKind::Index(..) | hir::ExprKind::Field(..) |
hir::ExprKind::Array(..) | hir::ExprKind::Tup(..) | hir::ExprKind::Binary(..) |

View File

@ -72,6 +72,7 @@ use crate::hir::{MutImmutable, MutMutable, PatKind};
use crate::hir::pat_util::EnumerateAndAdjustIterator;
use crate::hir;
use syntax::ast::{self, Name};
use syntax::symbol::sym;
use syntax_pos::Span;
use std::borrow::Cow;
@ -678,7 +679,7 @@ impl<'a, 'gcx, 'tcx> MemCategorizationContext<'a, 'gcx, 'tcx> {
hir::ExprKind::Closure(..) | hir::ExprKind::Ret(..) |
hir::ExprKind::Unary(..) | hir::ExprKind::Yield(..) |
hir::ExprKind::MethodCall(..) | hir::ExprKind::Cast(..) | hir::ExprKind::DropTemps(..) |
hir::ExprKind::Array(..) | hir::ExprKind::Tup(..) | hir::ExprKind::If(..) |
hir::ExprKind::Array(..) | hir::ExprKind::Tup(..) |
hir::ExprKind::Binary(..) | hir::ExprKind::While(..) |
hir::ExprKind::Block(..) | hir::ExprKind::Loop(..) | hir::ExprKind::Match(..) |
hir::ExprKind::Lit(..) | hir::ExprKind::Break(..) |
@ -714,7 +715,7 @@ impl<'a, 'gcx, 'tcx> MemCategorizationContext<'a, 'gcx, 'tcx> {
// they also cannot be moved out of.
let is_thread_local = self.tcx.get_attrs(def_id)[..]
.iter()
.any(|attr| attr.check_name("thread_local"));
.any(|attr| attr.check_name(sym::thread_local));
let cat = if is_thread_local {
let re = self.temporary_scope(hir_id.local_id);

View File

@ -7,15 +7,16 @@
use crate::session::Session;
use syntax::ast;
use syntax::symbol::{Symbol, sym};
use rustc_data_structures::sync::Once;
pub fn update_limits(sess: &Session, krate: &ast::Crate) {
update_limit(krate, &sess.recursion_limit, "recursion_limit", 64);
update_limit(krate, &sess.type_length_limit, "type_length_limit", 1048576);
update_limit(krate, &sess.recursion_limit, sym::recursion_limit, 64);
update_limit(krate, &sess.type_length_limit, sym::type_length_limit, 1048576);
}
fn update_limit(krate: &ast::Crate, limit: &Once<usize>, name: &str, default: usize) {
fn update_limit(krate: &ast::Crate, limit: &Once<usize>, name: Symbol, default: usize) {
for attr in &krate.attrs {
if !attr.check_name(name) {
continue;

View File

@ -158,7 +158,7 @@ newtype_index! {
impl_stable_hash_for!(struct crate::middle::region::FirstStatementIndex { private });
// compilation error if size of `ScopeData` is not the same as a `u32`
static_assert!(ASSERT_SCOPE_DATA: mem::size_of::<ScopeData>() == 4);
static_assert_size!(ScopeData, 4);
impl Scope {
/// Returns a item-local ID associated with this scope.
@ -884,17 +884,6 @@ fn resolve_expr<'a, 'tcx>(visitor: &mut RegionResolutionVisitor<'a, 'tcx>, expr:
terminating(r.hir_id.local_id);
}
hir::ExprKind::If(ref expr, ref then, Some(ref otherwise)) => {
terminating(expr.hir_id.local_id);
terminating(then.hir_id.local_id);
terminating(otherwise.hir_id.local_id);
}
hir::ExprKind::If(ref expr, ref then, None) => {
terminating(expr.hir_id.local_id);
terminating(then.hir_id.local_id);
}
hir::ExprKind::Loop(ref body, _, _) => {
terminating(body.hir_id.local_id);
}

View File

@ -23,7 +23,7 @@ use std::mem::replace;
use syntax::ast;
use syntax::attr;
use syntax::ptr::P;
use syntax::symbol::keywords;
use syntax::symbol::{keywords, sym};
use syntax_pos::Span;
use crate::hir::intravisit::{self, NestedVisitorMap, Visitor};
@ -1285,7 +1285,7 @@ fn compute_object_lifetime_defaults(
let result = object_lifetime_defaults_for_item(tcx, generics);
// Debugging aid.
if attr::contains_name(&item.attrs, "rustc_object_lifetime_default") {
if attr::contains_name(&item.attrs, sym::rustc_object_lifetime_default) {
let object_lifetime_default_reprs: String = result
.iter()
.map(|set| match *set {

View File

@ -11,7 +11,7 @@ use crate::hir::intravisit::{self, Visitor, NestedVisitorMap};
use crate::ty::query::Providers;
use crate::middle::privacy::AccessLevels;
use crate::session::{DiagnosticMessageId, Session};
use syntax::symbol::Symbol;
use syntax::symbol::{Symbol, sym};
use syntax_pos::{Span, MultiSpan};
use syntax::ast::Attribute;
use syntax::errors::Applicability;
@ -195,7 +195,7 @@ impl<'a, 'tcx: 'a> Annotator<'a, 'tcx> {
// Emit errors for non-staged-api crates.
for attr in attrs {
let name = attr.name_or_empty();
if ["unstable", "stable", "rustc_deprecated"].contains(&name.get()) {
if [sym::unstable, sym::stable, sym::rustc_deprecated].contains(&name) {
attr::mark_used(attr);
self.tcx.sess.span_err(attr.span, "stability attributes may not be used \
outside of the standard library");
@ -669,7 +669,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
match stability {
Some(&Stability { level: attr::Unstable { reason, issue }, feature, .. }) => {
if span.allows_unstable(&feature.as_str()) {
if span.allows_unstable(feature) {
debug!("stability: skipping span={:?} since it is internal", span);
return EvalResult::Allow;
}
@ -686,7 +686,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
// the `-Z force-unstable-if-unmarked` flag present (we're
// compiling a compiler crate), then let this missing feature
// annotation slide.
if feature == "rustc_private" && issue == 27812 {
if feature == sym::rustc_private && issue == 27812 {
if self.sess.opts.debugging_opts.force_unstable_if_unmarked {
return EvalResult::Allow;
}
@ -739,7 +739,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
let error_id = (DiagnosticMessageId::StabilityId(issue), span_key, msg.clone());
let fresh = self.sess.one_time_diagnostics.borrow_mut().insert(error_id);
if fresh {
emit_feature_err(&self.sess.parse_sess, &feature.as_str(), span,
emit_feature_err(&self.sess.parse_sess, feature, span,
GateIssue::Library(Some(issue)), &msg);
}
}
@ -802,13 +802,13 @@ impl<'a, 'tcx> Visitor<'tcx> for Checker<'a, 'tcx> {
if adt_def.has_dtor(self.tcx) {
emit_feature_err(&self.tcx.sess.parse_sess,
"untagged_unions", item.span, GateIssue::Language,
sym::untagged_unions, item.span, GateIssue::Language,
"unions with `Drop` implementations are unstable");
} else {
let param_env = self.tcx.param_env(def_id);
if !param_env.can_type_implement_copy(self.tcx, ty).is_ok() {
emit_feature_err(&self.tcx.sess.parse_sess,
"untagged_unions", item.span, GateIssue::Language,
sym::untagged_unions, item.span, GateIssue::Language,
"unions with non-`Copy` fields are unstable");
}
}

View File

@ -6,7 +6,7 @@ use crate::middle::lang_items;
use rustc_data_structures::fx::FxHashSet;
use rustc_target::spec::PanicStrategy;
use syntax::ast;
use syntax::symbol::Symbol;
use syntax::symbol::{Symbol, sym};
use syntax_pos::Span;
use crate::hir::def_id::DefId;
use crate::hir::intravisit::{Visitor, NestedVisitorMap};
@ -46,8 +46,8 @@ pub fn check_crate<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
pub fn link_name(attrs: &[ast::Attribute]) -> Option<Symbol> {
lang_items::extract(attrs).and_then(|(name, _)| {
$(if name == stringify!($name) {
Some(Symbol::intern(stringify!($sym)))
$(if name == sym::$name {
Some(sym::$sym)
} else)* {
None
}

View File

@ -78,7 +78,7 @@ pub struct Pointer<Tag=(),Id=AllocId> {
pub tag: Tag,
}
static_assert!(POINTER_SIZE: ::std::mem::size_of::<Pointer>() == 16);
static_assert_size!(Pointer, 16);
/// Produces a `Pointer` which points to the beginning of the Allocation
impl From<AllocId> for Pointer {

View File

@ -54,7 +54,7 @@ pub enum ConstValue<'tcx> {
}
#[cfg(target_arch = "x86_64")]
static_assert!(CONST_SIZE: ::std::mem::size_of::<ConstValue<'static>>() == 40);
static_assert_size!(ConstValue<'_>, 40);
impl<'tcx> ConstValue<'tcx> {
#[inline]
@ -111,7 +111,7 @@ pub enum Scalar<Tag=(), Id=AllocId> {
}
#[cfg(target_arch = "x86_64")]
static_assert!(SCALAR_SIZE: ::std::mem::size_of::<Scalar>() == 24);
static_assert_size!(Scalar, 24);
impl<Tag> fmt::Display for Scalar<Tag> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {

View File

@ -1738,7 +1738,7 @@ pub struct Statement<'tcx> {
// `Statement` is used a lot. Make sure it doesn't unintentionally get bigger.
#[cfg(target_arch = "x86_64")]
static_assert!(MEM_SIZE_OF_STATEMENT: mem::size_of::<Statement<'_>>() == 56);
static_assert_size!(Statement<'_>, 56);
impl<'tcx> Statement<'tcx> {
/// Changes a statement to a nop. This is both faster than deleting instructions and avoids
@ -1997,10 +1997,9 @@ pub type PlaceProjection<'tcx> = Projection<Place<'tcx>, Local, Ty<'tcx>>;
/// and the index is a local.
pub type PlaceElem<'tcx> = ProjectionElem<Local, Ty<'tcx>>;
// at least on 64 bit systems, `PlaceElem` should not be larger than two pointers
static_assert!(PROJECTION_ELEM_IS_2_PTRS_LARGE:
mem::size_of::<PlaceElem<'_>>() <= 16
);
// At least on 64 bit systems, `PlaceElem` should not be larger than two pointers.
#[cfg(target_arch = "x86_64")]
static_assert_size!(PlaceElem<'_>, 16);
/// Alias for projections as they appear in `UserTypeProjection`, where we
/// need neither the `V` parameter for `Index` nor the `T` for `Field`.

View File

@ -1,6 +1,6 @@
use crate::hir::def_id::{DefId, CrateNum, LOCAL_CRATE};
use crate::hir::HirId;
use syntax::symbol::{Symbol, InternedString};
use syntax::symbol::InternedString;
use crate::ty::{Instance, TyCtxt};
use crate::util::nodemap::FxHashMap;
use rustc_data_structures::base_n;
@ -280,7 +280,7 @@ impl<'a, 'gcx: 'tcx, 'tcx: 'a> CodegenUnitNameBuilder<'a, 'gcx, 'tcx> {
cgu_name
} else {
let cgu_name = &cgu_name.as_str()[..];
Symbol::intern(&CodegenUnit::mangle_name(cgu_name)).as_interned_str()
InternedString::intern(&CodegenUnit::mangle_name(cgu_name))
}
}
@ -336,6 +336,6 @@ impl<'a, 'gcx: 'tcx, 'tcx: 'a> CodegenUnitNameBuilder<'a, 'gcx, 'tcx> {
write!(cgu_name, ".{}", special_suffix).unwrap();
}
Symbol::intern(&cgu_name[..]).as_interned_str()
InternedString::intern(&cgu_name[..])
}
}

View File

@ -17,9 +17,9 @@ pub struct PlaceTy<'tcx> {
pub variant_index: Option<VariantIdx>,
}
static_assert!(PLACE_TY_IS_3_PTRS_LARGE:
mem::size_of::<PlaceTy<'_>>() <= 24
);
// At least on 64 bit systems, `PlaceTy` should not be larger than two or three pointers.
#[cfg(target_arch = "x86_64")]
static_assert_size!(PlaceTy<'_>, 16);
impl<'a, 'gcx, 'tcx> PlaceTy<'tcx> {
pub fn from_ty(ty: Ty<'tcx>) -> PlaceTy<'tcx> {

View File

@ -1052,7 +1052,7 @@ rustc_queries! {
}
Other {
query target_features_whitelist(_: CrateNum) -> Lrc<FxHashMap<String, Option<String>>> {
query target_features_whitelist(_: CrateNum) -> Lrc<FxHashMap<String, Option<Symbol>>> {
eval_always
desc { "looking up the whitelist of target features" }
}

View File

@ -1744,8 +1744,7 @@ pub fn rustc_short_optgroups() -> Vec<RustcOptGroup> {
opt::multi_s(
"",
"print",
"Comma separated list of compiler information to \
print on stdout",
"Compiler information to print on stdout",
"[crate-name|file-names|sysroot|cfg|target-list|\
target-cpus|target-features|relocation-models|\
code-models|tls-models|target-spec-json|native-static-libs]",
@ -2753,6 +2752,7 @@ mod tests {
// another --cfg test
#[test]
fn test_switch_implies_cfg_test_unless_cfg_test() {
use syntax::symbol::sym;
syntax::with_globals(|| {
let matches = &match optgroups().parse(&["--test".to_string(),
"--cfg=test".to_string()]) {
@ -2763,7 +2763,7 @@ mod tests {
let (sessopts, cfg) = build_session_options_and_crate_config(matches);
let sess = build_session(sessopts, None, registry);
let cfg = build_configuration(&sess, to_crate_config(cfg));
let mut test_items = cfg.iter().filter(|&&(name, _)| name == "test");
let mut test_items = cfg.iter().filter(|&&(name, _)| name == sym::test);
assert!(test_items.next().is_some());
assert!(test_items.next().is_none());
});

View File

@ -29,6 +29,7 @@ use syntax::feature_gate::{self, AttributeType};
use syntax::json::JsonEmitter;
use syntax::source_map;
use syntax::parse::{self, ParseSess};
use syntax::symbol::Symbol;
use syntax_pos::{MultiSpan, Span};
use crate::util::profiling::SelfProfiler;
@ -86,7 +87,7 @@ pub struct Session {
/// in order to avoid redundantly verbose output (Issue #24690, #44953).
pub one_time_diagnostics: Lock<FxHashSet<(DiagnosticMessageId, Option<Span>, String)>>,
pub plugin_llvm_passes: OneThread<RefCell<Vec<String>>>,
pub plugin_attributes: Lock<Vec<(String, AttributeType)>>,
pub plugin_attributes: Lock<Vec<(Symbol, AttributeType)>>,
pub crate_types: Once<Vec<config::CrateType>>,
pub dependency_formats: Once<dependency_format::Dependencies>,
/// The crate_disambiguator is constructed out of all the `-C metadata`

Some files were not shown because too many files have changed in this diff Show More