diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index e5054a075676..841bc39bf1e6 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -64,12 +64,18 @@ jobs: uses: Swatinem/rust-cache@9d47c6ad4b02e050fd481d890b2ea34778fd09d6 # v2.7.8 with: workspaces: src/ci/citool + - name: Test citool + # Only test citool on the auto branch, to reduce latency of the calculate matrix job + # on PR/try builds. + if: ${{ github.ref == 'refs/heads/auto' }} + run: | + cd src/ci/citool + CARGO_INCREMENTAL=0 cargo test - name: Calculate the CI job matrix env: COMMIT_MESSAGE: ${{ github.event.head_commit.message }} run: | cd src/ci/citool - CARGO_INCREMENTAL=0 cargo test CARGO_INCREMENTAL=0 cargo run calculate-job-matrix >> $GITHUB_OUTPUT id: jobs job: diff --git a/Cargo.lock b/Cargo.lock index 93abab8469a7..9c0978b92f73 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -80,9 +80,9 @@ dependencies = [ [[package]] name = "anstream" -version = "0.6.18" +version = "0.6.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8acc5369981196006228e28809f761875c0327210a891e941f4c683b3a99529b" +checksum = "301af1932e46185686725e0fad2f8f2aa7da69dd70bf6ecc44d6b703844a3933" dependencies = [ "anstyle", "anstyle-parse", @@ -95,58 +95,58 @@ dependencies = [ [[package]] name = "anstyle" -version = "1.0.10" +version = "1.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "55cc3b69f167a1ef2e161439aa98aed94e6028e5f9a59be9a6ffb47aef1651f9" +checksum = "862ed96ca487e809f1c8e5a8447f6ee2cf102f846893800b20cebdf541fc6bbd" [[package]] name = "anstyle-lossy" -version = "1.1.3" +version = "1.1.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "934ff8719effd2023a48cf63e69536c1c3ced9d3895068f6f5cc9a4ff845e59b" +checksum = "04d3a5dc826f84d0ea11882bb8054ff7f3d482602e11bb181101303a279ea01f" dependencies = [ "anstyle", ] [[package]] name = "anstyle-parse" -version = "0.2.6" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b2d16507662817a6a20a9ea92df6652ee4f94f914589377d69f3b21bc5798a9" +checksum = "4e7644824f0aa2c7b9384579234ef10eb7efb6a0deb83f9630a49594dd9c15c2" dependencies = [ "utf8parse", ] [[package]] name = "anstyle-query" -version = "1.1.2" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "79947af37f4177cfead1110013d678905c37501914fba0efea834c3fe9a8d60c" +checksum = "6c8bdeb6047d8983be085bab0ba1472e6dc604e7041dbf6fcd5e71523014fae9" dependencies = [ "windows-sys 0.59.0", ] [[package]] name = "anstyle-svg" -version = "0.1.7" +version = "0.1.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d3607949e9f6de49ea4bafe12f5e4fd73613ebf24795e48587302a8cc0e4bb35" +checksum = "c681338396641f4e32a29f045d0c70950da7207b4376685b51396c481ee36f1a" dependencies = [ - "anstream", "anstyle", "anstyle-lossy", + "anstyle-parse", "html-escape", "unicode-width 0.2.0", ] [[package]] name = "anstyle-wincon" -version = "3.0.7" +version = "3.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca3534e77181a9cc07539ad51f2141fe32f6c3ffd4df76db8ad92346b003ae4e" +checksum = "403f75924867bb1033c59fbf0797484329750cfbe3c4325cd33127941fabc882" dependencies = [ "anstyle", - "once_cell", + "once_cell_polyfill", "windows-sys 0.59.0", ] @@ -266,9 +266,9 @@ dependencies = [ [[package]] name = "bitflags" -version = "2.9.0" +version = "2.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c8214115b7bf84099f1309324e63141d4c5d7cc26862f97a0a857dbefe165bd" +checksum = "1b8e56985ec62d17e9c1001dc89c88ecd7dc08e47eba5ec7c29c7b5eeecde967" [[package]] name = "blake3" @@ -341,15 +341,15 @@ dependencies = [ [[package]] name = "bumpalo" -version = "3.17.0" +version = "3.18.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1628fb46dfa0b37568d12e5edd512553eccf6a22a78e8bde00bb4aed84d5bdbf" +checksum = "793db76d6187cd04dff33004d8e6c9cc4e05cd330500379d2394209271b4aeee" [[package]] name = "bytecount" -version = "0.6.8" +version = "0.6.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ce89b21cab1437276d2650d57e971f9d548a2d9037cc231abdc0562b97498ce" +checksum = "175812e0be2bccb6abe50bb8d566126198344f707e304f45c648fd8f2cc0365e" [[package]] name = "bytes" @@ -359,9 +359,9 @@ checksum = "d71b6127be86fdcfddb610f7182ac57211d4b18a3e9c82eb2d17662f2227ad6a" [[package]] name = "camino" -version = "1.1.9" +version = "1.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8b96ec4966b5813e2c0507c1f86115c8c5abaadc3980879c3424042a02fd1ad3" +checksum = "0da45bc31171d8d6960122e222a67740df867c1dd53b4d51caa297084c185cab" dependencies = [ "serde", ] @@ -487,9 +487,9 @@ dependencies = [ [[package]] name = "clap" -version = "4.5.38" +version = "4.5.39" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed93b9805f8ba930df42c2590f05453d5ec36cbb85d018868a5b24d31f6ac000" +checksum = "fd60e63e9be68e5fb56422e397cf9baddded06dae1d2e523401542383bc72a9f" dependencies = [ "clap_builder", "clap_derive", @@ -507,9 +507,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.5.38" +version = "4.5.39" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "379026ff283facf611b0ea629334361c4211d1b12ee01024eec1591133b04120" +checksum = "89cc6392a1f72bbeb820d71f32108f61fdaf18bc526e1d23954168a67759ef51" dependencies = [ "anstream", "anstyle", @@ -642,16 +642,16 @@ dependencies = [ [[package]] name = "color-eyre" -version = "0.6.4" +version = "0.6.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e6e1761c0e16f8883bbbb8ce5990867f4f06bf11a0253da6495a04ce4b6ef0ec" +checksum = "e5920befb47832a6d61ee3a3a846565cfa39b331331e68a3b1d1116630f2f26d" dependencies = [ "backtrace", "color-spantrace", "eyre", "indenter", "once_cell", - "owo-colors 4.2.0", + "owo-colors 4.2.1", "tracing-error", ] @@ -678,21 +678,21 @@ dependencies = [ [[package]] name = "color-spantrace" -version = "0.2.2" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2ddd8d5bfda1e11a501d0a7303f3bfed9aa632ebdb859be40d0fd70478ed70d5" +checksum = "b8b88ea9df13354b55bc7234ebcce36e6ef896aca2e42a15de9e10edce01b427" dependencies = [ "once_cell", - "owo-colors 4.2.0", + "owo-colors 4.2.1", "tracing-core", "tracing-error", ] [[package]] name = "colorchoice" -version = "1.0.3" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b63caa9aa9397e2d9480a9b13673856c78d8ac123288526c37d7839f2a86990" +checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75" [[package]] name = "colored" @@ -851,9 +851,9 @@ dependencies = [ [[package]] name = "curl" -version = "0.4.47" +version = "0.4.48" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9fb4d13a1be2b58f14d60adba57c9834b78c62fd86c3e76a148f732686e9265" +checksum = "9e2d5c8f48d9c0c23250e52b55e82a6ab4fdba6650c931f5a0a57a43abda812b" dependencies = [ "curl-sys", "libc", @@ -861,14 +861,14 @@ dependencies = [ "openssl-sys", "schannel", "socket2", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] name = "curl-sys" -version = "0.4.80+curl-8.12.1" +version = "0.4.82+curl-8.14.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "55f7df2eac63200c3ab25bde3b2268ef2ee56af3d238e76d61f01c3c49bff734" +checksum = "c4d63638b5ec65f1a4ae945287b3fd035be4554bbaf211901159c9a2a74fb5be" dependencies = [ "cc", "libc", @@ -876,7 +876,7 @@ dependencies = [ "openssl-sys", "pkg-config", "vcpkg", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -1142,9 +1142,9 @@ checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f" [[package]] name = "errno" -version = "0.3.11" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "976dd42dc7e85965fe702eb8164f21f450704bdde31faefd6471dba214cb594e" +checksum = "cea14ef9355e3beab063703aa9dab15afd25f0667c341310c1e5274bb1d0da18" dependencies = [ "libc", "windows-sys 0.59.0", @@ -1207,9 +1207,9 @@ dependencies = [ [[package]] name = "flate2" -version = "1.1.1" +version = "1.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ced92e76e966ca2fd84c8f7aa01a4aea65b0eb6648d72f7c8f3e2764a67fece" +checksum = "4a3d7db9596fecd151c5f638c0ee5d5bd487b6e0ea232e5dc96d5250f6f94b1d" dependencies = [ "crc32fast", "miniz_oxide", @@ -1487,9 +1487,9 @@ dependencies = [ [[package]] name = "hashbrown" -version = "0.15.3" +version = "0.15.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "84b26c544d002229e640969970a2e74021aadf6e2f96372b9c58eff97de08eb3" +checksum = "5971ac85611da7067dbfcabef3c70ebb5606018acd9e2a3903a0da507521e0d5" dependencies = [ "allocator-api2", "equivalent", @@ -1511,9 +1511,9 @@ checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" [[package]] name = "hermit-abi" -version = "0.3.9" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024" +checksum = "f154ce46856750ed433c8649605bf7ed2de3bc35fd9d2a9f30cddd873c80cb08" [[package]] name = "hex" @@ -1700,9 +1700,9 @@ checksum = "00210d6893afc98edb752b664b8890f0ef174c8adbb8d0be9710fa66fbbf72d3" [[package]] name = "icu_properties" -version = "2.0.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2549ca8c7241c82f59c80ba2a6f415d931c5b58d24fb8412caa1a1f02c49139a" +checksum = "016c619c1eeb94efb86809b015c58f479963de65bdb6253345c1a1276f22e32b" dependencies = [ "displaydoc", "icu_collections", @@ -1716,9 +1716,9 @@ dependencies = [ [[package]] name = "icu_properties_data" -version = "2.0.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8197e866e47b68f8f7d95249e172903bec06004b18b2937f1095d40a0c57de04" +checksum = "298459143998310acd25ffe6810ed544932242d3f07083eee1084d83a71bd632" [[package]] name = "icu_provider" @@ -1933,9 +1933,9 @@ checksum = "4a5f13b858c8d314ee3e8f639011f7ccefe71f97f96e50151fb991f267928e2c" [[package]] name = "jiff" -version = "0.2.13" +version = "0.2.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f02000660d30638906021176af16b17498bd0d12813dbfe7b276d8bc7f3c0806" +checksum = "a194df1107f33c79f4f93d02c80798520551949d59dfad22b6157048a88cca93" dependencies = [ "jiff-static", "log", @@ -1946,9 +1946,9 @@ dependencies = [ [[package]] name = "jiff-static" -version = "0.2.13" +version = "0.2.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3c30758ddd7188629c6713fc45d1188af4f44c90582311d0c8d8c9907f60c48" +checksum = "6c6e1db7ed32c6c71b759497fae34bf7933636f75a251b9e736555da426f6442" dependencies = [ "proc-macro2", "quote", @@ -2002,9 +2002,9 @@ dependencies = [ [[package]] name = "jsonpath-rust" -version = "1.0.1" +version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a37c2c87b8d16e788ce359660fead0ea5f4ed29ff400d55be74a4e01d1817d9" +checksum = "5b37465feaf9d41f74df7da98c6c1c31ca8ea06d11b5bf7869c8f1ccc51a793f" dependencies = [ "pest", "pest_derive", @@ -2080,9 +2080,9 @@ dependencies = [ [[package]] name = "libloading" -version = "0.8.7" +version = "0.8.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a793df0d7afeac54f95b471d3af7f0d4fb975699f972341a4b76988d49cdf0c" +checksum = "07033963ba89ebaf1584d767badaa2e8fcec21aedea6b8c0346d487d49c28667" dependencies = [ "cfg-if", "windows-targets 0.53.0", @@ -2170,9 +2170,9 @@ dependencies = [ [[package]] name = "lock_api" -version = "0.4.12" +version = "0.4.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17" +checksum = "96936507f153605bddfcda068dd804796c84324ed2510809e5b2a624c81da765" dependencies = [ "autocfg", "scopeguard", @@ -2463,9 +2463,9 @@ dependencies = [ [[package]] name = "num_cpus" -version = "1.16.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +checksum = "91df4bbde75afed763b708b7eee1e8e7651e02d97f6d5dd763e89367e957b23b" dependencies = [ "hermit-abi", "libc", @@ -2538,6 +2538,12 @@ version = "1.21.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "42f5e15c9953c5e4ccceeb2e7382a716482c34515315f7b03532b8b4e8393d2d" +[[package]] +name = "once_cell_polyfill" +version = "1.70.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4895175b425cb1f87721b59f0f286c2092bd4af812243672510e1ac53e2e0ad" + [[package]] name = "opener" version = "0.7.2" @@ -2558,9 +2564,9 @@ checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e" [[package]] name = "openssl-sys" -version = "0.9.108" +version = "0.9.109" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e145e1651e858e820e4860f7b9c5e169bc1d8ce1c86043be79fa7b7634821847" +checksum = "90096e2e47630d78b7d1c20952dc621f957103f8bc2c8359ec81290d75238571" dependencies = [ "cc", "libc", @@ -2611,9 +2617,9 @@ checksum = "c1b04fb49957986fdce4d6ee7a65027d55d4b6d2265e5848bbb507b58ccfdb6f" [[package]] name = "owo-colors" -version = "4.2.0" +version = "4.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1036865bb9422d3300cf723f657c2851d0e9ab12567854b1f4eba3d77decf564" +checksum = "26995317201fa17f3656c36716aed4a7c81743a9634ac4c99c0eeda495db0cec" [[package]] name = "pad" @@ -2637,9 +2643,9 @@ dependencies = [ [[package]] name = "parking_lot" -version = "0.12.3" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27" +checksum = "70d58bf43669b5795d1576d0641cfb6fbb2057bf629506267a92807158584a13" dependencies = [ "lock_api", "parking_lot_core", @@ -2647,9 +2653,9 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.9.10" +version = "0.9.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8" +checksum = "bc838d2a56b5b1a6c25f55575dfc605fabb63bb2365f6c2353ef9159aa69e4a5" dependencies = [ "cfg-if", "libc", @@ -2802,9 +2808,9 @@ dependencies = [ [[package]] name = "portable-atomic" -version = "1.11.0" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "350e9b48cbc6b0e028b0473b114454c6316e57336ee184ceab6e53f72c178b3e" +checksum = "f84267b20a16ea918e43c6a88433c2d54fa145c92a811b5b047ccbe153674483" [[package]] name = "portable-atomic-util" @@ -3228,9 +3234,9 @@ dependencies = [ [[package]] name = "rustc_apfloat" -version = "0.2.2+llvm-462a31f5a5ab" +version = "0.2.3+llvm-462a31f5a5ab" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "121e2195ff969977a4e2b5c9965ea867fce7e4cb5aee5b09dee698a7932d574f" +checksum = "486c2179b4796f65bfe2ee33679acf0927ac83ecf583ad6c91c3b4570911b9ad" dependencies = [ "bitflags", "smallvec", @@ -3787,6 +3793,7 @@ dependencies = [ "rustc_arena", "rustc_ast", "rustc_attr_data_structures", + "rustc_attr_parsing", "rustc_data_structures", "rustc_errors", "rustc_feature", @@ -4768,9 +4775,9 @@ dependencies = [ [[package]] name = "rustversion" -version = "1.0.20" +version = "1.0.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eded382c5f5f786b989652c49544c4877d9f015cc22e145a5ea8ea66c2921cd2" +checksum = "8a0d197bd2c9dc6e53b84da9556a69ba4cdfab8619eb41a8bd1cc2027a0f6b1d" [[package]] name = "ruzstd" @@ -4866,9 +4873,9 @@ dependencies = [ [[package]] name = "serde_spanned" -version = "0.6.8" +version = "0.6.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87607cb1398ed59d48732e575a4c28a7a8ebf2454b964fe3f224f2afc07909e1" +checksum = "bf41e0cfaf7226dca15e8197172c295a782857fcb97fad1808a166870dee75a3" dependencies = [ "serde", ] @@ -4933,15 +4940,15 @@ dependencies = [ [[package]] name = "smallvec" -version = "1.15.0" +version = "1.15.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8917285742e9f3e1683f0a9c4e6b57960b7314d0b08d30d1ecd426713ee2eee9" +checksum = "67b1b7a3b5fe4f1376887184045fcf45c69e92af734b7aaddc05fb777b6fbd03" [[package]] name = "socket2" -version = "0.5.9" +version = "0.5.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f5fd57c80058a56cf5c777ab8a126398ece8e442983605d280a44ce79d0edef" +checksum = "e22376abed350d73dd1cd119b57ffccad95b4e585a7cda43e286245ce23c0678" dependencies = [ "libc", "windows-sys 0.52.0", @@ -5111,9 +5118,9 @@ dependencies = [ [[package]] name = "sysinfo" -version = "0.35.0" +version = "0.35.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b897c8ea620e181c7955369a31be5f48d9a9121cb59fd33ecef9ff2a34323422" +checksum = "3c3ffa3e4ff2b324a57f7aeb3c349656c7b127c3c189520251a648102a92496e" dependencies = [ "libc", "objc2-core-foundation", @@ -5354,9 +5361,9 @@ checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" [[package]] name = "tokio" -version = "1.45.0" +version = "1.45.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2513ca694ef9ede0fb23fe71a4ee4107cb102b9dc1930f6d0fd77aae068ae165" +checksum = "75ef51a33ef1da925cea3e4eb122833cb377c61439ca401b770f54902b806779" dependencies = [ "backtrace", "bytes", @@ -5386,9 +5393,9 @@ dependencies = [ [[package]] name = "toml_datetime" -version = "0.6.9" +version = "0.6.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3da5db5a963e24bc68be8b17b6fa82814bb22ee8660f192bb182771d498f09a3" +checksum = "22cddaf88f4fbc13c51aebbf5f8eceb5c7c5a9da2ac40a13519eb5b0a0e8f11c" dependencies = [ "serde", ] @@ -5420,9 +5427,9 @@ dependencies = [ [[package]] name = "tracing-attributes" -version = "0.1.28" +version = "0.1.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "395ae124c09f9e6918a2310af6038fba074bcf474ac352496d5910dd59a2226d" +checksum = "1b1ffbcf9c6f6b99d386e7444eb608ba646ae452a36b39737deb9663b610f662" dependencies = [ "proc-macro2", "quote", @@ -5504,11 +5511,11 @@ dependencies = [ [[package]] name = "type-map" -version = "0.5.0" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "deb68604048ff8fa93347f02441e4487594adc20bb8a084f9e564d2b827a0a9f" +checksum = "cb30dbbd9036155e74adad6812e9898d03ec374946234fbcebd5dfc7b9187b90" dependencies = [ - "rustc-hash 1.1.0", + "rustc-hash 2.1.1", ] [[package]] @@ -5729,11 +5736,13 @@ checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821" [[package]] name = "uuid" -version = "1.16.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "458f7a779bf54acc9f347480ac654f68407d3aab21269a6e3c9f922acd9e2da9" +checksum = "3cf4199d1e5d15ddd86a694e4d0dffa9c323ce759fea589f00fef9d81cc1931d" dependencies = [ "getrandom 0.3.3", + "js-sys", + "wasm-bindgen", ] [[package]] @@ -5892,12 +5901,12 @@ dependencies = [ [[package]] name = "wasm-encoder" -version = "0.230.0" +version = "0.233.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d4349d0943718e6e434b51b9639e876293093dca4b96384fb136ab5bd5ce6660" +checksum = "9679ae3cf7cfa2ca3a327f7fab97f27f3294d402fd1a76ca8ab514e17973e4d3" dependencies = [ "leb128fmt", - "wasmparser 0.230.0", + "wasmparser 0.233.0", ] [[package]] @@ -5935,17 +5944,6 @@ dependencies = [ "serde", ] -[[package]] -name = "wasmparser" -version = "0.230.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "808198a69b5a0535583370a51d459baa14261dfab04800c4864ee9e1a14346ed" -dependencies = [ - "bitflags", - "indexmap", - "semver", -] - [[package]] name = "wasmparser" version = "0.232.0" @@ -5956,23 +5954,34 @@ dependencies = [ ] [[package]] -name = "wast" -version = "230.0.0" +name = "wasmparser" +version = "0.233.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b8edac03c5fa691551531533928443faf3dc61a44f814a235c7ec5d17b7b34f1" +checksum = "b51cb03afce7964bbfce46602d6cb358726f36430b6ba084ac6020d8ce5bc102" +dependencies = [ + "bitflags", + "indexmap", + "semver", +] + +[[package]] +name = "wast" +version = "233.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2eaf4099d8d0c922b83bf3c90663f5666f0769db9e525184284ebbbdb1dd2180" dependencies = [ "bumpalo", "leb128fmt", "memchr", "unicode-width 0.2.0", - "wasm-encoder 0.230.0", + "wasm-encoder 0.233.0", ] [[package]] name = "wat" -version = "1.230.0" +version = "1.233.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d77d62229e38db83eac32bacb5f61ebb952366ab0dae90cf2b3c07a65eea894" +checksum = "3d9bc80f5e4b25ea086ef41b91ccd244adde45d931c384d94a8ff64ab8bd7d87" dependencies = [ "wast", ] @@ -6033,13 +6042,13 @@ dependencies = [ [[package]] name = "windows-bindgen" -version = "0.61.0" +version = "0.61.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ac1c59c20569610dd9ed784d5f003fb493ec57b4cf39d974eb03a84bb7156c90" +checksum = "9b4e97b01190d32f268a2dfbd3f006f77840633746707fbe40bcee588108a231" dependencies = [ - "rayon", "serde", "serde_json", + "windows-threading", ] [[package]] @@ -6053,9 +6062,9 @@ dependencies = [ [[package]] name = "windows-core" -version = "0.61.0" +version = "0.61.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4763c1de310c86d75a878046489e2e5ba02c649d185f21c67d4cf8a56d098980" +checksum = "c0fdd3ddb90610c7638aa2b3a3ab2904fb9e5cdbecc643ddb3647212781c4ae3" dependencies = [ "windows-implement", "windows-interface", @@ -6066,12 +6075,13 @@ dependencies = [ [[package]] name = "windows-future" -version = "0.2.0" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a1d6bbefcb7b60acd19828e1bc965da6fcf18a7e39490c5f8be71e54a19ba32" +checksum = "fc6a41e98427b19fe4b73c550f060b59fa592d7d686537eebf9385621bfbad8e" dependencies = [ "windows-core", "windows-link", + "windows-threading", ] [[package]] @@ -6114,18 +6124,18 @@ dependencies = [ [[package]] name = "windows-result" -version = "0.3.2" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c64fd11a4fd95df68efcfee5f44a294fe71b8bc6a91993e2791938abcc712252" +checksum = "56f42bd332cc6c8eac5af113fc0c1fd6a8fd2aa08a0119358686e5160d0586c6" dependencies = [ "windows-link", ] [[package]] name = "windows-strings" -version = "0.4.0" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a2ba9642430ee452d5a7aa78d72907ebe8cfda358e8cb7918a2050581322f97" +checksum = "56e6c93f3a0c3b36176cb1327a4958a0353d5d166c2a35cb268ace15e91d3b57" dependencies = [ "windows-link", ] @@ -6204,6 +6214,15 @@ dependencies = [ "windows_x86_64_msvc 0.53.0", ] +[[package]] +name = "windows-threading" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b66463ad2e0ea3bbf808b7f1d371311c80e115c0b71d60efc142cafbcfb057a6" +dependencies = [ + "windows-link", +] + [[package]] name = "windows_aarch64_gnullvm" version = "0.48.5" diff --git a/bootstrap.example.toml b/bootstrap.example.toml index 1371fd6442f9..19cf360b0fb8 100644 --- a/bootstrap.example.toml +++ b/bootstrap.example.toml @@ -381,6 +381,15 @@ # "miri", "cargo-miri" # for dev/nightly channels #] +# Specify build configuration specific for some tool, such as enabled features. +# This option has no effect on which tools are enabled: refer to the `tools` option for that. +# +# For example, to build Miri with tracing support, use `tool.miri.features = ["tracing"]` +# +# The default value for the `features` array is `[]`. However, please note that other flags in +# `bootstrap.toml` might influence the features enabled for some tools. +#tool.TOOL_NAME.features = [FEATURE1, FEATURE2] + # Verbosity level: 0 == not verbose, 1 == verbose, 2 == very verbose, 3 == print environment variables on each rustc invocation #verbose = 0 diff --git a/compiler/rustc_abi/src/canon_abi.rs b/compiler/rustc_abi/src/canon_abi.rs index 03eeb645489c..7c020be67617 100644 --- a/compiler/rustc_abi/src/canon_abi.rs +++ b/compiler/rustc_abi/src/canon_abi.rs @@ -28,6 +28,9 @@ pub enum CanonAbi { Rust, RustCold, + /// An ABI that rustc does not know how to call or define. + Custom, + /// ABIs relevant to 32-bit Arm targets Arm(ArmCall), /// ABI relevant to GPUs: the entry point for a GPU kernel @@ -57,6 +60,7 @@ impl fmt::Display for CanonAbi { CanonAbi::C => ExternAbi::C { unwind: false }, CanonAbi::Rust => ExternAbi::Rust, CanonAbi::RustCold => ExternAbi::RustCold, + CanonAbi::Custom => ExternAbi::Custom, CanonAbi::Arm(arm_call) => match arm_call { ArmCall::Aapcs => ExternAbi::Aapcs { unwind: false }, ArmCall::CCmseNonSecureCall => ExternAbi::CCmseNonSecureCall, diff --git a/compiler/rustc_abi/src/extern_abi.rs b/compiler/rustc_abi/src/extern_abi.rs index 0bc1c8a09308..7457ae1f0334 100644 --- a/compiler/rustc_abi/src/extern_abi.rs +++ b/compiler/rustc_abi/src/extern_abi.rs @@ -40,6 +40,11 @@ pub enum ExternAbi { /// Even normally-compatible Rust types can become ABI-incompatible with this ABI! Unadjusted, + /// An ABI that rustc does not know how to call or define. Functions with this ABI can + /// only be created using `#[naked]` functions or `extern "custom"` blocks, and can only + /// be called from inline assembly. + Custom, + /// UEFI ABI, usually an alias of C, but sometimes an arch-specific alias /// and only valid on platforms that have a UEFI standard EfiApi, @@ -141,6 +146,7 @@ abi_impls! { AvrNonBlockingInterrupt =><= "avr-non-blocking-interrupt", Cdecl { unwind: false } =><= "cdecl", Cdecl { unwind: true } =><= "cdecl-unwind", + Custom =><= "custom", EfiApi =><= "efiapi", Fastcall { unwind: false } =><= "fastcall", Fastcall { unwind: true } =><= "fastcall-unwind", diff --git a/compiler/rustc_ast/src/ast.rs b/compiler/rustc_ast/src/ast.rs index cf40c3f7f6f8..6b51cbd7fbeb 100644 --- a/compiler/rustc_ast/src/ast.rs +++ b/compiler/rustc_ast/src/ast.rs @@ -97,12 +97,12 @@ pub struct Path { pub tokens: Option, } +// Succeeds if the path has a single segment that is arg-free and matches the given symbol. impl PartialEq for Path { #[inline] fn eq(&self, name: &Symbol) -> bool { if let [segment] = self.segments.as_ref() - && segment.args.is_none() - && segment.ident.name == *name + && segment == name { true } else { @@ -111,6 +111,15 @@ impl PartialEq for Path { } } +// Succeeds if the path has segments that are arg-free and match the given symbols. +impl PartialEq<&[Symbol]> for Path { + #[inline] + fn eq(&self, names: &&[Symbol]) -> bool { + self.segments.len() == names.len() + && self.segments.iter().zip(names.iter()).all(|(s1, s2)| s1 == s2) + } +} + impl HashStable for Path { fn hash_stable(&self, hcx: &mut CTX, hasher: &mut StableHasher) { self.segments.len().hash_stable(hcx, hasher); @@ -166,6 +175,14 @@ pub struct PathSegment { pub args: Option>, } +// Succeeds if the path segment is arg-free and matches the given symbol. +impl PartialEq for PathSegment { + #[inline] + fn eq(&self, name: &Symbol) -> bool { + self.args.is_none() && self.ident.name == *name + } +} + impl PathSegment { pub fn from_ident(ident: Ident) -> Self { PathSegment { ident, id: DUMMY_NODE_ID, args: None } @@ -1441,11 +1458,15 @@ impl Expr { } } - ExprKind::Break(..) - | ExprKind::Ret(..) - | ExprKind::Yield(..) - | ExprKind::Yeet(..) - | ExprKind::Become(..) => ExprPrecedence::Jump, + ExprKind::Break(_ /*label*/, value) + | ExprKind::Ret(value) + | ExprKind::Yield(YieldKind::Prefix(value)) + | ExprKind::Yeet(value) => match value { + Some(_) => ExprPrecedence::Jump, + None => ExprPrecedence::Unambiguous, + }, + + ExprKind::Become(_) => ExprPrecedence::Jump, // `Range` claims to have higher precedence than `Assign`, but `x .. x = x` fails to // parse, instead of parsing as `(x .. x) = x`. Giving `Range` a lower precedence @@ -1502,6 +1523,7 @@ impl Expr { | ExprKind::Underscore | ExprKind::UnsafeBinderCast(..) | ExprKind::While(..) + | ExprKind::Yield(YieldKind::Postfix(..)) | ExprKind::Err(_) | ExprKind::Dummy => ExprPrecedence::Unambiguous, } @@ -3520,6 +3542,38 @@ impl FnHeader { || matches!(constness, Const::Yes(_)) || !matches!(ext, Extern::None) } + + /// Return a span encompassing the header, or none if all options are default. + pub fn span(&self) -> Option { + fn append(a: &mut Option, b: Span) { + *a = match a { + None => Some(b), + Some(x) => Some(x.to(b)), + } + } + + let mut full_span = None; + + match self.safety { + Safety::Unsafe(span) | Safety::Safe(span) => append(&mut full_span, span), + Safety::Default => {} + }; + + if let Some(coroutine_kind) = self.coroutine_kind { + append(&mut full_span, coroutine_kind.span()); + } + + if let Const::Yes(span) = self.constness { + append(&mut full_span, span); + } + + match self.ext { + Extern::Implicit(span) | Extern::Explicit(_, span) => append(&mut full_span, span), + Extern::None => {} + } + + full_span + } } impl Default for FnHeader { diff --git a/compiler/rustc_ast/src/mut_visit.rs b/compiler/rustc_ast/src/mut_visit.rs index 77cbdde61a42..71a47dcfcba2 100644 --- a/compiler/rustc_ast/src/mut_visit.rs +++ b/compiler/rustc_ast/src/mut_visit.rs @@ -11,7 +11,7 @@ use std::ops::DerefMut; use std::panic; use rustc_data_structures::flat_map_in_place::FlatMapInPlace; -use rustc_data_structures::stack::ensure_sufficient_stack; +use rustc_span::source_map::Spanned; use rustc_span::{Ident, Span}; use smallvec::{Array, SmallVec, smallvec}; use thin_vec::ThinVec; @@ -19,7 +19,7 @@ use thin_vec::ThinVec; use crate::ast::*; use crate::ptr::P; use crate::tokenstream::*; -use crate::visit::{AssocCtxt, BoundKind, FnCtxt, try_visit, visit_opt, walk_list}; +use crate::visit::{AssocCtxt, BoundKind, FnCtxt, VisitorResult, try_visit, visit_opt, walk_list}; pub trait ExpectOne { fn expect_one(self, err: &'static str) -> A::Item; @@ -32,7 +32,22 @@ impl ExpectOne for SmallVec { } } -pub trait MutVisitor: Sized { +mod sealed { + use rustc_ast_ir::visit::VisitorResult; + + /// This is for compatibility with the regular `Visitor`. + pub trait MutVisitorResult { + type Result: VisitorResult; + } + + impl MutVisitorResult for T { + type Result = (); + } +} + +use sealed::MutVisitorResult; + +pub trait MutVisitor: Sized + MutVisitorResult { // Methods in this trait have one of three forms: // // fn visit_t(&mut self, t: &mut T); // common @@ -227,14 +242,6 @@ pub trait MutVisitor: Sized { walk_generic_args(self, p); } - fn visit_angle_bracketed_parameter_data(&mut self, p: &mut AngleBracketedArgs) { - walk_angle_bracketed_parameter_data(self, p); - } - - fn visit_parenthesized_parameter_data(&mut self, p: &mut ParenthesizedArgs) { - walk_parenthesized_parameter_data(self, p); - } - fn visit_local(&mut self, l: &mut Local) { walk_local(self, l); } @@ -303,10 +310,6 @@ pub trait MutVisitor: Sized { walk_flat_map_expr_field(self, f) } - fn visit_where_clause(&mut self, where_clause: &mut WhereClause) { - walk_where_clause(self, where_clause); - } - fn flat_map_where_predicate( &mut self, where_predicate: WherePredicate, @@ -385,19 +388,14 @@ generate_flat_map_visitor_fns! { visit_generic_params, GenericParam, flat_map_generic_param; visit_stmts, Stmt, flat_map_stmt; visit_exprs, P, filter_map_expr; + visit_expr_fields, ExprField, flat_map_expr_field; visit_pat_fields, PatField, flat_map_pat_field; visit_variants, Variant, flat_map_variant; visit_assoc_items, P, flat_map_assoc_item, ctxt: AssocCtxt; -} - -#[inline] -fn visit_vec(elems: &mut Vec, mut visit_elem: F) -where - F: FnMut(&mut T), -{ - for elem in elems { - visit_elem(elem); - } + visit_where_predicates, WherePredicate, flat_map_where_predicate; + visit_params, Param, flat_map_param; + visit_field_defs, FieldDef, flat_map_field_def; + visit_arms, Arm, flat_map_arm; } #[inline] @@ -410,40 +408,12 @@ where } } -#[inline] -fn visit_opt(opt: &mut Option, mut visit_elem: F) -where - F: FnMut(&mut T), -{ - if let Some(elem) = opt { - visit_elem(elem); - } -} - fn visit_attrs(vis: &mut T, attrs: &mut AttrVec) { for attr in attrs.iter_mut() { vis.visit_attribute(attr); } } -fn visit_attr_args(vis: &mut T, args: &mut AttrArgs) { - match args { - AttrArgs::Empty => {} - AttrArgs::Delimited(args) => visit_delim_args(vis, args), - AttrArgs::Eq { eq_span, expr } => { - vis.visit_expr(expr); - vis.visit_span(eq_span); - } - } -} - -fn visit_delim_args(vis: &mut T, args: &mut DelimArgs) { - let DelimArgs { dspan, delim: _, tokens: _ } = args; - let DelimSpan { open, close } = dspan; - vis.visit_span(open); - vis.visit_span(close); -} - pub fn walk_flat_map_pat_field( vis: &mut T, mut fp: PatField, @@ -461,40 +431,11 @@ fn visit_nested_use_tree( vis.visit_use_tree(nested_tree); } -pub fn walk_arm(vis: &mut T, arm: &mut Arm) { - let Arm { attrs, pat, guard, body, span, id, is_placeholder: _ } = arm; - vis.visit_id(id); - visit_attrs(vis, attrs); - vis.visit_pat(pat); - visit_opt(guard, |guard| vis.visit_expr(guard)); - visit_opt(body, |body| vis.visit_expr(body)); - vis.visit_span(span); -} - pub fn walk_flat_map_arm(vis: &mut T, mut arm: Arm) -> SmallVec<[Arm; 1]> { vis.visit_arm(&mut arm); smallvec![arm] } -fn walk_assoc_item_constraint( - vis: &mut T, - AssocItemConstraint { id, ident, gen_args, kind, span }: &mut AssocItemConstraint, -) { - vis.visit_id(id); - vis.visit_ident(ident); - if let Some(gen_args) = gen_args { - vis.visit_generic_args(gen_args); - } - match kind { - AssocItemConstraintKind::Equality { term } => match term { - Term::Ty(ty) => vis.visit_ty(ty), - Term::Const(c) => vis.visit_anon_const(c), - }, - AssocItemConstraintKind::Bound { bounds } => visit_bounds(vis, bounds, BoundKind::Bound), - } - vis.visit_span(span); -} - pub fn walk_flat_map_variant( vis: &mut T, mut variant: Variant, @@ -503,64 +444,6 @@ pub fn walk_flat_map_variant( smallvec![variant] } -fn walk_generic_args(vis: &mut T, generic_args: &mut GenericArgs) { - match generic_args { - GenericArgs::AngleBracketed(data) => vis.visit_angle_bracketed_parameter_data(data), - GenericArgs::Parenthesized(data) => vis.visit_parenthesized_parameter_data(data), - GenericArgs::ParenthesizedElided(span) => vis.visit_span(span), - } -} - -fn walk_generic_arg(vis: &mut T, arg: &mut GenericArg) { - match arg { - GenericArg::Lifetime(lt) => vis.visit_lifetime(lt), - GenericArg::Type(ty) => vis.visit_ty(ty), - GenericArg::Const(ct) => vis.visit_anon_const(ct), - } -} - -fn walk_angle_bracketed_parameter_data(vis: &mut T, data: &mut AngleBracketedArgs) { - let AngleBracketedArgs { args, span } = data; - visit_thin_vec(args, |arg| match arg { - AngleBracketedArg::Arg(arg) => vis.visit_generic_arg(arg), - AngleBracketedArg::Constraint(constraint) => vis.visit_assoc_item_constraint(constraint), - }); - vis.visit_span(span); -} - -fn walk_parenthesized_parameter_data(vis: &mut T, args: &mut ParenthesizedArgs) { - let ParenthesizedArgs { inputs, output, span, inputs_span } = args; - visit_thin_vec(inputs, |input| vis.visit_ty(input)); - vis.visit_fn_ret_ty(output); - vis.visit_span(span); - vis.visit_span(inputs_span); -} - -fn walk_attribute(vis: &mut T, attr: &mut Attribute) { - let Attribute { kind, id: _, style: _, span } = attr; - match kind { - AttrKind::Normal(normal) => { - let NormalAttr { item: AttrItem { unsafety: _, path, args, tokens: _ }, tokens: _ } = - &mut **normal; - vis.visit_path(path); - visit_attr_args(vis, args); - } - AttrKind::DocComment(_kind, _sym) => {} - } - vis.visit_span(span); -} - -fn walk_mac(vis: &mut T, mac: &mut MacCall) { - let MacCall { path, args } = mac; - vis.visit_path(path); - visit_delim_args(vis, args); -} - -fn walk_macro_def(vis: &mut T, macro_def: &mut MacroDef) { - let MacroDef { body, macro_rules: _ } = macro_def; - visit_delim_args(vis, body); -} - fn walk_meta_list_item(vis: &mut T, li: &mut MetaItemInner) { match li { MetaItemInner::MetaItem(mi) => vis.visit_meta_item(mi), @@ -578,138 +461,11 @@ fn walk_meta_item(vis: &mut T, mi: &mut MetaItem) { vis.visit_span(span); } -pub fn walk_param(vis: &mut T, param: &mut Param) { - let Param { attrs, id, pat, span, ty, is_placeholder: _ } = param; - vis.visit_id(id); - visit_attrs(vis, attrs); - vis.visit_pat(pat); - vis.visit_ty(ty); - vis.visit_span(span); -} - pub fn walk_flat_map_param(vis: &mut T, mut param: Param) -> SmallVec<[Param; 1]> { vis.visit_param(&mut param); smallvec![param] } -fn walk_closure_binder(vis: &mut T, binder: &mut ClosureBinder) { - match binder { - ClosureBinder::NotPresent => {} - ClosureBinder::For { span: _, generic_params } => { - generic_params.flat_map_in_place(|param| vis.flat_map_generic_param(param)); - } - } -} - -fn walk_fn(vis: &mut T, kind: FnKind<'_>) { - match kind { - FnKind::Fn( - _ctxt, - _vis, - Fn { - defaultness, - ident, - generics, - contract, - body, - sig: FnSig { header, decl, span }, - define_opaque, - }, - ) => { - // Visibility is visited as a part of the item. - visit_defaultness(vis, defaultness); - vis.visit_ident(ident); - vis.visit_fn_header(header); - vis.visit_generics(generics); - vis.visit_fn_decl(decl); - if let Some(contract) = contract { - vis.visit_contract(contract); - } - if let Some(body) = body { - vis.visit_block(body); - } - vis.visit_span(span); - - walk_define_opaques(vis, define_opaque); - } - FnKind::Closure(binder, coroutine_kind, decl, body) => { - vis.visit_closure_binder(binder); - coroutine_kind.as_mut().map(|coroutine_kind| vis.visit_coroutine_kind(coroutine_kind)); - vis.visit_fn_decl(decl); - vis.visit_expr(body); - } - } -} - -fn walk_contract(vis: &mut T, contract: &mut FnContract) { - let FnContract { requires, ensures } = contract; - if let Some(pred) = requires { - vis.visit_expr(pred); - } - if let Some(pred) = ensures { - vis.visit_expr(pred); - } -} - -fn walk_fn_decl(vis: &mut T, decl: &mut FnDecl) { - let FnDecl { inputs, output } = decl; - inputs.flat_map_in_place(|param| vis.flat_map_param(param)); - vis.visit_fn_ret_ty(output); -} - -fn walk_fn_ret_ty(vis: &mut T, fn_ret_ty: &mut FnRetTy) { - match fn_ret_ty { - FnRetTy::Default(span) => vis.visit_span(span), - FnRetTy::Ty(ty) => vis.visit_ty(ty), - } -} - -fn walk_param_bound(vis: &mut T, pb: &mut GenericBound) { - match pb { - GenericBound::Trait(trait_ref) => vis.visit_poly_trait_ref(trait_ref), - GenericBound::Outlives(lifetime) => walk_lifetime(vis, lifetime), - GenericBound::Use(args, span) => { - for arg in args { - vis.visit_precise_capturing_arg(arg); - } - vis.visit_span(span); - } - } -} - -fn walk_precise_capturing_arg(vis: &mut T, arg: &mut PreciseCapturingArg) { - match arg { - PreciseCapturingArg::Lifetime(lt) => { - vis.visit_lifetime(lt); - } - PreciseCapturingArg::Arg(path, id) => { - vis.visit_id(id); - vis.visit_path(path); - } - } -} - -pub fn walk_generic_param(vis: &mut T, param: &mut GenericParam) { - let GenericParam { id, ident, attrs, bounds, kind, colon_span, is_placeholder: _ } = param; - vis.visit_id(id); - visit_attrs(vis, attrs); - vis.visit_ident(ident); - visit_vec(bounds, |bound| vis.visit_param_bound(bound, BoundKind::Bound)); - match kind { - GenericParamKind::Lifetime => {} - GenericParamKind::Type { default } => { - visit_opt(default, |default| vis.visit_ty(default)); - } - GenericParamKind::Const { ty, kw_span: _, default } => { - vis.visit_ty(ty); - visit_opt(default, |default| vis.visit_anon_const(default)); - } - } - if let Some(colon_span) = colon_span { - vis.visit_span(colon_span); - } -} - pub fn walk_flat_map_generic_param( vis: &mut T, mut param: GenericParam, @@ -718,13 +474,6 @@ pub fn walk_flat_map_generic_param( smallvec![param] } -fn walk_generics(vis: &mut T, generics: &mut Generics) { - let Generics { params, where_clause, span } = generics; - params.flat_map_in_place(|param| vis.flat_map_generic_param(param)); - vis.visit_where_clause(where_clause); - vis.visit_span(span); -} - fn walk_ty_alias_where_clauses(vis: &mut T, tawcs: &mut TyAliasWhereClauses) { let TyAliasWhereClauses { before, after, split: _ } = tawcs; let TyAliasWhereClause { has_where_token: _, span: span_before } = before; @@ -733,70 +482,14 @@ fn walk_ty_alias_where_clauses(vis: &mut T, tawcs: &mut TyAliasWh vis.visit_span(span_after); } -fn walk_where_clause(vis: &mut T, wc: &mut WhereClause) { - let WhereClause { has_where_token: _, predicates, span } = wc; - predicates.flat_map_in_place(|predicate| vis.flat_map_where_predicate(predicate)); - vis.visit_span(span); -} - pub fn walk_flat_map_where_predicate( vis: &mut T, mut pred: WherePredicate, ) -> SmallVec<[WherePredicate; 1]> { - let WherePredicate { attrs, kind, id, span, is_placeholder: _ } = &mut pred; - vis.visit_id(id); - visit_attrs(vis, attrs); - vis.visit_where_predicate_kind(kind); - vis.visit_span(span); + walk_where_predicate(vis, &mut pred); smallvec![pred] } -pub fn walk_where_predicate_kind(vis: &mut T, kind: &mut WherePredicateKind) { - match kind { - WherePredicateKind::BoundPredicate(bp) => { - let WhereBoundPredicate { bound_generic_params, bounded_ty, bounds } = bp; - bound_generic_params.flat_map_in_place(|param| vis.flat_map_generic_param(param)); - vis.visit_ty(bounded_ty); - visit_vec(bounds, |bound| vis.visit_param_bound(bound, BoundKind::Bound)); - } - WherePredicateKind::RegionPredicate(rp) => { - let WhereRegionPredicate { lifetime, bounds } = rp; - vis.visit_lifetime(lifetime); - visit_vec(bounds, |bound| vis.visit_param_bound(bound, BoundKind::Bound)); - } - WherePredicateKind::EqPredicate(ep) => { - let WhereEqPredicate { lhs_ty, rhs_ty } = ep; - vis.visit_ty(lhs_ty); - vis.visit_ty(rhs_ty); - } - } -} - -fn walk_variant_data(vis: &mut T, vdata: &mut VariantData) { - match vdata { - VariantData::Struct { fields, recovered: _ } => { - fields.flat_map_in_place(|field| vis.flat_map_field_def(field)); - } - VariantData::Tuple(fields, id) => { - vis.visit_id(id); - fields.flat_map_in_place(|field| vis.flat_map_field_def(field)); - } - VariantData::Unit(id) => vis.visit_id(id), - } -} - -pub fn walk_field_def(visitor: &mut T, fd: &mut FieldDef) { - let FieldDef { span, ident, vis, id, ty, attrs, is_placeholder: _, safety, default } = fd; - visitor.visit_id(id); - visit_attrs(visitor, attrs); - visitor.visit_vis(vis); - visit_safety(visitor, safety); - visit_opt(ident, |ident| visitor.visit_ident(ident)); - visitor.visit_ty(ty); - visit_opt(default, |default| visitor.visit_anon_const(default)); - visitor.visit_span(span); -} - pub fn walk_flat_map_field_def( vis: &mut T, mut fd: FieldDef, @@ -846,255 +539,6 @@ pub fn walk_flat_map_assoc_item( smallvec![item] } -fn walk_inline_asm(vis: &mut T, asm: &mut InlineAsm) { - // FIXME: Visit spans inside all this currently ignored stuff. - let InlineAsm { - asm_macro: _, - template: _, - template_strs: _, - operands, - clobber_abis: _, - options: _, - line_spans: _, - } = asm; - for (op, span) in operands { - match op { - InlineAsmOperand::In { expr, reg: _ } - | InlineAsmOperand::Out { expr: Some(expr), reg: _, late: _ } - | InlineAsmOperand::InOut { expr, reg: _, late: _ } => vis.visit_expr(expr), - InlineAsmOperand::Out { expr: None, reg: _, late: _ } => {} - InlineAsmOperand::SplitInOut { in_expr, out_expr, reg: _, late: _ } => { - vis.visit_expr(in_expr); - if let Some(out_expr) = out_expr { - vis.visit_expr(out_expr); - } - } - InlineAsmOperand::Const { anon_const } => vis.visit_anon_const(anon_const), - InlineAsmOperand::Sym { sym } => vis.visit_inline_asm_sym(sym), - InlineAsmOperand::Label { block } => vis.visit_block(block), - } - vis.visit_span(span); - } -} - -fn walk_inline_asm_sym( - vis: &mut T, - InlineAsmSym { id, qself, path }: &mut InlineAsmSym, -) { - vis.visit_id(id); - vis.visit_qself(qself); - vis.visit_path(path); -} - -fn walk_format_args(vis: &mut T, fmt: &mut FormatArgs) { - // FIXME: visit the template exhaustively. - let FormatArgs { span, template: _, arguments, uncooked_fmt_str: _ } = fmt; - for FormatArgument { kind, expr } in arguments.all_args_mut() { - match kind { - FormatArgumentKind::Named(ident) | FormatArgumentKind::Captured(ident) => { - vis.visit_ident(ident) - } - FormatArgumentKind::Normal => {} - } - vis.visit_expr(expr); - } - vis.visit_span(span); -} - -pub fn walk_expr(vis: &mut T, Expr { kind, id, span, attrs, tokens: _ }: &mut Expr) { - vis.visit_id(id); - visit_attrs(vis, attrs); - match kind { - ExprKind::Array(exprs) => visit_exprs(vis, exprs), - ExprKind::ConstBlock(anon_const) => { - vis.visit_anon_const(anon_const); - } - ExprKind::Repeat(expr, count) => { - vis.visit_expr(expr); - vis.visit_anon_const(count); - } - ExprKind::Tup(exprs) => visit_exprs(vis, exprs), - ExprKind::Call(f, args) => { - vis.visit_expr(f); - visit_exprs(vis, args); - } - ExprKind::MethodCall(box MethodCall { - seg: PathSegment { ident, id, args: seg_args }, - receiver, - args: call_args, - span, - }) => { - vis.visit_method_receiver_expr(receiver); - vis.visit_id(id); - vis.visit_ident(ident); - visit_opt(seg_args, |args| vis.visit_generic_args(args)); - visit_exprs(vis, call_args); - vis.visit_span(span); - } - ExprKind::Binary(binop, lhs, rhs) => { - vis.visit_expr(lhs); - vis.visit_expr(rhs); - vis.visit_span(&mut binop.span); - } - ExprKind::Unary(_unop, ohs) => vis.visit_expr(ohs), - ExprKind::Cast(expr, ty) => { - vis.visit_expr(expr); - vis.visit_ty(ty); - } - ExprKind::Type(expr, ty) => { - vis.visit_expr(expr); - vis.visit_ty(ty); - } - ExprKind::AddrOf(_kind, _mut, ohs) => vis.visit_expr(ohs), - ExprKind::Let(pat, scrutinee, span, _recovered) => { - vis.visit_pat(pat); - vis.visit_expr(scrutinee); - vis.visit_span(span); - } - ExprKind::If(cond, tr, fl) => { - vis.visit_expr(cond); - vis.visit_block(tr); - visit_opt(fl, |fl| ensure_sufficient_stack(|| vis.visit_expr(fl))); - } - ExprKind::While(cond, body, label) => { - visit_opt(label, |label| vis.visit_label(label)); - vis.visit_expr(cond); - vis.visit_block(body); - } - ExprKind::ForLoop { pat, iter, body, label, kind: _ } => { - visit_opt(label, |label| vis.visit_label(label)); - vis.visit_pat(pat); - vis.visit_expr(iter); - vis.visit_block(body); - } - ExprKind::Loop(body, label, span) => { - visit_opt(label, |label| vis.visit_label(label)); - vis.visit_block(body); - vis.visit_span(span); - } - ExprKind::Match(expr, arms, _kind) => { - vis.visit_expr(expr); - arms.flat_map_in_place(|arm| vis.flat_map_arm(arm)); - } - ExprKind::Closure(box Closure { - binder, - capture_clause, - constness, - coroutine_kind, - movability: _, - fn_decl, - body, - fn_decl_span, - fn_arg_span, - }) => { - visit_constness(vis, constness); - vis.visit_capture_by(capture_clause); - vis.visit_fn(FnKind::Closure(binder, coroutine_kind, fn_decl, body), *span, *id); - vis.visit_span(fn_decl_span); - vis.visit_span(fn_arg_span); - } - ExprKind::Block(blk, label) => { - visit_opt(label, |label| vis.visit_label(label)); - vis.visit_block(blk); - } - ExprKind::Gen(_capture_by, body, _kind, decl_span) => { - vis.visit_block(body); - vis.visit_span(decl_span); - } - ExprKind::Await(expr, await_kw_span) => { - vis.visit_expr(expr); - vis.visit_span(await_kw_span); - } - ExprKind::Use(expr, use_kw_span) => { - vis.visit_expr(expr); - vis.visit_span(use_kw_span); - } - ExprKind::Assign(el, er, span) => { - vis.visit_expr(el); - vis.visit_expr(er); - vis.visit_span(span); - } - ExprKind::AssignOp(_op, el, er) => { - vis.visit_expr(el); - vis.visit_expr(er); - } - ExprKind::Field(el, ident) => { - vis.visit_expr(el); - vis.visit_ident(ident); - } - ExprKind::Index(el, er, brackets_span) => { - vis.visit_expr(el); - vis.visit_expr(er); - vis.visit_span(brackets_span); - } - ExprKind::Range(e1, e2, _lim) => { - visit_opt(e1, |e1| vis.visit_expr(e1)); - visit_opt(e2, |e2| vis.visit_expr(e2)); - } - ExprKind::Underscore => {} - ExprKind::Path(qself, path) => { - vis.visit_qself(qself); - vis.visit_path(path); - } - ExprKind::Break(label, expr) => { - visit_opt(label, |label| vis.visit_label(label)); - visit_opt(expr, |expr| vis.visit_expr(expr)); - } - ExprKind::Continue(label) => { - visit_opt(label, |label| vis.visit_label(label)); - } - ExprKind::Ret(expr) => { - visit_opt(expr, |expr| vis.visit_expr(expr)); - } - ExprKind::Yeet(expr) => { - visit_opt(expr, |expr| vis.visit_expr(expr)); - } - ExprKind::Become(expr) => vis.visit_expr(expr), - ExprKind::InlineAsm(asm) => vis.visit_inline_asm(asm), - ExprKind::FormatArgs(fmt) => vis.visit_format_args(fmt), - ExprKind::OffsetOf(container, fields) => { - vis.visit_ty(container); - for field in fields.iter_mut() { - vis.visit_ident(field); - } - } - ExprKind::MacCall(mac) => vis.visit_mac_call(mac), - ExprKind::Struct(se) => { - let StructExpr { qself, path, fields, rest } = se.deref_mut(); - vis.visit_qself(qself); - vis.visit_path(path); - fields.flat_map_in_place(|field| vis.flat_map_expr_field(field)); - match rest { - StructRest::Base(expr) => vis.visit_expr(expr), - StructRest::Rest(_span) => {} - StructRest::None => {} - } - } - ExprKind::Paren(expr) => { - vis.visit_expr(expr); - } - ExprKind::Yield(kind) => { - let expr = kind.expr_mut(); - if let Some(expr) = expr { - vis.visit_expr(expr); - } - } - ExprKind::Try(expr) => vis.visit_expr(expr), - ExprKind::TryBlock(body) => vis.visit_block(body), - ExprKind::Lit(_token) => {} - ExprKind::IncludedBytes(_bytes) => {} - ExprKind::UnsafeBinderCast(_kind, expr, ty) => { - vis.visit_expr(expr); - if let Some(ty) = ty { - vis.visit_ty(ty); - } - } - ExprKind::Err(_guar) => {} - ExprKind::Dummy => {} - } - vis.visit_span(span); -} - pub fn walk_filter_map_expr(vis: &mut T, mut e: P) -> Option> { vis.visit_expr(&mut e); Some(e) @@ -1139,18 +583,6 @@ fn walk_flat_map_stmt_kind(vis: &mut T, kind: StmtKind) -> SmallV } } -fn walk_vis(vis: &mut T, visibility: &mut Visibility) { - let Visibility { kind, span, tokens: _ } = visibility; - match kind { - VisibilityKind::Public | VisibilityKind::Inherited => {} - VisibilityKind::Restricted { path, id, shorthand: _ } => { - vis.visit_id(id); - vis.visit_path(path); - } - } - vis.visit_span(span); -} - fn walk_capture_by(vis: &mut T, capture_by: &mut CaptureBy) { match capture_by { CaptureBy::Ref => {} diff --git a/compiler/rustc_ast/src/visit.rs b/compiler/rustc_ast/src/visit.rs index d2f22b04a671..c88aa5c33ea9 100644 --- a/compiler/rustc_ast/src/visit.rs +++ b/compiler/rustc_ast/src/visit.rs @@ -15,11 +15,13 @@ pub use rustc_ast_ir::visit::VisitorResult; pub use rustc_ast_ir::{try_visit, visit_opt, walk_list, walk_visitable_list}; +use rustc_span::source_map::Spanned; use rustc_span::{Ident, Span}; use thin_vec::ThinVec; use crate::ast::*; use crate::ptr::P; +use crate::tokenstream::DelimSpan; #[derive(Copy, Clone, Debug, PartialEq)] pub enum AssocCtxt { @@ -237,8 +239,8 @@ pub trait Visitor<'ast>: Sized { fn visit_id(&mut self, _id: NodeId) -> Self::Result { Self::Result::output() } - fn visit_macro_def(&mut self, _mac: &'ast MacroDef) -> Self::Result { - Self::Result::output() + fn visit_macro_def(&mut self, macro_def: &'ast MacroDef) -> Self::Result { + walk_macro_def(self, macro_def) } fn visit_path(&mut self, path: &'ast Path) -> Self::Result { walk_path(self, path) @@ -320,8 +322,8 @@ macro_rules! common_visitor_and_walkers { id: NodeId, visibility: &$($lt)? $($mut)? Visibility, ctxt: Self::Ctxt, - visitor: &mut V, - ) $(-> >::Result)?; + vis: &mut V, + ) -> V::Result; } // this is only used by the MutVisitor. We include this symmetry here to make writing other functions easier @@ -329,12 +331,12 @@ macro_rules! common_visitor_and_walkers { #[expect(unused, rustc::pass_by_value)] #[inline] )? - fn visit_span<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, span: &$($lt)? $($mut)? Span) $(-> >::Result)? { + fn visit_span<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, span: &$($lt)? $($mut)? Span) -> V::Result { $( ${ignore($mut)} - visitor.visit_span(span); + vis.visit_span(span); )? - $(${ignore($lt)}V::Result::output())? + V::Result::output() } /// helper since `Visitor` wants `NodeId` but `MutVisitor` wants `&mut NodeId` @@ -342,34 +344,34 @@ macro_rules! common_visitor_and_walkers { #[expect(rustc::pass_by_value)] )? #[inline] - fn visit_id<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, id: &$($lt)? $($mut)? NodeId) $(-> >::Result)? { + fn visit_id<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, id: &$($lt)? $($mut)? NodeId) -> V::Result { // deref `&NodeId` into `NodeId` only for `Visitor` - visitor.visit_id( $(${ignore($lt)} * )? id) + vis.visit_id( $(${ignore($lt)} * )? id) } // this is only used by the MutVisitor. We include this symmetry here to make writing other functions easier - fn visit_safety<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, safety: &$($lt)? $($mut)? Safety) $(-> >::Result)? { + fn visit_safety<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, safety: &$($lt)? $($mut)? Safety) -> V::Result { match safety { Safety::Unsafe(span) => visit_span(vis, span), Safety::Safe(span) => visit_span(vis, span), - Safety::Default => { $(${ignore($lt)}V::Result::output())? } + Safety::Default => { V::Result::output() } } } - fn visit_constness<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, constness: &$($lt)? $($mut)? Const) $(-> >::Result)? { + fn visit_constness<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, constness: &$($lt)? $($mut)? Const) -> V::Result { match constness { Const::Yes(span) => visit_span(vis, span), Const::No => { - $(>::Result::output())? + V::Result::output() } } } - fn visit_defaultness<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, defaultness: &$($lt)? $($mut)? Defaultness) $(-> >::Result)? { + fn visit_defaultness<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, defaultness: &$($lt)? $($mut)? Defaultness) -> V::Result { match defaultness { Defaultness::Default(span) => visit_span(vis, span), Defaultness::Final => { - $(>::Result::output())? + V::Result::output() } } } @@ -377,9 +379,9 @@ macro_rules! common_visitor_and_walkers { fn visit_polarity<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, polarity: &$($lt)? $($mut)? ImplPolarity, - ) $(-> >::Result)? { + ) -> V::Result { match polarity { - ImplPolarity::Positive => { $(>::Result::output())? } + ImplPolarity::Positive => { V::Result::output() } ImplPolarity::Negative(span) => visit_span(vis, span), } } @@ -390,7 +392,7 @@ macro_rules! common_visitor_and_walkers { fn visit_modifiers<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, m: &$($lt)? $($mut)? TraitBoundModifiers - ) $(-> >::Result)? { + ) -> V::Result { let TraitBoundModifiers { constness, asyncness, polarity } = m; match constness { BoundConstness::Never => {} @@ -404,26 +406,26 @@ macro_rules! common_visitor_and_walkers { BoundPolarity::Positive => {} BoundPolarity::Negative(span) | BoundPolarity::Maybe(span) => try_visit!(visit_span(vis, span)), } - $(>::Result::output())? + V::Result::output() } - fn visit_bounds<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, bounds: &$($lt)? $($mut)? GenericBounds, ctxt: BoundKind) $(-> >::Result)? { + fn visit_bounds<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, bounds: &$($lt)? $($mut)? GenericBounds, ctxt: BoundKind) -> V::Result { walk_list!(visitor, visit_param_bound, bounds, ctxt); - $(>::Result::output())? + V::Result::output() } - pub fn walk_label<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, Label { ident }: &$($lt)? $($mut)? Label) $(-> >::Result)? { + pub fn walk_label<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, Label { ident }: &$($lt)? $($mut)? Label) -> V::Result { visitor.visit_ident(ident) } - pub fn walk_fn_header<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, header: &$($lt)? $($mut)? FnHeader) $(-> >::Result)? { + pub fn walk_fn_header<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, header: &$($lt)? $($mut)? FnHeader) -> V::Result { let FnHeader { safety, coroutine_kind, constness, ext: _ } = header; try_visit!(visit_constness(visitor, constness)); visit_opt!(visitor, visit_coroutine_kind, coroutine_kind); visit_safety(visitor, safety) } - pub fn walk_lifetime<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, Lifetime { id, ident }: &$($lt)? $($mut)? Lifetime) $(-> >::Result)? { + pub fn walk_lifetime<$($lt,)? V: $Visitor$(<$lt>)?>(visitor: &mut V, Lifetime { id, ident }: &$($lt)? $($mut)? Lifetime) -> V::Result { try_visit!(visit_id(visitor, id)); visitor.visit_ident(ident) } @@ -432,7 +434,7 @@ macro_rules! common_visitor_and_walkers { visitor: &mut V, item: &$($mut)? $($lt)? Item, ctxt: K::Ctxt, - ) $(-> >::Result)? { + ) -> V::Result { let Item { attrs, id, kind, vis, span, tokens: _ } = item; try_visit!(visit_id(visitor, id)); walk_list!(visitor, visit_attribute, attrs); @@ -444,7 +446,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_item<$($lt,)? V: $Visitor$(<$lt>)?, K: WalkItemKind>( visitor: &mut V, item: &$($mut)? $($lt)? Item, - ) $(-> >::Result)? { + ) -> V::Result { walk_item_ctxt(visitor, item, ()) } @@ -452,7 +454,7 @@ macro_rules! common_visitor_and_walkers { visitor: &mut V, item: &$($mut)? $($lt)? AssocItem, ctxt: AssocCtxt, - ) $(-> >::Result)? { + ) -> V::Result { walk_item_ctxt(visitor, item, ctxt) } @@ -465,7 +467,7 @@ macro_rules! common_visitor_and_walkers { visibility: &$($lt)? $($mut)? Visibility, _ctxt: Self::Ctxt, vis: &mut V, - ) $(-> >::Result)? { + ) -> V::Result { match self { ItemKind::ExternCrate(_orig_name, ident) => vis.visit_ident(ident), ItemKind::Use(use_tree) => vis.visit_use_tree(use_tree), @@ -505,7 +507,7 @@ macro_rules! common_visitor_and_walkers { } ModKind::Unloaded => {} } - $(>::Result::output())? + V::Result::output() } ItemKind::ForeignMod(nm) => vis.visit_foreign_mod(nm), ItemKind::GlobalAsm(asm) => vis.visit_inline_asm(asm), @@ -526,7 +528,7 @@ macro_rules! common_visitor_and_walkers { $(${ignore($mut)} walk_ty_alias_where_clauses(vis, where_clauses); )? - $(>::Result::output())? + V::Result::output() } ItemKind::Enum(ident, generics, enum_definition) => { try_visit!(vis.visit_ident(ident)); @@ -590,7 +592,7 @@ macro_rules! common_visitor_and_walkers { try_visit!(vis.visit_ident(ident)); visit_opt!(vis, visit_ident, rename); visit_opt!(vis, visit_block, body); - $(>::Result::output())? + V::Result::output() } ItemKind::DelegationMac(box DelegationMac { qself, prefix, suffixes, body }) => { try_visit!(vis.visit_qself(qself)); @@ -602,7 +604,7 @@ macro_rules! common_visitor_and_walkers { } } visit_opt!(vis, visit_block, body); - $(>::Result::output())? + V::Result::output() } } } @@ -611,7 +613,7 @@ macro_rules! common_visitor_and_walkers { fn walk_const_item<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, item: &$($lt)? $($mut)? ConstItem, - ) $(-> >::Result)? { + ) -> V::Result { let ConstItem { defaultness, ident, generics, ty, expr, define_opaque } = item; try_visit!(visit_defaultness(vis, defaultness)); try_visit!(vis.visit_ident(ident)); @@ -621,7 +623,7 @@ macro_rules! common_visitor_and_walkers { walk_define_opaques(vis, define_opaque) } - fn walk_foreign_mod<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, foreign_mod: &$($lt)? $($mut)? ForeignMod) $(-> >::Result)? { + fn walk_foreign_mod<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, foreign_mod: &$($lt)? $($mut)? ForeignMod) -> V::Result { let ForeignMod { extern_span: _, safety, abi: _, items } = foreign_mod; try_visit!(visit_safety(vis, safety)); visit_foreign_items(vis, items) @@ -630,14 +632,14 @@ macro_rules! common_visitor_and_walkers { fn walk_define_opaques<$($lt,)? V: $Visitor$(<$lt>)?>( visitor: &mut V, define_opaque: &$($lt)? $($mut)? Option>, - ) $(-> >::Result)? { + ) -> V::Result { if let Some(define_opaque) = define_opaque { for (id, path) in define_opaque { try_visit!(visit_id(visitor, id)); try_visit!(visitor.visit_path(path)); } } - $(>::Result::output())? + V::Result::output() } impl WalkItemKind for AssocItemKind { @@ -649,7 +651,7 @@ macro_rules! common_visitor_and_walkers { visibility: &$($lt)? $($mut)? Visibility, ctxt: Self::Ctxt, vis: &mut V, - ) $(-> >::Result)? { + ) -> V::Result { match self { AssocItemKind::Const(item) => { walk_const_item(vis, item) @@ -674,7 +676,7 @@ macro_rules! common_visitor_and_walkers { $(${ignore($mut)} walk_ty_alias_where_clauses(vis, where_clauses); )? - $(>::Result::output())? + V::Result::output() } AssocItemKind::MacCall(mac) => { vis.visit_mac_call(mac) @@ -694,7 +696,7 @@ macro_rules! common_visitor_and_walkers { try_visit!(vis.visit_ident(ident)); visit_opt!(vis, visit_ident, rename); visit_opt!(vis, visit_block, body); - $(>::Result::output())? + V::Result::output() } AssocItemKind::DelegationMac(box DelegationMac { qself, prefix, suffixes, body }) => { try_visit!(vis.visit_qself(qself)); @@ -706,7 +708,7 @@ macro_rules! common_visitor_and_walkers { } } visit_opt!(vis, visit_block, body); - $(>::Result::output())? + V::Result::output() } } } @@ -721,7 +723,7 @@ macro_rules! common_visitor_and_walkers { visibility: &$($lt)? $($mut)? Visibility, _ctxt: Self::Ctxt, vis: &mut V, - ) $(-> >::Result)? { + ) -> V::Result { match self { ForeignItemKind::Static(box StaticItem { ident, @@ -756,7 +758,7 @@ macro_rules! common_visitor_and_walkers { $(${ignore($mut)} walk_ty_alias_where_clauses(vis, where_clauses); )? - $(>::Result::output())? + V::Result::output() } ForeignItemKind::MacCall(mac) => { vis.visit_mac_call(mac) @@ -768,7 +770,7 @@ macro_rules! common_visitor_and_walkers { fn walk_coroutine_kind<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, coroutine_kind: &$($lt)? $($mut)? CoroutineKind, - ) $(-> >::Result)? { + ) -> V::Result { let (CoroutineKind::Async { span, closure_id, return_impl_trait_id } | CoroutineKind::Gen { span, closure_id, return_impl_trait_id } | CoroutineKind::AsyncGen { span, closure_id, return_impl_trait_id }) @@ -781,7 +783,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_pat<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, pattern: &$($lt)? $($mut)? Pat - ) $(-> >::Result)? { + ) -> V::Result { let Pat { id, kind, span, tokens: _ } = pattern; try_visit!(visit_id(vis, id)); match kind { @@ -832,7 +834,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_anon_const<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, constant: &$($lt)? $($mut)? AnonConst, - ) $(-> >::Result)? { + ) -> V::Result { let AnonConst { id, value } = constant; try_visit!(visit_id(vis, id)); vis.visit_expr(value) @@ -841,18 +843,18 @@ macro_rules! common_visitor_and_walkers { pub fn walk_path_segment<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, segment: &$($lt)? $($mut)? PathSegment, - ) $(-> >::Result)? { + ) -> V::Result { let PathSegment { ident, id, args } = segment; try_visit!(visit_id(vis, id)); try_visit!(vis.visit_ident(ident)); visit_opt!(vis, visit_generic_args, args); - $(>::Result::output())? + V::Result::output() } pub fn walk_block<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, block: &$($lt)? $($mut)? Block - ) $(-> >::Result)? { + ) -> V::Result { let Block { stmts, id, rules: _, span, tokens: _ } = block; try_visit!(visit_id(vis, id)); try_visit!(visit_stmts(vis, stmts)); @@ -862,7 +864,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_ty<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, ty: &$($lt)? $($mut)? Ty - ) $(-> >::Result)? { + ) -> V::Result { let Ty { id, kind, span, tokens: _ } = ty; try_visit!(visit_id(vis, id)); match kind { @@ -920,7 +922,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_crate<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, krate: &$($lt)? $($mut)? Crate, - ) $(-> >::Result)? { + ) -> V::Result { let Crate { attrs, items, spans, id, is_placeholder: _ } = krate; try_visit!(visit_id(vis, id)); walk_list!(vis, visit_attribute, attrs); @@ -933,7 +935,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_local<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, local: &$($lt)? $($mut)? Local, - ) $(-> >::Result)? { + ) -> V::Result { let Local { id, super_, pat, ty, kind, span, colon_sp, attrs, tokens: _ } = local; if let Some(sp) = super_ { try_visit!(visit_span(vis, sp)); @@ -961,7 +963,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_poly_trait_ref<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, p: &$($lt)? $($mut)? PolyTraitRef, - ) $(-> >::Result)? { + ) -> V::Result { let PolyTraitRef { bound_generic_params, modifiers, trait_ref, span } = p; try_visit!(visit_modifiers(vis, modifiers)); try_visit!(visit_generic_params(vis, bound_generic_params)); @@ -972,7 +974,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_trait_ref<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, TraitRef { path, ref_id }: &$($lt)? $($mut)? TraitRef, - ) $(-> >::Result)? { + ) -> V::Result { try_visit!(vis.visit_path(path)); visit_id(vis, ref_id) } @@ -980,7 +982,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_variant<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, variant: &$($lt)? $($mut)? Variant, - ) $(-> >::Result)? { + ) -> V::Result { let Variant { attrs, id, span, vis: visibility, ident, data, disr_expr, is_placeholder: _ } = variant; try_visit!(visit_id(vis, id)); walk_list!(vis, visit_attribute, attrs); @@ -995,7 +997,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_expr_field<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, f: &$($lt)? $($mut)? ExprField, - ) $(-> >::Result)? { + ) -> V::Result { let ExprField { attrs, id, span, ident, expr, is_shorthand: _, is_placeholder: _ } = f; try_visit!(visit_id(vis, id)); walk_list!(vis, visit_attribute, attrs); @@ -1007,7 +1009,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_pat_field<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, fp: &$($lt)? $($mut)? PatField, - ) $(-> >::Result)? { + ) -> V::Result { let PatField { ident, pat, is_shorthand: _, attrs, id, span, is_placeholder: _ } = fp; try_visit!(visit_id(vis, id)); walk_list!(vis, visit_attribute, attrs); @@ -1019,7 +1021,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_ty_pat<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, tp: &$($lt)? $($mut)? TyPat, - ) $(-> >::Result)? { + ) -> V::Result { let TyPat { id, kind, span, tokens: _ } = tp; try_visit!(visit_id(vis, id)); match kind { @@ -1036,19 +1038,19 @@ macro_rules! common_visitor_and_walkers { fn walk_qself<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, qself: &$($lt)? $($mut)? Option>, - ) $(-> >::Result)? { + ) -> V::Result { if let Some(qself) = qself { let QSelf { ty, path_span, position: _ } = &$($mut)? **qself; try_visit!(vis.visit_ty(ty)); try_visit!(visit_span(vis, path_span)); } - $(>::Result::output())? + V::Result::output() } pub fn walk_path<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, path: &$($lt)? $($mut)? Path, - ) $(-> >::Result)? { + ) -> V::Result { let Path { span, segments, tokens: _ } = path; walk_list!(vis, visit_path_segment, segments); visit_span(vis, span) @@ -1057,7 +1059,7 @@ macro_rules! common_visitor_and_walkers { pub fn walk_use_tree<$($lt,)? V: $Visitor$(<$lt>)?>( vis: &mut V, use_tree: &$($lt)? $($mut)? UseTree, - ) $(-> >::Result)? { + ) -> V::Result { let UseTree { prefix, kind, span } = use_tree; try_visit!(vis.visit_path(prefix)); match kind { @@ -1075,6 +1077,581 @@ macro_rules! common_visitor_and_walkers { } visit_span(vis, span) } + + pub fn walk_generic_args<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + generic_args: &$($lt)? $($mut)? GenericArgs + ) -> V::Result { + match generic_args { + GenericArgs::AngleBracketed(AngleBracketedArgs { span, args }) => { + for arg in args { + match arg { + AngleBracketedArg::Arg(a) => try_visit!(vis.visit_generic_arg(a)), + AngleBracketedArg::Constraint(c) => { + try_visit!(vis.visit_assoc_item_constraint(c)) + } + } + } + visit_span(vis, span) + } + GenericArgs::Parenthesized(data) => { + let ParenthesizedArgs { span, inputs, inputs_span, output } = data; + walk_list!(vis, visit_ty, inputs); + try_visit!(vis.visit_fn_ret_ty(output)); + try_visit!(visit_span(vis, span)); + visit_span(vis, inputs_span) + } + GenericArgs::ParenthesizedElided(span) => visit_span(vis, span) + } + } + + pub fn walk_generic_arg<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + generic_arg: &$($lt)? $($mut)? GenericArg, + ) -> V::Result { + match generic_arg { + GenericArg::Lifetime(lt) => vis.visit_lifetime(lt, $(${ignore($lt)} LifetimeCtxt::GenericArg)? ), + GenericArg::Type(ty) => vis.visit_ty(ty), + GenericArg::Const(ct) => vis.visit_anon_const(ct), + } + } + + pub fn walk_assoc_item_constraint<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + constraint: &$($lt)? $($mut)? AssocItemConstraint, + ) -> V::Result { + let AssocItemConstraint { id, ident, gen_args, kind, span } = constraint; + try_visit!(visit_id(vis, id)); + try_visit!(vis.visit_ident(ident)); + visit_opt!(vis, visit_generic_args, gen_args); + match kind { + AssocItemConstraintKind::Equality { term } => match term { + Term::Ty(ty) => try_visit!(vis.visit_ty(ty)), + Term::Const(c) => try_visit!(vis.visit_anon_const(c)), + }, + AssocItemConstraintKind::Bound { bounds } => { + try_visit!(visit_bounds(vis, bounds, BoundKind::Bound)); + } + } + visit_span(vis, span) + } + + pub fn walk_param_bound<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, bound: &$($lt)? $($mut)? GenericBound) -> V::Result { + match bound { + GenericBound::Trait(trait_ref) => vis.visit_poly_trait_ref(trait_ref), + GenericBound::Outlives(lifetime) => vis.visit_lifetime(lifetime, $(${ignore($lt)} LifetimeCtxt::Bound)?), + GenericBound::Use(args, span) => { + walk_list!(vis, visit_precise_capturing_arg, args); + visit_span(vis, span) + } + } + } + + pub fn walk_precise_capturing_arg<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + arg: &$($lt)? $($mut)? PreciseCapturingArg, + ) -> V::Result { + match arg { + PreciseCapturingArg::Lifetime(lt) => vis.visit_lifetime(lt, $(${ignore($lt)} LifetimeCtxt::GenericArg)?), + PreciseCapturingArg::Arg(path, id) => { + try_visit!(visit_id(vis, id)); + vis.visit_path(path) + } + } + } + + pub fn walk_generic_param<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + param: &$($lt)? $($mut)? GenericParam, + ) -> V::Result { + let GenericParam { id, ident, attrs, bounds, is_placeholder: _, kind, colon_span } = + param; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + try_visit!(vis.visit_ident(ident)); + walk_list!(vis, visit_param_bound, bounds, BoundKind::Bound); + match kind { + GenericParamKind::Lifetime => (), + GenericParamKind::Type { default } => visit_opt!(vis, visit_ty, default), + GenericParamKind::Const { ty, default, kw_span: _ } => { + try_visit!(vis.visit_ty(ty)); + visit_opt!(vis, visit_anon_const, default); + } + } + if let Some(sp) = colon_span { + try_visit!(visit_span(vis, sp)) + } + V::Result::output() + } + + pub fn walk_generics<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, generics: &$($lt)? $($mut)? Generics) -> V::Result { + let Generics { params, where_clause, span } = generics; + let WhereClause { has_where_token: _, predicates, span: where_clause_span } = where_clause; + try_visit!(visit_generic_params(vis, params)); + try_visit!(visit_where_predicates(vis, predicates)); + try_visit!(visit_span(vis, span)); + visit_span(vis, where_clause_span) + } + + pub fn walk_contract<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, c: &$($lt)? $($mut)? FnContract) -> V::Result { + let FnContract { requires, ensures } = c; + visit_opt!(vis, visit_expr, requires); + visit_opt!(vis, visit_expr, ensures); + V::Result::output() + } + + pub fn walk_where_predicate<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + predicate: &$($lt)? $($mut)? WherePredicate, + ) -> V::Result { + let WherePredicate { attrs, kind, id, span, is_placeholder: _ } = predicate; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + try_visit!(visit_span(vis, span)); + vis.visit_where_predicate_kind(kind) + } + + pub fn walk_closure_binder<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + binder: &$($lt)? $($mut)? ClosureBinder, + ) -> V::Result { + match binder { + ClosureBinder::NotPresent => {} + ClosureBinder::For { generic_params, span } => { + try_visit!(visit_generic_params(vis, generic_params)); + try_visit!(visit_span(vis, span)); + } + } + V::Result::output() + } + + pub fn walk_where_predicate_kind<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + kind: &$($lt)? $($mut)? WherePredicateKind, + ) -> V::Result { + match kind { + WherePredicateKind::BoundPredicate(WhereBoundPredicate { + bounded_ty, + bounds, + bound_generic_params, + }) => { + visit_generic_params(vis, bound_generic_params); + try_visit!(vis.visit_ty(bounded_ty)); + walk_list!(vis, visit_param_bound, bounds, BoundKind::Bound); + } + WherePredicateKind::RegionPredicate(WhereRegionPredicate { lifetime, bounds }) => { + try_visit!(vis.visit_lifetime(lifetime, $(${ignore($lt)} LifetimeCtxt::Bound )?)); + walk_list!(vis, visit_param_bound, bounds, BoundKind::Bound); + } + WherePredicateKind::EqPredicate(WhereEqPredicate { lhs_ty, rhs_ty }) => { + try_visit!(vis.visit_ty(lhs_ty)); + try_visit!(vis.visit_ty(rhs_ty)); + } + } + V::Result::output() + } + + pub fn walk_fn_decl<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + FnDecl { inputs, output }: &$($lt)? $($mut)? FnDecl, + ) -> V::Result { + try_visit!(visit_params(vis, inputs)); + vis.visit_fn_ret_ty(output) + } + + pub fn walk_fn_ret_ty<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, ret_ty: &$($lt)? $($mut)? FnRetTy) -> V::Result { + match ret_ty { + FnRetTy::Default(span) => visit_span(vis, span), + FnRetTy::Ty(output_ty) => vis.visit_ty(output_ty), + } + } + + pub fn walk_fn<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, kind: FnKind<$($lt)? $(${ignore($mut)} '_)?>) -> V::Result { + match kind { + FnKind::Fn( + _ctxt, + _vis, + Fn { + defaultness, + ident, + sig: FnSig { header, decl, span }, + generics, + contract, + body, + define_opaque, + }, + ) => { + // Visibility is visited as a part of the item. + try_visit!(visit_defaultness(vis, defaultness)); + try_visit!(vis.visit_ident(ident)); + try_visit!(vis.visit_fn_header(header)); + try_visit!(vis.visit_generics(generics)); + try_visit!(vis.visit_fn_decl(decl)); + visit_opt!(vis, visit_contract, contract); + visit_opt!(vis, visit_block, body); + try_visit!(visit_span(vis, span)); + walk_define_opaques(vis, define_opaque) + } + FnKind::Closure(binder, coroutine_kind, decl, body) => { + try_visit!(vis.visit_closure_binder(binder)); + visit_opt!(vis, visit_coroutine_kind, coroutine_kind); + try_visit!(vis.visit_fn_decl(decl)); + vis.visit_expr(body) + } + } + } + + pub fn walk_variant_data<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, data: &$($lt)? $($mut)? VariantData) -> V::Result { + match data { + VariantData::Struct { fields, recovered: _ } => { + visit_field_defs(vis, fields) + } + VariantData::Tuple(fields, id) => { + try_visit!(visit_id(vis, id)); + visit_field_defs(vis, fields) + } + VariantData::Unit(id) => visit_id(vis, id), + } + } + + pub fn walk_field_def<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, field: &$($lt)? $($mut)? FieldDef) -> V::Result { + let FieldDef { attrs, id, span, vis: visibility, ident, ty, is_placeholder: _, safety: _, default } = + field; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + try_visit!(vis.visit_vis(visibility)); + visit_opt!(vis, visit_ident, ident); + try_visit!(vis.visit_ty(ty)); + visit_opt!(vis, visit_anon_const, default); + visit_span(vis, span) + } + + fn visit_delim_args<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, args: &$($lt)? $($mut)? DelimArgs) -> V::Result { + let DelimArgs { dspan, delim: _, tokens: _ } = args; + let DelimSpan { open, close } = dspan; + try_visit!(visit_span(vis, open)); + visit_span(vis, close) + } + + pub fn walk_mac<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, mac: &$($lt)? $($mut)? MacCall) -> V::Result { + let MacCall { path, args } = mac; + try_visit!(vis.visit_path(path)); + visit_delim_args(vis, args) + } + + fn walk_macro_def<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, macro_def: &$($lt)? $($mut)? MacroDef) -> V::Result { + let MacroDef { body, macro_rules: _ } = macro_def; + visit_delim_args(vis, body) + } + + pub fn walk_inline_asm<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, asm: &$($lt)? $($mut)? InlineAsm) -> V::Result { + // FIXME: Visit spans inside all this currently ignored stuff. + let InlineAsm { + asm_macro: _, + template: _, + template_strs: _, + operands, + clobber_abis: _, + options: _, + line_spans: _, + } = asm; + for (op, span) in operands { + match op { + InlineAsmOperand::In { expr, reg: _ } + | InlineAsmOperand::Out { expr: Some(expr), reg: _, late: _ } + | InlineAsmOperand::InOut { expr, reg: _, late: _ } => { + try_visit!(vis.visit_expr(expr)) + } + InlineAsmOperand::Out { expr: None, reg: _, late: _ } => {} + InlineAsmOperand::SplitInOut { in_expr, out_expr, reg: _, late: _ } => { + try_visit!(vis.visit_expr(in_expr)); + visit_opt!(vis, visit_expr, out_expr); + } + InlineAsmOperand::Const { anon_const } => { + try_visit!(vis.visit_anon_const(anon_const)) + } + InlineAsmOperand::Sym { sym } => try_visit!(vis.visit_inline_asm_sym(sym)), + InlineAsmOperand::Label { block } => try_visit!(vis.visit_block(block)), + } + try_visit!(visit_span(vis, span)); + } + V::Result::output() + } + + pub fn walk_inline_asm_sym<$($lt,)? V: $Visitor$(<$lt>)?>( + vis: &mut V, + InlineAsmSym { id, qself, path }: &$($lt)? $($mut)? InlineAsmSym, + ) -> V::Result { + try_visit!(visit_id(vis, id)); + try_visit!(vis.visit_qself(qself)); + vis.visit_path(path) + } + + // FIXME: visit the template exhaustively. + pub fn walk_format_args<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, fmt: &$($lt)? $($mut)? FormatArgs) -> V::Result { + let FormatArgs { span, template: _, arguments, uncooked_fmt_str: _ } = fmt; + let args = $(${ignore($mut)} arguments.all_args_mut())? $(${ignore($lt)} arguments.all_args())? ; + for FormatArgument { kind, expr } in args { + match kind { + FormatArgumentKind::Named(ident) | FormatArgumentKind::Captured(ident) => { + try_visit!(vis.visit_ident(ident)) + } + FormatArgumentKind::Normal => {} + } + try_visit!(vis.visit_expr(expr)); + } + visit_span(vis, span) + } + + pub fn walk_expr<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, expression: &$($lt)? $($mut)? Expr) -> V::Result { + let Expr { id, kind, span, attrs, tokens: _ } = expression; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + match kind { + ExprKind::Array(exprs) => { + try_visit!(visit_exprs(vis, exprs)); + } + ExprKind::ConstBlock(anon_const) => try_visit!(vis.visit_anon_const(anon_const)), + ExprKind::Repeat(element, count) => { + try_visit!(vis.visit_expr(element)); + try_visit!(vis.visit_anon_const(count)); + } + ExprKind::Struct(se) => { + let StructExpr { qself, path, fields, rest } = &$($mut)?**se; + try_visit!(vis.visit_qself(qself)); + try_visit!(vis.visit_path(path)); + visit_expr_fields(vis, fields); + match rest { + StructRest::Base(expr) => try_visit!(vis.visit_expr(expr)), + StructRest::Rest(_span) => {} + StructRest::None => {} + } + } + ExprKind::Tup(exprs) => { + try_visit!(visit_exprs(vis, exprs)); + } + ExprKind::Call(callee_expression, arguments) => { + try_visit!(vis.visit_expr(callee_expression)); + try_visit!(visit_exprs(vis, arguments)); + } + ExprKind::MethodCall(box MethodCall { seg, receiver, args, span }) => { + try_visit!(vis.visit_method_receiver_expr(receiver)); + try_visit!(vis.visit_path_segment(seg)); + try_visit!(visit_exprs(vis, args)); + try_visit!(visit_span(vis, span)); + } + ExprKind::Binary(Spanned { span, node: _ }, left_expression, right_expression) => { + try_visit!(vis.visit_expr(left_expression)); + try_visit!(vis.visit_expr(right_expression)); + try_visit!(visit_span(vis, span)) + } + ExprKind::AddrOf(_kind, _mutbl, subexpression) => { + try_visit!(vis.visit_expr(subexpression)); + } + ExprKind::Unary(_op, subexpression) => { + try_visit!(vis.visit_expr(subexpression)); + } + ExprKind::Cast(subexpression, typ) | ExprKind::Type(subexpression, typ) => { + try_visit!(vis.visit_expr(subexpression)); + try_visit!(vis.visit_ty(typ)); + } + ExprKind::Let(pat, expr, span, _recovered) => { + try_visit!(vis.visit_pat(pat)); + try_visit!(vis.visit_expr(expr)); + try_visit!(visit_span(vis, span)) + } + ExprKind::If(head_expression, if_block, optional_else) => { + try_visit!(vis.visit_expr(head_expression)); + try_visit!(vis.visit_block(if_block)); + visit_opt!(vis, visit_expr, optional_else); + } + ExprKind::While(subexpression, block, opt_label) => { + visit_opt!(vis, visit_label, opt_label); + try_visit!(vis.visit_expr(subexpression)); + try_visit!(vis.visit_block(block)); + } + ExprKind::ForLoop { pat, iter, body, label, kind: _ } => { + visit_opt!(vis, visit_label, label); + try_visit!(vis.visit_pat(pat)); + try_visit!(vis.visit_expr(iter)); + try_visit!(vis.visit_block(body)); + } + ExprKind::Loop(block, opt_label, span) => { + visit_opt!(vis, visit_label, opt_label); + try_visit!(vis.visit_block(block)); + try_visit!(visit_span(vis, span)) + } + ExprKind::Match(subexpression, arms, _kind) => { + try_visit!(vis.visit_expr(subexpression)); + try_visit!(visit_arms(vis, arms)); + } + ExprKind::Closure(box Closure { + binder, + capture_clause, + coroutine_kind, + constness, + movability: _, + fn_decl, + body, + fn_decl_span, + fn_arg_span, + }) => { + try_visit!(visit_constness(vis, constness)); + try_visit!(vis.visit_capture_by(capture_clause)); + try_visit!(vis.visit_fn( + FnKind::Closure(binder, coroutine_kind, fn_decl, body), + *span, + *id + )); + try_visit!(visit_span(vis, fn_decl_span)); + try_visit!(visit_span(vis, fn_arg_span)); + } + ExprKind::Block(block, opt_label) => { + visit_opt!(vis, visit_label, opt_label); + try_visit!(vis.visit_block(block)); + } + ExprKind::Gen(_capt, body, _kind, decl_span) => { + try_visit!(vis.visit_block(body)); + try_visit!(visit_span(vis, decl_span)); + } + ExprKind::Await(expr, span) => { + try_visit!(vis.visit_expr(expr)); + try_visit!(visit_span(vis, span)); + } + ExprKind::Use(expr, span) => { + try_visit!(vis.visit_expr(expr)); + try_visit!(visit_span(vis, span)); + } + ExprKind::Assign(lhs, rhs, span) => { + try_visit!(vis.visit_expr(lhs)); + try_visit!(vis.visit_expr(rhs)); + try_visit!(visit_span(vis, span)); + } + ExprKind::AssignOp(_op, left_expression, right_expression) => { + try_visit!(vis.visit_expr(left_expression)); + try_visit!(vis.visit_expr(right_expression)); + } + ExprKind::Field(subexpression, ident) => { + try_visit!(vis.visit_expr(subexpression)); + try_visit!(vis.visit_ident(ident)); + } + ExprKind::Index(main_expression, index_expression, span) => { + try_visit!(vis.visit_expr(main_expression)); + try_visit!(vis.visit_expr(index_expression)); + try_visit!(visit_span(vis, span)); + } + ExprKind::Range(start, end, _limit) => { + visit_opt!(vis, visit_expr, start); + visit_opt!(vis, visit_expr, end); + } + ExprKind::Underscore => {} + ExprKind::Path(maybe_qself, path) => { + try_visit!(vis.visit_qself(maybe_qself)); + try_visit!(vis.visit_path(path)); + } + ExprKind::Break(opt_label, opt_expr) => { + visit_opt!(vis, visit_label, opt_label); + visit_opt!(vis, visit_expr, opt_expr); + } + ExprKind::Continue(opt_label) => { + visit_opt!(vis, visit_label, opt_label); + } + ExprKind::Ret(optional_expression) => { + visit_opt!(vis, visit_expr, optional_expression); + } + ExprKind::Yeet(optional_expression) => { + visit_opt!(vis, visit_expr, optional_expression); + } + ExprKind::Become(expr) => try_visit!(vis.visit_expr(expr)), + ExprKind::MacCall(mac) => try_visit!(vis.visit_mac_call(mac)), + ExprKind::Paren(subexpression) => try_visit!(vis.visit_expr(subexpression)), + ExprKind::InlineAsm(asm) => try_visit!(vis.visit_inline_asm(asm)), + ExprKind::FormatArgs(f) => try_visit!(vis.visit_format_args(f)), + ExprKind::OffsetOf(container, fields) => { + try_visit!(vis.visit_ty(container)); + walk_list!(vis, visit_ident, fields); + } + ExprKind::Yield(kind) => { + match kind { + YieldKind::Postfix(expr) => { + try_visit!(vis.visit_expr(expr)); + } + YieldKind::Prefix(expr) => { + visit_opt!(vis, visit_expr, expr); + } + } + } + ExprKind::Try(subexpression) => try_visit!(vis.visit_expr(subexpression)), + ExprKind::TryBlock(body) => try_visit!(vis.visit_block(body)), + ExprKind::Lit(_token) => {} + ExprKind::IncludedBytes(_bytes) => {} + ExprKind::UnsafeBinderCast(_kind, expr, ty) => { + try_visit!(vis.visit_expr(expr)); + visit_opt!(vis, visit_ty, ty); + } + ExprKind::Err(_guar) => {} + ExprKind::Dummy => {} + } + + visit_span(vis, span) + } + + pub fn walk_param<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, param: &$($lt)? $($mut)? Param) -> V::Result { + let Param { attrs, ty, pat, id, span, is_placeholder: _ } = param; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + try_visit!(vis.visit_pat(pat)); + try_visit!(vis.visit_ty(ty)); + visit_span(vis, span) + } + + pub fn walk_arm<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, arm: &$($lt)? $($mut)? Arm) -> V::Result { + let Arm { attrs, pat, guard, body, span, id, is_placeholder: _ } = arm; + try_visit!(visit_id(vis, id)); + walk_list!(vis, visit_attribute, attrs); + try_visit!(vis.visit_pat(pat)); + visit_opt!(vis, visit_expr, guard); + visit_opt!(vis, visit_expr, body); + visit_span(vis, span) + } + + pub fn walk_vis<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, visibility: &$($lt)? $($mut)? Visibility) -> V::Result { + let Visibility { kind, span, tokens: _ } = visibility; + match kind { + VisibilityKind::Restricted { path, id, shorthand: _ } => { + try_visit!(visit_id(vis, id)); + try_visit!(vis.visit_path(path)); + } + VisibilityKind::Public | VisibilityKind::Inherited => {} + } + visit_span(vis, span) + } + + pub fn walk_attribute<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, attr: &$($lt)? $($mut)? Attribute) -> V::Result { + let Attribute { kind, id: _, style: _, span } = attr; + match kind { + AttrKind::Normal(normal) => { + let NormalAttr { item, tokens: _ } = &$($mut)?**normal; + let AttrItem { unsafety: _, path, args, tokens: _ } = item; + try_visit!(vis.visit_path(path)); + try_visit!(walk_attr_args(vis, args)); + } + AttrKind::DocComment(_kind, _sym) => {} + } + visit_span(vis, span) + } + + pub fn walk_attr_args<$($lt,)? V: $Visitor$(<$lt>)?>(vis: &mut V, args: &$($lt)? $($mut)? AttrArgs) -> V::Result { + match args { + AttrArgs::Empty => {} + AttrArgs::Delimited(args) => try_visit!(visit_delim_args(vis, args)), + AttrArgs::Eq { eq_span, expr } => { + try_visit!(vis.visit_expr(expr)); + try_visit!(visit_span(vis, eq_span)); + } + } + V::Result::output() + } }; } @@ -1102,9 +1679,15 @@ generate_list_visit_fns! { visit_foreign_items, P, visit_foreign_item; visit_generic_params, GenericParam, visit_generic_param; visit_stmts, Stmt, visit_stmt; + visit_exprs, P, visit_expr; + visit_expr_fields, ExprField, visit_expr_field; visit_pat_fields, PatField, visit_pat_field; visit_variants, Variant, visit_variant; visit_assoc_items, P, visit_assoc_item, ctxt: AssocCtxt; + visit_where_predicates, WherePredicate, visit_where_predicate; + visit_params, Param, visit_param; + visit_field_defs, FieldDef, visit_field_def; + visit_arms, Arm, visit_arm; } #[expect(rustc::pass_by_value)] // needed for symmetry with mut_visit @@ -1116,239 +1699,6 @@ fn visit_nested_use_tree<'a, V: Visitor<'a>>( vis.visit_nested_use_tree(nested_tree, nested_id) } -pub fn walk_generic_args<'a, V>(visitor: &mut V, generic_args: &'a GenericArgs) -> V::Result -where - V: Visitor<'a>, -{ - match generic_args { - GenericArgs::AngleBracketed(AngleBracketedArgs { span: _, args }) => { - for arg in args { - match arg { - AngleBracketedArg::Arg(a) => try_visit!(visitor.visit_generic_arg(a)), - AngleBracketedArg::Constraint(c) => { - try_visit!(visitor.visit_assoc_item_constraint(c)) - } - } - } - } - GenericArgs::Parenthesized(data) => { - let ParenthesizedArgs { span: _, inputs, inputs_span: _, output } = data; - walk_list!(visitor, visit_ty, inputs); - try_visit!(visitor.visit_fn_ret_ty(output)); - } - GenericArgs::ParenthesizedElided(_span) => {} - } - V::Result::output() -} - -pub fn walk_generic_arg<'a, V>(visitor: &mut V, generic_arg: &'a GenericArg) -> V::Result -where - V: Visitor<'a>, -{ - match generic_arg { - GenericArg::Lifetime(lt) => visitor.visit_lifetime(lt, LifetimeCtxt::GenericArg), - GenericArg::Type(ty) => visitor.visit_ty(ty), - GenericArg::Const(ct) => visitor.visit_anon_const(ct), - } -} - -pub fn walk_assoc_item_constraint<'a, V: Visitor<'a>>( - visitor: &mut V, - constraint: &'a AssocItemConstraint, -) -> V::Result { - let AssocItemConstraint { id: _, ident, gen_args, kind, span: _ } = constraint; - try_visit!(visitor.visit_ident(ident)); - visit_opt!(visitor, visit_generic_args, gen_args); - match kind { - AssocItemConstraintKind::Equality { term } => match term { - Term::Ty(ty) => try_visit!(visitor.visit_ty(ty)), - Term::Const(c) => try_visit!(visitor.visit_anon_const(c)), - }, - AssocItemConstraintKind::Bound { bounds } => { - walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); - } - } - V::Result::output() -} - -pub fn walk_param_bound<'a, V: Visitor<'a>>(visitor: &mut V, bound: &'a GenericBound) -> V::Result { - match bound { - GenericBound::Trait(trait_ref) => visitor.visit_poly_trait_ref(trait_ref), - GenericBound::Outlives(lifetime) => visitor.visit_lifetime(lifetime, LifetimeCtxt::Bound), - GenericBound::Use(args, _span) => { - walk_list!(visitor, visit_precise_capturing_arg, args); - V::Result::output() - } - } -} - -pub fn walk_precise_capturing_arg<'a, V: Visitor<'a>>( - visitor: &mut V, - arg: &'a PreciseCapturingArg, -) -> V::Result { - match arg { - PreciseCapturingArg::Lifetime(lt) => visitor.visit_lifetime(lt, LifetimeCtxt::GenericArg), - PreciseCapturingArg::Arg(path, id) => { - try_visit!(visitor.visit_id(*id)); - visitor.visit_path(path) - } - } -} - -pub fn walk_generic_param<'a, V: Visitor<'a>>( - visitor: &mut V, - param: &'a GenericParam, -) -> V::Result { - let GenericParam { id: _, ident, attrs, bounds, is_placeholder: _, kind, colon_span: _ } = - param; - walk_list!(visitor, visit_attribute, attrs); - try_visit!(visitor.visit_ident(ident)); - walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); - match kind { - GenericParamKind::Lifetime => (), - GenericParamKind::Type { default } => visit_opt!(visitor, visit_ty, default), - GenericParamKind::Const { ty, default, kw_span: _ } => { - try_visit!(visitor.visit_ty(ty)); - visit_opt!(visitor, visit_anon_const, default); - } - } - V::Result::output() -} - -pub fn walk_generics<'a, V: Visitor<'a>>(visitor: &mut V, generics: &'a Generics) -> V::Result { - let Generics { params, where_clause, span: _ } = generics; - let WhereClause { has_where_token: _, predicates, span: _ } = where_clause; - walk_list!(visitor, visit_generic_param, params); - walk_list!(visitor, visit_where_predicate, predicates); - V::Result::output() -} - -pub fn walk_closure_binder<'a, V: Visitor<'a>>( - visitor: &mut V, - binder: &'a ClosureBinder, -) -> V::Result { - match binder { - ClosureBinder::NotPresent => {} - ClosureBinder::For { generic_params, span: _ } => { - walk_list!(visitor, visit_generic_param, generic_params) - } - } - V::Result::output() -} - -pub fn walk_contract<'a, V: Visitor<'a>>(visitor: &mut V, c: &'a FnContract) -> V::Result { - let FnContract { requires, ensures } = c; - if let Some(pred) = requires { - visitor.visit_expr(pred); - } - if let Some(pred) = ensures { - visitor.visit_expr(pred); - } - V::Result::output() -} - -pub fn walk_where_predicate<'a, V: Visitor<'a>>( - visitor: &mut V, - predicate: &'a WherePredicate, -) -> V::Result { - let WherePredicate { attrs, kind, id: _, span: _, is_placeholder: _ } = predicate; - walk_list!(visitor, visit_attribute, attrs); - visitor.visit_where_predicate_kind(kind) -} - -pub fn walk_where_predicate_kind<'a, V: Visitor<'a>>( - visitor: &mut V, - kind: &'a WherePredicateKind, -) -> V::Result { - match kind { - WherePredicateKind::BoundPredicate(WhereBoundPredicate { - bounded_ty, - bounds, - bound_generic_params, - }) => { - walk_list!(visitor, visit_generic_param, bound_generic_params); - try_visit!(visitor.visit_ty(bounded_ty)); - walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); - } - WherePredicateKind::RegionPredicate(WhereRegionPredicate { lifetime, bounds }) => { - try_visit!(visitor.visit_lifetime(lifetime, LifetimeCtxt::Bound)); - walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound); - } - WherePredicateKind::EqPredicate(WhereEqPredicate { lhs_ty, rhs_ty }) => { - try_visit!(visitor.visit_ty(lhs_ty)); - try_visit!(visitor.visit_ty(rhs_ty)); - } - } - V::Result::output() -} - -pub fn walk_fn_ret_ty<'a, V: Visitor<'a>>(visitor: &mut V, ret_ty: &'a FnRetTy) -> V::Result { - match ret_ty { - FnRetTy::Default(_span) => {} - FnRetTy::Ty(output_ty) => try_visit!(visitor.visit_ty(output_ty)), - } - V::Result::output() -} - -pub fn walk_fn_decl<'a, V: Visitor<'a>>( - visitor: &mut V, - FnDecl { inputs, output }: &'a FnDecl, -) -> V::Result { - walk_list!(visitor, visit_param, inputs); - visitor.visit_fn_ret_ty(output) -} - -pub fn walk_fn<'a, V: Visitor<'a>>(visitor: &mut V, kind: FnKind<'a>) -> V::Result { - match kind { - FnKind::Fn( - _ctxt, - _vis, - Fn { - defaultness: _, - ident, - sig: FnSig { header, decl, span: _ }, - generics, - contract, - body, - define_opaque, - }, - ) => { - // Visibility is visited as a part of the item. - try_visit!(visitor.visit_ident(ident)); - try_visit!(visitor.visit_fn_header(header)); - try_visit!(visitor.visit_generics(generics)); - try_visit!(visitor.visit_fn_decl(decl)); - visit_opt!(visitor, visit_contract, contract); - visit_opt!(visitor, visit_block, body); - try_visit!(walk_define_opaques(visitor, define_opaque)); - } - FnKind::Closure(binder, coroutine_kind, decl, body) => { - try_visit!(visitor.visit_closure_binder(binder)); - visit_opt!(visitor, visit_coroutine_kind, coroutine_kind.as_ref()); - try_visit!(visitor.visit_fn_decl(decl)); - try_visit!(visitor.visit_expr(body)); - } - } - V::Result::output() -} - -pub fn walk_variant_data<'a, V: Visitor<'a>>(visitor: &mut V, data: &'a VariantData) -> V::Result { - visit_opt!(visitor, visit_id, data.ctor_node_id()); - walk_list!(visitor, visit_field_def, data.fields()); - V::Result::output() -} - -pub fn walk_field_def<'a, V: Visitor<'a>>(visitor: &mut V, field: &'a FieldDef) -> V::Result { - let FieldDef { attrs, id: _, span: _, vis, ident, ty, is_placeholder: _, safety: _, default } = - field; - walk_list!(visitor, visit_attribute, attrs); - try_visit!(visitor.visit_vis(vis)); - visit_opt!(visitor, visit_ident, ident); - try_visit!(visitor.visit_ty(ty)); - visit_opt!(visitor, visit_anon_const, &*default); - V::Result::output() -} - pub fn walk_stmt<'a, V: Visitor<'a>>(visitor: &mut V, statement: &'a Stmt) -> V::Result { let Stmt { id: _, kind, span: _ } = statement; match kind { @@ -1364,284 +1714,3 @@ pub fn walk_stmt<'a, V: Visitor<'a>>(visitor: &mut V, statement: &'a Stmt) -> V: } V::Result::output() } - -pub fn walk_mac<'a, V: Visitor<'a>>(visitor: &mut V, mac: &'a MacCall) -> V::Result { - let MacCall { path, args: _ } = mac; - visitor.visit_path(path) -} - -pub fn walk_inline_asm<'a, V: Visitor<'a>>(visitor: &mut V, asm: &'a InlineAsm) -> V::Result { - let InlineAsm { - asm_macro: _, - template: _, - template_strs: _, - operands, - clobber_abis: _, - options: _, - line_spans: _, - } = asm; - for (op, _span) in operands { - match op { - InlineAsmOperand::In { expr, reg: _ } - | InlineAsmOperand::Out { expr: Some(expr), reg: _, late: _ } - | InlineAsmOperand::InOut { expr, reg: _, late: _ } => { - try_visit!(visitor.visit_expr(expr)) - } - InlineAsmOperand::Out { expr: None, reg: _, late: _ } => {} - InlineAsmOperand::SplitInOut { in_expr, out_expr, reg: _, late: _ } => { - try_visit!(visitor.visit_expr(in_expr)); - visit_opt!(visitor, visit_expr, out_expr); - } - InlineAsmOperand::Const { anon_const } => { - try_visit!(visitor.visit_anon_const(anon_const)) - } - InlineAsmOperand::Sym { sym } => try_visit!(visitor.visit_inline_asm_sym(sym)), - InlineAsmOperand::Label { block } => try_visit!(visitor.visit_block(block)), - } - } - V::Result::output() -} - -pub fn walk_inline_asm_sym<'a, V: Visitor<'a>>( - visitor: &mut V, - InlineAsmSym { id, qself, path }: &'a InlineAsmSym, -) -> V::Result { - try_visit!(visitor.visit_qself(qself)); - try_visit!(visitor.visit_id(*id)); - visitor.visit_path(path) -} - -pub fn walk_format_args<'a, V: Visitor<'a>>(visitor: &mut V, fmt: &'a FormatArgs) -> V::Result { - let FormatArgs { span: _, template: _, arguments, uncooked_fmt_str: _ } = fmt; - for FormatArgument { kind, expr } in arguments.all_args() { - match kind { - FormatArgumentKind::Named(ident) | FormatArgumentKind::Captured(ident) => { - try_visit!(visitor.visit_ident(ident)) - } - FormatArgumentKind::Normal => {} - } - try_visit!(visitor.visit_expr(expr)); - } - V::Result::output() -} - -pub fn walk_expr<'a, V: Visitor<'a>>(visitor: &mut V, expression: &'a Expr) -> V::Result { - let Expr { id, kind, span, attrs, tokens: _ } = expression; - walk_list!(visitor, visit_attribute, attrs); - match kind { - ExprKind::Array(subexpressions) => { - walk_list!(visitor, visit_expr, subexpressions); - } - ExprKind::ConstBlock(anon_const) => try_visit!(visitor.visit_anon_const(anon_const)), - ExprKind::Repeat(element, count) => { - try_visit!(visitor.visit_expr(element)); - try_visit!(visitor.visit_anon_const(count)); - } - ExprKind::Struct(se) => { - let StructExpr { qself, path, fields, rest } = &**se; - try_visit!(visitor.visit_qself(qself)); - try_visit!(visitor.visit_id(*id)); - try_visit!(visitor.visit_path(path)); - walk_list!(visitor, visit_expr_field, fields); - match rest { - StructRest::Base(expr) => try_visit!(visitor.visit_expr(expr)), - StructRest::Rest(_span) => {} - StructRest::None => {} - } - } - ExprKind::Tup(subexpressions) => { - walk_list!(visitor, visit_expr, subexpressions); - } - ExprKind::Call(callee_expression, arguments) => { - try_visit!(visitor.visit_expr(callee_expression)); - walk_list!(visitor, visit_expr, arguments); - } - ExprKind::MethodCall(box MethodCall { seg, receiver, args, span: _ }) => { - try_visit!(visitor.visit_expr(receiver)); - try_visit!(visitor.visit_path_segment(seg)); - walk_list!(visitor, visit_expr, args); - } - ExprKind::Binary(_op, left_expression, right_expression) => { - try_visit!(visitor.visit_expr(left_expression)); - try_visit!(visitor.visit_expr(right_expression)); - } - ExprKind::AddrOf(_kind, _mutbl, subexpression) => { - try_visit!(visitor.visit_expr(subexpression)); - } - ExprKind::Unary(_op, subexpression) => { - try_visit!(visitor.visit_expr(subexpression)); - } - ExprKind::Cast(subexpression, typ) | ExprKind::Type(subexpression, typ) => { - try_visit!(visitor.visit_expr(subexpression)); - try_visit!(visitor.visit_ty(typ)); - } - ExprKind::Let(pat, expr, _span, _recovered) => { - try_visit!(visitor.visit_pat(pat)); - try_visit!(visitor.visit_expr(expr)); - } - ExprKind::If(head_expression, if_block, optional_else) => { - try_visit!(visitor.visit_expr(head_expression)); - try_visit!(visitor.visit_block(if_block)); - visit_opt!(visitor, visit_expr, optional_else); - } - ExprKind::While(subexpression, block, opt_label) => { - visit_opt!(visitor, visit_label, opt_label); - try_visit!(visitor.visit_expr(subexpression)); - try_visit!(visitor.visit_block(block)); - } - ExprKind::ForLoop { pat, iter, body, label, kind: _ } => { - visit_opt!(visitor, visit_label, label); - try_visit!(visitor.visit_pat(pat)); - try_visit!(visitor.visit_expr(iter)); - try_visit!(visitor.visit_block(body)); - } - ExprKind::Loop(block, opt_label, _span) => { - visit_opt!(visitor, visit_label, opt_label); - try_visit!(visitor.visit_block(block)); - } - ExprKind::Match(subexpression, arms, _kind) => { - try_visit!(visitor.visit_expr(subexpression)); - walk_list!(visitor, visit_arm, arms); - } - ExprKind::Closure(box Closure { - binder, - capture_clause, - coroutine_kind, - constness: _, - movability: _, - fn_decl, - body, - fn_decl_span: _, - fn_arg_span: _, - }) => { - try_visit!(visitor.visit_capture_by(capture_clause)); - try_visit!(visitor.visit_fn( - FnKind::Closure(binder, coroutine_kind, fn_decl, body), - *span, - *id - )); - } - ExprKind::Block(block, opt_label) => { - visit_opt!(visitor, visit_label, opt_label); - try_visit!(visitor.visit_block(block)); - } - ExprKind::Gen(_capt, body, _kind, _decl_span) => try_visit!(visitor.visit_block(body)), - ExprKind::Await(expr, _span) => try_visit!(visitor.visit_expr(expr)), - ExprKind::Use(expr, _span) => try_visit!(visitor.visit_expr(expr)), - ExprKind::Assign(lhs, rhs, _span) => { - try_visit!(visitor.visit_expr(lhs)); - try_visit!(visitor.visit_expr(rhs)); - } - ExprKind::AssignOp(_op, left_expression, right_expression) => { - try_visit!(visitor.visit_expr(left_expression)); - try_visit!(visitor.visit_expr(right_expression)); - } - ExprKind::Field(subexpression, ident) => { - try_visit!(visitor.visit_expr(subexpression)); - try_visit!(visitor.visit_ident(ident)); - } - ExprKind::Index(main_expression, index_expression, _span) => { - try_visit!(visitor.visit_expr(main_expression)); - try_visit!(visitor.visit_expr(index_expression)); - } - ExprKind::Range(start, end, _limit) => { - visit_opt!(visitor, visit_expr, start); - visit_opt!(visitor, visit_expr, end); - } - ExprKind::Underscore => {} - ExprKind::Path(maybe_qself, path) => { - try_visit!(visitor.visit_qself(maybe_qself)); - try_visit!(visitor.visit_id(*id)); - try_visit!(visitor.visit_path(path)); - } - ExprKind::Break(opt_label, opt_expr) => { - visit_opt!(visitor, visit_label, opt_label); - visit_opt!(visitor, visit_expr, opt_expr); - } - ExprKind::Continue(opt_label) => { - visit_opt!(visitor, visit_label, opt_label); - } - ExprKind::Ret(optional_expression) => { - visit_opt!(visitor, visit_expr, optional_expression); - } - ExprKind::Yeet(optional_expression) => { - visit_opt!(visitor, visit_expr, optional_expression); - } - ExprKind::Become(expr) => try_visit!(visitor.visit_expr(expr)), - ExprKind::MacCall(mac) => try_visit!(visitor.visit_mac_call(mac)), - ExprKind::Paren(subexpression) => try_visit!(visitor.visit_expr(subexpression)), - ExprKind::InlineAsm(asm) => try_visit!(visitor.visit_inline_asm(asm)), - ExprKind::FormatArgs(f) => try_visit!(visitor.visit_format_args(f)), - ExprKind::OffsetOf(container, fields) => { - try_visit!(visitor.visit_ty(container)); - walk_list!(visitor, visit_ident, fields.iter()); - } - ExprKind::Yield(kind) => { - visit_opt!(visitor, visit_expr, kind.expr()); - } - ExprKind::Try(subexpression) => try_visit!(visitor.visit_expr(subexpression)), - ExprKind::TryBlock(body) => try_visit!(visitor.visit_block(body)), - ExprKind::Lit(_token) => {} - ExprKind::IncludedBytes(_bytes) => {} - ExprKind::UnsafeBinderCast(_kind, expr, ty) => { - try_visit!(visitor.visit_expr(expr)); - visit_opt!(visitor, visit_ty, ty); - } - ExprKind::Err(_guar) => {} - ExprKind::Dummy => {} - } - - V::Result::output() -} - -pub fn walk_param<'a, V: Visitor<'a>>(visitor: &mut V, param: &'a Param) -> V::Result { - let Param { attrs, ty, pat, id: _, span: _, is_placeholder: _ } = param; - walk_list!(visitor, visit_attribute, attrs); - try_visit!(visitor.visit_pat(pat)); - try_visit!(visitor.visit_ty(ty)); - V::Result::output() -} - -pub fn walk_arm<'a, V: Visitor<'a>>(visitor: &mut V, arm: &'a Arm) -> V::Result { - let Arm { attrs, pat, guard, body, span: _, id: _, is_placeholder: _ } = arm; - walk_list!(visitor, visit_attribute, attrs); - try_visit!(visitor.visit_pat(pat)); - visit_opt!(visitor, visit_expr, guard); - visit_opt!(visitor, visit_expr, body); - V::Result::output() -} - -pub fn walk_vis<'a, V: Visitor<'a>>(visitor: &mut V, vis: &'a Visibility) -> V::Result { - let Visibility { kind, span: _, tokens: _ } = vis; - match kind { - VisibilityKind::Restricted { path, id, shorthand: _ } => { - try_visit!(visitor.visit_id(*id)); - try_visit!(visitor.visit_path(path)); - } - VisibilityKind::Public | VisibilityKind::Inherited => {} - } - V::Result::output() -} - -pub fn walk_attribute<'a, V: Visitor<'a>>(visitor: &mut V, attr: &'a Attribute) -> V::Result { - let Attribute { kind, id: _, style: _, span: _ } = attr; - match kind { - AttrKind::Normal(normal) => { - let NormalAttr { item, tokens: _ } = &**normal; - let AttrItem { unsafety: _, path, args, tokens: _ } = item; - try_visit!(visitor.visit_path(path)); - try_visit!(walk_attr_args(visitor, args)); - } - AttrKind::DocComment(_kind, _sym) => {} - } - V::Result::output() -} - -pub fn walk_attr_args<'a, V: Visitor<'a>>(visitor: &mut V, args: &'a AttrArgs) -> V::Result { - match args { - AttrArgs::Empty => {} - AttrArgs::Delimited(_args) => {} - AttrArgs::Eq { expr, .. } => try_visit!(visitor.visit_expr(expr)), - } - V::Result::output() -} diff --git a/compiler/rustc_ast_lowering/src/expr.rs b/compiler/rustc_ast_lowering/src/expr.rs index 537d4a2a6af6..718edad0cc61 100644 --- a/compiler/rustc_ast_lowering/src/expr.rs +++ b/compiler/rustc_ast_lowering/src/expr.rs @@ -73,16 +73,15 @@ impl<'hir> LoweringContext<'_, 'hir> { // Merge attributes into the inner expression. if !e.attrs.is_empty() { let old_attrs = self.attrs.get(&ex.hir_id.local_id).copied().unwrap_or(&[]); - let attrs = &*self.arena.alloc_from_iter( - self.lower_attrs_vec(&e.attrs, e.span) - .into_iter() - .chain(old_attrs.iter().cloned()), - ); - if attrs.is_empty() { + let new_attrs = self + .lower_attrs_vec(&e.attrs, e.span, ex.hir_id) + .into_iter() + .chain(old_attrs.iter().cloned()); + let new_attrs = &*self.arena.alloc_from_iter(new_attrs); + if new_attrs.is_empty() { return ex; } - - self.attrs.insert(ex.hir_id.local_id, attrs); + self.attrs.insert(ex.hir_id.local_id, new_attrs); } return ex; } @@ -2035,7 +2034,7 @@ impl<'hir> LoweringContext<'_, 'hir> { let ret_expr = self.checked_return(Some(from_residual_expr)); self.arena.alloc(self.expr(try_span, ret_expr)) }; - self.lower_attrs(ret_expr.hir_id, &attrs, ret_expr.span); + self.lower_attrs(ret_expr.hir_id, &attrs, span); let break_pat = self.pat_cf_break(try_span, residual_local); self.arm(break_pat, ret_expr) diff --git a/compiler/rustc_ast_lowering/src/item.rs b/compiler/rustc_ast_lowering/src/item.rs index d1a2ddbdb347..e2d291a536da 100644 --- a/compiler/rustc_ast_lowering/src/item.rs +++ b/compiler/rustc_ast_lowering/src/item.rs @@ -63,7 +63,7 @@ impl<'a, 'hir> ItemLowerer<'a, 'hir> { for (def_id, info) in lctx.children { let owner = self.owners.ensure_contains_elem(def_id, || hir::MaybeOwner::Phantom); - debug_assert!( + assert!( matches!(owner, hir::MaybeOwner::Phantom), "duplicate copy of {def_id:?} in lctx.children" ); @@ -78,7 +78,7 @@ impl<'a, 'hir> ItemLowerer<'a, 'hir> { match node { AstOwner::NonOwner => {} AstOwner::Crate(c) => { - debug_assert_eq!(self.resolver.node_id_to_def_id[&CRATE_NODE_ID], CRATE_DEF_ID); + assert_eq!(self.resolver.node_id_to_def_id[&CRATE_NODE_ID], CRATE_DEF_ID); self.with_lctx(CRATE_NODE_ID, |lctx| { let module = lctx.lower_mod(&c.items, &c.spans); // FIXME(jdonszelman): is dummy span ever a problem here? @@ -1160,7 +1160,7 @@ impl<'hir> LoweringContext<'_, 'hir> { ) -> hir::BodyId { let body = hir::Body { params, value: self.arena.alloc(value) }; let id = body.id(); - debug_assert_eq!(id.hir_id.owner, self.current_hir_id_owner); + assert_eq!(id.hir_id.owner, self.current_hir_id_owner); self.bodies.push((id.hir_id.local_id, self.arena.alloc(body))); id } @@ -1673,8 +1673,8 @@ impl<'hir> LoweringContext<'_, 'hir> { itctx: ImplTraitContext, f: impl FnOnce(&mut Self) -> T, ) -> (&'hir hir::Generics<'hir>, T) { - debug_assert!(self.impl_trait_defs.is_empty()); - debug_assert!(self.impl_trait_bounds.is_empty()); + assert!(self.impl_trait_defs.is_empty()); + assert!(self.impl_trait_bounds.is_empty()); // Error if `?Trait` bounds in where clauses don't refer directly to type parameters. // Note: we used to clone these bounds directly onto the type parameter (and avoid lowering diff --git a/compiler/rustc_ast_lowering/src/lib.rs b/compiler/rustc_ast_lowering/src/lib.rs index b99df8bd7e55..4f0368bcb01b 100644 --- a/compiler/rustc_ast_lowering/src/lib.rs +++ b/compiler/rustc_ast_lowering/src/lib.rs @@ -51,6 +51,7 @@ use rustc_data_structures::tagged_ptr::TaggedRef; use rustc_errors::{DiagArgFromDisplay, DiagCtxtHandle, StashKey}; use rustc_hir::def::{DefKind, LifetimeRes, Namespace, PartialRes, PerNS, Res}; use rustc_hir::def_id::{CRATE_DEF_ID, LOCAL_CRATE, LocalDefId}; +use rustc_hir::lints::DelayedLint; use rustc_hir::{ self as hir, AngleBrackets, ConstArg, GenericArg, HirId, ItemLocalMap, LangItem, LifetimeSource, LifetimeSyntax, ParamName, TraitCandidate, @@ -141,6 +142,8 @@ struct LoweringContext<'a, 'hir> { allow_for_await: Arc<[Symbol]>, allow_async_fn_traits: Arc<[Symbol]>, + delayed_lints: Vec, + attribute_parser: AttributeParser<'hir>, } @@ -190,6 +193,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { allow_async_iterator: [sym::gen_future, sym::async_iterator].into(), attribute_parser: AttributeParser::new(tcx.sess, tcx.features(), registered_tools), + delayed_lints: Vec::new(), } } @@ -198,6 +202,22 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { } } +struct SpanLowerer { + is_incremental: bool, + def_id: LocalDefId, +} + +impl SpanLowerer { + fn lower(&self, span: Span) -> Span { + if self.is_incremental { + span.with_parent(Some(self.def_id)) + } else { + // Do not make spans relative when not using incremental compilation. + span + } + } +} + #[extension(trait ResolverAstLoweringExt)] impl ResolverAstLowering { fn legacy_const_generic_args(&self, expr: &Expr) -> Option> { @@ -503,7 +523,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { span: Span, ) -> LocalDefId { let parent = self.current_hir_id_owner.def_id; - debug_assert_ne!(node_id, ast::DUMMY_NODE_ID); + assert_ne!(node_id, ast::DUMMY_NODE_ID); assert!( self.opt_local_def_id(node_id).is_none(), "adding a def'n for node-id {:?} and def kind {:?} but a previous def'n exists: {:?}", @@ -573,6 +593,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { std::mem::replace(&mut self.item_local_id_counter, hir::ItemLocalId::new(1)); let current_impl_trait_defs = std::mem::take(&mut self.impl_trait_defs); let current_impl_trait_bounds = std::mem::take(&mut self.impl_trait_bounds); + let current_delayed_lints = std::mem::take(&mut self.delayed_lints); // Do not reset `next_node_id` and `node_id_to_def_id`: // we want `f` to be able to refer to the `LocalDefId`s that the caller created. @@ -586,10 +607,10 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { } let item = f(self); - debug_assert_eq!(owner_id, item.def_id()); + assert_eq!(owner_id, item.def_id()); // `f` should have consumed all the elements in these vectors when constructing `item`. - debug_assert!(self.impl_trait_defs.is_empty()); - debug_assert!(self.impl_trait_bounds.is_empty()); + assert!(self.impl_trait_defs.is_empty()); + assert!(self.impl_trait_bounds.is_empty()); let info = self.make_owner_info(item); self.attrs = current_attrs; @@ -606,6 +627,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { self.item_local_id_counter = current_local_counter; self.impl_trait_defs = current_impl_trait_defs; self.impl_trait_bounds = current_impl_trait_bounds; + self.delayed_lints = current_delayed_lints; debug_assert!(!self.children.iter().any(|(id, _)| id == &owner_id.def_id)); self.children.push((owner_id.def_id, hir::MaybeOwner::Owner(info))); @@ -616,6 +638,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { let mut bodies = std::mem::take(&mut self.bodies); let define_opaque = std::mem::take(&mut self.define_opaque); let trait_map = std::mem::take(&mut self.trait_map); + let delayed_lints = std::mem::take(&mut self.delayed_lints).into_boxed_slice(); #[cfg(debug_assertions)] for (id, attrs) in attrs.iter() { @@ -629,14 +652,16 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { let bodies = SortedMap::from_presorted_elements(bodies); // Don't hash unless necessary, because it's expensive. - let (opt_hash_including_bodies, attrs_hash) = - self.tcx.hash_owner_nodes(node, &bodies, &attrs, define_opaque); + let (opt_hash_including_bodies, attrs_hash, delayed_lints_hash) = + self.tcx.hash_owner_nodes(node, &bodies, &attrs, &delayed_lints, define_opaque); let num_nodes = self.item_local_id_counter.as_usize(); let (nodes, parenting) = index::index_hir(self.tcx, node, &bodies, num_nodes); let nodes = hir::OwnerNodes { opt_hash_including_bodies, nodes, bodies }; let attrs = hir::AttributeMap { map: attrs, opt_hash: attrs_hash, define_opaque }; + let delayed_lints = + hir::lints::DelayedLints { lints: delayed_lints, opt_hash: delayed_lints_hash }; - self.arena.alloc(hir::OwnerInfo { nodes, parenting, attrs, trait_map }) + self.arena.alloc(hir::OwnerInfo { nodes, parenting, attrs, trait_map, delayed_lints }) } /// This method allocates a new `HirId` for the given `NodeId`. @@ -759,15 +784,17 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { }) } + fn span_lowerer(&self) -> SpanLowerer { + SpanLowerer { + is_incremental: self.tcx.sess.opts.incremental.is_some(), + def_id: self.current_hir_id_owner.def_id, + } + } + /// Intercept all spans entering HIR. /// Mark a span as relative to the current owning item. fn lower_span(&self, span: Span) -> Span { - if self.tcx.sess.opts.incremental.is_some() { - span.with_parent(Some(self.current_hir_id_owner.def_id)) - } else { - // Do not make spans relative when not using incremental compilation. - span - } + self.span_lowerer().lower(span) } fn lower_ident(&self, ident: Ident) -> Ident { @@ -889,9 +916,9 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { if attrs.is_empty() { &[] } else { - let lowered_attrs = self.lower_attrs_vec(attrs, self.lower_span(target_span)); + let lowered_attrs = self.lower_attrs_vec(attrs, self.lower_span(target_span), id); - debug_assert_eq!(id.owner, self.current_hir_id_owner); + assert_eq!(id.owner, self.current_hir_id_owner); let ret = self.arena.alloc_from_iter(lowered_attrs); // this is possible if an item contained syntactical attribute, @@ -909,16 +936,30 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { } } - fn lower_attrs_vec(&self, attrs: &[Attribute], target_span: Span) -> Vec { - self.attribute_parser - .parse_attribute_list(attrs, target_span, OmitDoc::Lower, |s| self.lower_span(s)) + fn lower_attrs_vec( + &mut self, + attrs: &[Attribute], + target_span: Span, + target_hir_id: HirId, + ) -> Vec { + let l = self.span_lowerer(); + self.attribute_parser.parse_attribute_list( + attrs, + target_span, + target_hir_id, + OmitDoc::Lower, + |s| l.lower(s), + |l| { + self.delayed_lints.push(DelayedLint::AttributeParsing(l)); + }, + ) } fn alias_attrs(&mut self, id: HirId, target_id: HirId) { - debug_assert_eq!(id.owner, self.current_hir_id_owner); - debug_assert_eq!(target_id.owner, self.current_hir_id_owner); + assert_eq!(id.owner, self.current_hir_id_owner); + assert_eq!(target_id.owner, self.current_hir_id_owner); if let Some(&a) = self.attrs.get(&target_id.local_id) { - debug_assert!(!a.is_empty()); + assert!(!a.is_empty()); self.attrs.insert(id.local_id, a); } } @@ -1397,7 +1438,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { let id = if let Some(LifetimeRes::ElidedAnchor { start, end }) = self.resolver.get_lifetime_res(t.id) { - debug_assert_eq!(start.plus(1), end); + assert_eq!(start.plus(1), end); start } else { self.next_node_id() @@ -1805,16 +1846,16 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { let res = match res { LifetimeRes::Param { param, .. } => hir::LifetimeKind::Param(param), LifetimeRes::Fresh { param, .. } => { - debug_assert_eq!(ident.name, kw::UnderscoreLifetime); + assert_eq!(ident.name, kw::UnderscoreLifetime); let param = self.local_def_id(param); hir::LifetimeKind::Param(param) } LifetimeRes::Infer => { - debug_assert_eq!(ident.name, kw::UnderscoreLifetime); + assert_eq!(ident.name, kw::UnderscoreLifetime); hir::LifetimeKind::Infer } LifetimeRes::Static { .. } => { - debug_assert!(matches!(ident.name, kw::StaticLifetime | kw::UnderscoreLifetime)); + assert!(matches!(ident.name, kw::StaticLifetime | kw::UnderscoreLifetime)); hir::LifetimeKind::Static } LifetimeRes::Error => hir::LifetimeKind::Error, @@ -2244,7 +2285,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> { ) -> hir::Stmt<'hir> { let hir_id = self.next_id(); if let Some(a) = attrs { - debug_assert!(!a.is_empty()); + assert!(!a.is_empty()); self.attrs.insert(hir_id.local_id, a); } let local = hir::LetStmt { diff --git a/compiler/rustc_ast_lowering/src/stability.rs b/compiler/rustc_ast_lowering/src/stability.rs index eb052ba1c6d7..b8fa2dd3dd62 100644 --- a/compiler/rustc_ast_lowering/src/stability.rs +++ b/compiler/rustc_ast_lowering/src/stability.rs @@ -134,5 +134,8 @@ pub fn extern_abi_stability(abi: ExternAbi) -> Result<(), UnstableAbi> { feature: sym::cmse_nonsecure_entry, explain: GateReason::Experimental, }), + ExternAbi::Custom => { + Err(UnstableAbi { abi, feature: sym::abi_custom, explain: GateReason::Experimental }) + } } } diff --git a/compiler/rustc_ast_passes/messages.ftl b/compiler/rustc_ast_passes/messages.ftl index 80754a8f65a6..9a267501230f 100644 --- a/compiler/rustc_ast_passes/messages.ftl +++ b/compiler/rustc_ast_passes/messages.ftl @@ -1,3 +1,20 @@ +ast_passes_abi_custom_coroutine = + functions with the `"custom"` ABI cannot be `{$coroutine_kind_str}` + .suggestion = remove the `{$coroutine_kind_str}` keyword from this definiton + +ast_passes_abi_custom_invalid_signature = + invalid signature for `extern "custom"` function + .note = functions with the `"custom"` ABI cannot have any parameters or return type + .suggestion = remove the parameters and return type + +ast_passes_abi_custom_safe_foreign_function = + foreign functions with the `"custom"` ABI cannot be safe + .suggestion = remove the `safe` keyword from this definition + +ast_passes_abi_custom_safe_function = + functions with the `"custom"` ABI must be unsafe + .suggestion = add the `unsafe` keyword to this definition + ast_passes_assoc_const_without_body = associated constant in `impl` without body .suggestion = provide a definition for the constant diff --git a/compiler/rustc_ast_passes/src/ast_validation.rs b/compiler/rustc_ast_passes/src/ast_validation.rs index d6fe04d2994b..018887d0e8ea 100644 --- a/compiler/rustc_ast_passes/src/ast_validation.rs +++ b/compiler/rustc_ast_passes/src/ast_validation.rs @@ -18,6 +18,7 @@ use std::mem; use std::ops::{Deref, DerefMut}; +use std::str::FromStr; use itertools::{Either, Itertools}; use rustc_abi::ExternAbi; @@ -81,6 +82,7 @@ struct AstValidator<'a> { /// Used to ban explicit safety on foreign items when the extern block is not marked as unsafe. extern_mod_safety: Option, + extern_mod_abi: Option, lint_node_id: NodeId, @@ -121,10 +123,17 @@ impl<'a> AstValidator<'a> { self.outer_trait_or_trait_impl = old; } - fn with_in_extern_mod(&mut self, extern_mod_safety: Safety, f: impl FnOnce(&mut Self)) { - let old = mem::replace(&mut self.extern_mod_safety, Some(extern_mod_safety)); + fn with_in_extern_mod( + &mut self, + extern_mod_safety: Safety, + abi: Option, + f: impl FnOnce(&mut Self), + ) { + let old_safety = mem::replace(&mut self.extern_mod_safety, Some(extern_mod_safety)); + let old_abi = mem::replace(&mut self.extern_mod_abi, abi); f(self); - self.extern_mod_safety = old; + self.extern_mod_safety = old_safety; + self.extern_mod_abi = old_abi; } fn with_tilde_const( @@ -370,6 +379,65 @@ impl<'a> AstValidator<'a> { } } + /// An `extern "custom"` function must be unsafe, and must not have any parameters or return + /// type. + fn check_custom_abi(&self, ctxt: FnCtxt, ident: &Ident, sig: &FnSig) { + let dcx = self.dcx(); + + // An `extern "custom"` function must be unsafe. + match sig.header.safety { + Safety::Unsafe(_) => { /* all good */ } + Safety::Safe(safe_span) => { + let safe_span = + self.sess.psess.source_map().span_until_non_whitespace(safe_span.to(sig.span)); + dcx.emit_err(errors::AbiCustomSafeForeignFunction { span: sig.span, safe_span }); + } + Safety::Default => match ctxt { + FnCtxt::Foreign => { /* all good */ } + FnCtxt::Free | FnCtxt::Assoc(_) => { + self.dcx().emit_err(errors::AbiCustomSafeFunction { + span: sig.span, + unsafe_span: sig.span.shrink_to_lo(), + }); + } + }, + } + + // An `extern "custom"` function cannot be `async` and/or `gen`. + if let Some(coroutine_kind) = sig.header.coroutine_kind { + let coroutine_kind_span = self + .sess + .psess + .source_map() + .span_until_non_whitespace(coroutine_kind.span().to(sig.span)); + + self.dcx().emit_err(errors::AbiCustomCoroutine { + span: sig.span, + coroutine_kind_span, + coroutine_kind_str: coroutine_kind.as_str(), + }); + } + + // An `extern "custom"` function must not have any parameters or return type. + let mut spans: Vec<_> = sig.decl.inputs.iter().map(|p| p.span).collect(); + if let FnRetTy::Ty(ref ret_ty) = sig.decl.output { + spans.push(ret_ty.span); + } + + if !spans.is_empty() { + let header_span = sig.header.span().unwrap_or(sig.span.shrink_to_lo()); + let suggestion_span = header_span.shrink_to_hi().to(sig.decl.output.span()); + let padding = if header_span.is_empty() { "" } else { " " }; + + self.dcx().emit_err(errors::AbiCustomInvalidSignature { + spans, + symbol: ident.name, + suggestion_span, + padding, + }); + } + } + /// This ensures that items can only be `unsafe` (or unmarked) outside of extern /// blocks. /// @@ -1005,7 +1073,9 @@ impl<'a> Visitor<'a> for AstValidator<'a> { if abi.is_none() { self.handle_missing_abi(*extern_span, item.id); } - self.with_in_extern_mod(*safety, |this| { + + let extern_abi = abi.and_then(|abi| ExternAbi::from_str(abi.symbol.as_str()).ok()); + self.with_in_extern_mod(*safety, extern_abi, |this| { visit::walk_item(this, item); }); self.extern_mod_span = old_item; @@ -1145,6 +1215,9 @@ impl<'a> Visitor<'a> for AstValidator<'a> { self.check_foreign_fn_bodyless(*ident, body.as_deref()); self.check_foreign_fn_headerless(sig.header); self.check_foreign_item_ascii_only(*ident); + if self.extern_mod_abi == Some(ExternAbi::Custom) { + self.check_custom_abi(FnCtxt::Foreign, ident, sig); + } } ForeignItemKind::TyAlias(box TyAlias { defaultness, @@ -1352,6 +1425,13 @@ impl<'a> Visitor<'a> for AstValidator<'a> { self.check_item_safety(span, safety); } + if let FnKind::Fn(ctxt, _, fun) = fk + && let Extern::Explicit(str_lit, _) = fun.sig.header.ext + && let Ok(ExternAbi::Custom) = ExternAbi::from_str(str_lit.symbol.as_str()) + { + self.check_custom_abi(ctxt, &fun.ident, &fun.sig); + } + self.check_c_variadic_type(fk); // Functions cannot both be `const async` or `const gen` @@ -1703,6 +1783,7 @@ pub fn check_crate( outer_impl_trait_span: None, disallow_tilde_const: Some(TildeConstReason::Item), extern_mod_safety: None, + extern_mod_abi: None, lint_node_id: CRATE_NODE_ID, is_sdylib_interface, lint_buffer: lints, diff --git a/compiler/rustc_ast_passes/src/errors.rs b/compiler/rustc_ast_passes/src/errors.rs index 6f9737e08314..c437e62f4d37 100644 --- a/compiler/rustc_ast_passes/src/errors.rs +++ b/compiler/rustc_ast_passes/src/errors.rs @@ -824,3 +824,67 @@ pub(crate) struct MissingAbi { #[suggestion(code = "extern \"\"", applicability = "has-placeholders")] pub span: Span, } + +#[derive(Diagnostic)] +#[diag(ast_passes_abi_custom_safe_foreign_function)] +pub(crate) struct AbiCustomSafeForeignFunction { + #[primary_span] + pub span: Span, + + #[suggestion( + ast_passes_suggestion, + applicability = "maybe-incorrect", + code = "", + style = "verbose" + )] + pub safe_span: Span, +} + +#[derive(Diagnostic)] +#[diag(ast_passes_abi_custom_safe_function)] +pub(crate) struct AbiCustomSafeFunction { + #[primary_span] + pub span: Span, + + #[suggestion( + ast_passes_suggestion, + applicability = "maybe-incorrect", + code = "unsafe ", + style = "verbose" + )] + pub unsafe_span: Span, +} + +#[derive(Diagnostic)] +#[diag(ast_passes_abi_custom_coroutine)] +pub(crate) struct AbiCustomCoroutine { + #[primary_span] + pub span: Span, + + #[suggestion( + ast_passes_suggestion, + applicability = "maybe-incorrect", + code = "", + style = "verbose" + )] + pub coroutine_kind_span: Span, + pub coroutine_kind_str: &'static str, +} + +#[derive(Diagnostic)] +#[diag(ast_passes_abi_custom_invalid_signature)] +#[note] +pub(crate) struct AbiCustomInvalidSignature { + #[primary_span] + pub spans: Vec, + + #[suggestion( + ast_passes_suggestion, + applicability = "maybe-incorrect", + code = "{padding}fn {symbol}()", + style = "verbose" + )] + pub suggestion_span: Span, + pub symbol: Symbol, + pub padding: &'static str, +} diff --git a/compiler/rustc_ast_passes/src/feature_gate.rs b/compiler/rustc_ast_passes/src/feature_gate.rs index 3682d25d3414..1ec56868f378 100644 --- a/compiler/rustc_ast_passes/src/feature_gate.rs +++ b/compiler/rustc_ast_passes/src/feature_gate.rs @@ -36,6 +36,16 @@ macro_rules! gate_alt { feature_err(&$visitor.sess, $name, $span, $explain).emit(); } }}; + ($visitor:expr, $has_feature:expr, $name:expr, $span:expr, $explain:expr, $notes: expr) => {{ + if !$has_feature && !$span.allows_unstable($name) { + #[allow(rustc::untranslatable_diagnostic)] // FIXME: make this translatable + let mut diag = feature_err(&$visitor.sess, $name, $span, $explain); + for note in $notes { + diag.note(*note); + } + diag.emit(); + } + }}; } /// The case involving a multispan. @@ -154,11 +164,11 @@ impl<'a> Visitor<'a> for PostExpansionVisitor<'a> { let attr_info = attr.ident().and_then(|ident| BUILTIN_ATTRIBUTE_MAP.get(&ident.name)); // Check feature gates for built-in attributes. if let Some(BuiltinAttribute { - gate: AttributeGate::Gated(_, name, descr, has_feature), + gate: AttributeGate::Gated { feature, message, check, notes, .. }, .. }) = attr_info { - gate_alt!(self, has_feature(self.features), *name, attr.span, *descr); + gate_alt!(self, check(self.features), *feature, attr.span, *message, *notes); } // Check unstable flavors of the `#[doc]` attribute. if attr.has_name(sym::doc) { diff --git a/compiler/rustc_ast_pretty/src/pprust/mod.rs b/compiler/rustc_ast_pretty/src/pprust/mod.rs index a05e2bd6a5d7..a766e2006e59 100644 --- a/compiler/rustc_ast_pretty/src/pprust/mod.rs +++ b/compiler/rustc_ast_pretty/src/pprust/mod.rs @@ -53,6 +53,18 @@ pub fn item_to_string(i: &ast::Item) -> String { State::new().item_to_string(i) } +pub fn assoc_item_to_string(i: &ast::AssocItem) -> String { + State::new().assoc_item_to_string(i) +} + +pub fn foreign_item_to_string(i: &ast::ForeignItem) -> String { + State::new().foreign_item_to_string(i) +} + +pub fn stmt_to_string(s: &ast::Stmt) -> String { + State::new().stmt_to_string(s) +} + pub fn path_to_string(p: &ast::Path) -> String { State::new().path_to_string(p) } diff --git a/compiler/rustc_ast_pretty/src/pprust/state.rs b/compiler/rustc_ast_pretty/src/pprust/state.rs index 0990c9b27eb0..3d738fa31f2b 100644 --- a/compiler/rustc_ast_pretty/src/pprust/state.rs +++ b/compiler/rustc_ast_pretty/src/pprust/state.rs @@ -1063,6 +1063,14 @@ pub trait PrintState<'a>: std::ops::Deref + std::ops::Dere Self::to_string(|s| s.print_item(i)) } + fn assoc_item_to_string(&self, i: &ast::AssocItem) -> String { + Self::to_string(|s| s.print_assoc_item(i)) + } + + fn foreign_item_to_string(&self, i: &ast::ForeignItem) -> String { + Self::to_string(|s| s.print_foreign_item(i)) + } + fn path_to_string(&self, p: &ast::Path) -> String { Self::to_string(|s| s.print_path(p, false, 0)) } diff --git a/compiler/rustc_ast_pretty/src/pprust/state/expr.rs b/compiler/rustc_ast_pretty/src/pprust/state/expr.rs index c9a7e2aebd01..ee49246a4bbf 100644 --- a/compiler/rustc_ast_pretty/src/pprust/state/expr.rs +++ b/compiler/rustc_ast_pretty/src/pprust/state/expr.rs @@ -7,8 +7,8 @@ use rustc_ast::util::classify; use rustc_ast::util::literal::escape_byte_str_symbol; use rustc_ast::util::parser::{self, ExprPrecedence, Fixity}; use rustc_ast::{ - self as ast, BlockCheckMode, FormatAlignment, FormatArgPosition, FormatArgsPiece, FormatCount, - FormatDebugHex, FormatSign, FormatTrait, YieldKind, token, + self as ast, BinOpKind, BlockCheckMode, FormatAlignment, FormatArgPosition, FormatArgsPiece, + FormatCount, FormatDebugHex, FormatSign, FormatTrait, YieldKind, token, }; use crate::pp::Breaks::Inconsistent; @@ -214,13 +214,6 @@ impl<'a> State<'a> { } fn print_expr_call(&mut self, func: &ast::Expr, args: &[P], fixup: FixupContext) { - let needs_paren = match func.kind { - // In order to call a named field, needs parens: `(self.fun)()` - // But not for an unnamed field: `self.0()` - ast::ExprKind::Field(_, name) => !name.is_numeric(), - _ => func.precedence() < ExprPrecedence::Unambiguous, - }; - // Independent of parenthesization related to precedence, we must // parenthesize `func` if this is a statement context in which without // parentheses, a statement boundary would occur inside `func` or @@ -237,8 +230,16 @@ impl<'a> State<'a> { // because the latter is valid syntax but with the incorrect meaning. // It's a match-expression followed by tuple-expression, not a function // call. - self.print_expr_cond_paren(func, needs_paren, fixup.leftmost_subexpression()); + let func_fixup = fixup.leftmost_subexpression_with_operator(true); + let needs_paren = match func.kind { + // In order to call a named field, needs parens: `(self.fun)()` + // But not for an unnamed field: `self.0()` + ast::ExprKind::Field(_, name) => !name.is_numeric(), + _ => func_fixup.precedence(func) < ExprPrecedence::Unambiguous, + }; + + self.print_expr_cond_paren(func, needs_paren, func_fixup); self.print_call_post(args) } @@ -281,9 +282,24 @@ impl<'a> State<'a> { rhs: &ast::Expr, fixup: FixupContext, ) { + let operator_can_begin_expr = match op { + | BinOpKind::Sub // -x + | BinOpKind::Mul // *x + | BinOpKind::And // &&x + | BinOpKind::Or // || x + | BinOpKind::BitAnd // &x + | BinOpKind::BitOr // |x| x + | BinOpKind::Shl // <::Type as Trait>::CONST + | BinOpKind::Lt // ::CONST + => true, + _ => false, + }; + + let left_fixup = fixup.leftmost_subexpression_with_operator(operator_can_begin_expr); + let binop_prec = op.precedence(); - let left_prec = lhs.precedence(); - let right_prec = rhs.precedence(); + let left_prec = left_fixup.precedence(lhs); + let right_prec = fixup.precedence(rhs); let (mut left_needs_paren, right_needs_paren) = match op.fixity() { Fixity::Left => (left_prec < binop_prec, right_prec <= binop_prec), @@ -312,18 +328,18 @@ impl<'a> State<'a> { _ => {} } - self.print_expr_cond_paren(lhs, left_needs_paren, fixup.leftmost_subexpression()); + self.print_expr_cond_paren(lhs, left_needs_paren, left_fixup); self.space(); self.word_space(op.as_str()); - self.print_expr_cond_paren(rhs, right_needs_paren, fixup.subsequent_subexpression()); + self.print_expr_cond_paren(rhs, right_needs_paren, fixup.rightmost_subexpression()); } fn print_expr_unary(&mut self, op: ast::UnOp, expr: &ast::Expr, fixup: FixupContext) { self.word(op.as_str()); self.print_expr_cond_paren( expr, - expr.precedence() < ExprPrecedence::Prefix, - fixup.subsequent_subexpression(), + fixup.precedence(expr) < ExprPrecedence::Prefix, + fixup.rightmost_subexpression(), ); } @@ -344,8 +360,8 @@ impl<'a> State<'a> { } self.print_expr_cond_paren( expr, - expr.precedence() < ExprPrecedence::Prefix, - fixup.subsequent_subexpression(), + fixup.precedence(expr) < ExprPrecedence::Prefix, + fixup.rightmost_subexpression(), ); } @@ -590,8 +606,8 @@ impl<'a> State<'a> { self.word_space("="); self.print_expr_cond_paren( rhs, - rhs.precedence() < ExprPrecedence::Assign, - fixup.subsequent_subexpression(), + fixup.precedence(rhs) < ExprPrecedence::Assign, + fixup.rightmost_subexpression(), ); } ast::ExprKind::AssignOp(op, lhs, rhs) => { @@ -604,8 +620,8 @@ impl<'a> State<'a> { self.word_space(op.node.as_str()); self.print_expr_cond_paren( rhs, - rhs.precedence() < ExprPrecedence::Assign, - fixup.subsequent_subexpression(), + fixup.precedence(rhs) < ExprPrecedence::Assign, + fixup.rightmost_subexpression(), ); } ast::ExprKind::Field(expr, ident) => { @@ -618,10 +634,11 @@ impl<'a> State<'a> { self.print_ident(*ident); } ast::ExprKind::Index(expr, index, _) => { + let expr_fixup = fixup.leftmost_subexpression_with_operator(true); self.print_expr_cond_paren( expr, - expr.precedence() < ExprPrecedence::Unambiguous, - fixup.leftmost_subexpression(), + expr_fixup.precedence(expr) < ExprPrecedence::Unambiguous, + expr_fixup, ); self.word("["); self.print_expr(index, FixupContext::default()); @@ -634,10 +651,11 @@ impl<'a> State<'a> { // a "normal" binop gets parenthesized. (`LOr` is the lowest-precedence binop.) let fake_prec = ExprPrecedence::LOr; if let Some(e) = start { + let start_fixup = fixup.leftmost_subexpression_with_operator(true); self.print_expr_cond_paren( e, - e.precedence() < fake_prec, - fixup.leftmost_subexpression(), + start_fixup.precedence(e) < fake_prec, + start_fixup, ); } match limits { @@ -647,8 +665,8 @@ impl<'a> State<'a> { if let Some(e) = end { self.print_expr_cond_paren( e, - e.precedence() < fake_prec, - fixup.subsequent_subexpression(), + fixup.precedence(e) < fake_prec, + fixup.rightmost_subexpression(), ); } } @@ -665,11 +683,10 @@ impl<'a> State<'a> { self.space(); self.print_expr_cond_paren( expr, - // Parenthesize if required by precedence, or in the - // case of `break 'inner: loop { break 'inner 1 } + 1` - expr.precedence() < ExprPrecedence::Jump - || (opt_label.is_none() && classify::leading_labeled_expr(expr)), - fixup.subsequent_subexpression(), + // Parenthesize `break 'inner: loop { break 'inner 1 } + 1` + // ^---------------------------------^ + opt_label.is_none() && classify::leading_labeled_expr(expr), + fixup.rightmost_subexpression(), ); } } @@ -684,11 +701,7 @@ impl<'a> State<'a> { self.word("return"); if let Some(expr) = result { self.word(" "); - self.print_expr_cond_paren( - expr, - expr.precedence() < ExprPrecedence::Jump, - fixup.subsequent_subexpression(), - ); + self.print_expr(expr, fixup.rightmost_subexpression()); } } ast::ExprKind::Yeet(result) => { @@ -697,21 +710,13 @@ impl<'a> State<'a> { self.word("yeet"); if let Some(expr) = result { self.word(" "); - self.print_expr_cond_paren( - expr, - expr.precedence() < ExprPrecedence::Jump, - fixup.subsequent_subexpression(), - ); + self.print_expr(expr, fixup.rightmost_subexpression()); } } ast::ExprKind::Become(result) => { self.word("become"); self.word(" "); - self.print_expr_cond_paren( - result, - result.precedence() < ExprPrecedence::Jump, - fixup.subsequent_subexpression(), - ); + self.print_expr(result, fixup.rightmost_subexpression()); } ast::ExprKind::InlineAsm(a) => { // FIXME: Print `builtin # asm` once macro `asm` uses `builtin_syntax`. @@ -761,11 +766,7 @@ impl<'a> State<'a> { if let Some(expr) = e { self.space(); - self.print_expr_cond_paren( - expr, - expr.precedence() < ExprPrecedence::Jump, - fixup.subsequent_subexpression(), - ); + self.print_expr(expr, fixup.rightmost_subexpression()); } } ast::ExprKind::Yield(YieldKind::Postfix(e)) => { diff --git a/compiler/rustc_ast_pretty/src/pprust/state/fixup.rs b/compiler/rustc_ast_pretty/src/pprust/state/fixup.rs index 3ef21f5cb29e..eb5ac8b78a83 100644 --- a/compiler/rustc_ast_pretty/src/pprust/state/fixup.rs +++ b/compiler/rustc_ast_pretty/src/pprust/state/fixup.rs @@ -1,5 +1,6 @@ -use rustc_ast::Expr; -use rustc_ast::util::{classify, parser}; +use rustc_ast::util::classify; +use rustc_ast::util::parser::{self, ExprPrecedence}; +use rustc_ast::{Expr, ExprKind, YieldKind}; // The default amount of fixing is minimal fixing, so all fixups are set to `false` by `Default`. // Fixups should be turned on in a targeted fashion where needed. @@ -93,6 +94,24 @@ pub(crate) struct FixupContext { /// } /// ``` parenthesize_exterior_struct_lit: bool, + + /// This is the difference between: + /// + /// ```ignore (illustrative) + /// let _ = (return) - 1; // without paren, this would return -1 + /// + /// let _ = return + 1; // no paren because '+' cannot begin expr + /// ``` + next_operator_can_begin_expr: bool, + + /// This is the difference between: + /// + /// ```ignore (illustrative) + /// let _ = 1 + return 1; // no parens if rightmost subexpression + /// + /// let _ = 1 + (return 1) + 1; // needs parens + /// ``` + next_operator_can_continue_expr: bool, } impl FixupContext { @@ -134,6 +153,8 @@ impl FixupContext { match_arm: false, leftmost_subexpression_in_match_arm: self.match_arm || self.leftmost_subexpression_in_match_arm, + next_operator_can_begin_expr: false, + next_operator_can_continue_expr: true, ..self } } @@ -148,19 +169,34 @@ impl FixupContext { leftmost_subexpression_in_stmt: false, match_arm: self.match_arm || self.leftmost_subexpression_in_match_arm, leftmost_subexpression_in_match_arm: false, + next_operator_can_begin_expr: false, + next_operator_can_continue_expr: true, ..self } } - /// Transform this fixup into the one that should apply when printing any - /// subexpression that is neither a leftmost subexpression nor surrounded in - /// delimiters. + /// Transform this fixup into the one that should apply when printing a + /// leftmost subexpression followed by punctuation that is legal as the + /// first token of an expression. + pub(crate) fn leftmost_subexpression_with_operator( + self, + next_operator_can_begin_expr: bool, + ) -> Self { + FixupContext { next_operator_can_begin_expr, ..self.leftmost_subexpression() } + } + + /// Transform this fixup into the one that should apply when printing the + /// rightmost subexpression of the current expression. /// - /// This is for any subexpression that has a different first token than the - /// current expression, and is not surrounded by a paren/bracket/brace. For - /// example the `$b` in `$a + $b` and `-$b`, but not the one in `[$b]` or - /// `$a.f($b)`. - pub(crate) fn subsequent_subexpression(self) -> Self { + /// The rightmost subexpression is any subexpression that has a different + /// first token than the current expression, but has the same last token. + /// + /// For example in `$a + $b` and `-$b`, the subexpression `$b` is a + /// rightmost subexpression. + /// + /// Not every expression has a rightmost subexpression. For example neither + /// `[$b]` nor `$a.f($b)` have one. + pub(crate) fn rightmost_subexpression(self) -> Self { FixupContext { stmt: false, leftmost_subexpression_in_stmt: false, @@ -193,6 +229,39 @@ impl FixupContext { /// "let chain". pub(crate) fn needs_par_as_let_scrutinee(self, expr: &Expr) -> bool { self.parenthesize_exterior_struct_lit && parser::contains_exterior_struct_lit(expr) - || parser::needs_par_as_let_scrutinee(expr.precedence()) + || parser::needs_par_as_let_scrutinee(self.precedence(expr)) + } + + /// Determines the effective precedence of a subexpression. Some expressions + /// have higher or lower precedence when adjacent to particular operators. + pub(crate) fn precedence(self, expr: &Expr) -> ExprPrecedence { + if self.next_operator_can_begin_expr { + // Decrease precedence of value-less jumps when followed by an + // operator that would otherwise get interpreted as beginning a + // value for the jump. + if let ExprKind::Break(..) + | ExprKind::Ret(..) + | ExprKind::Yeet(..) + | ExprKind::Yield(YieldKind::Prefix(..)) = expr.kind + { + return ExprPrecedence::Jump; + } + } + + if !self.next_operator_can_continue_expr { + // Increase precedence of expressions that extend to the end of + // current statement or group. + if let ExprKind::Break(..) + | ExprKind::Closure(..) + | ExprKind::Ret(..) + | ExprKind::Yeet(..) + | ExprKind::Yield(YieldKind::Prefix(..)) + | ExprKind::Range(None, ..) = expr.kind + { + return ExprPrecedence::Prefix; + } + } + + expr.precedence() } } diff --git a/compiler/rustc_ast_pretty/src/pprust/state/item.rs b/compiler/rustc_ast_pretty/src/pprust/state/item.rs index 3638eb31c618..6c442553976e 100644 --- a/compiler/rustc_ast_pretty/src/pprust/state/item.rs +++ b/compiler/rustc_ast_pretty/src/pprust/state/item.rs @@ -28,7 +28,7 @@ impl<'a> State<'a> { } } - fn print_foreign_item(&mut self, item: &ast::ForeignItem) { + pub(crate) fn print_foreign_item(&mut self, item: &ast::ForeignItem) { let ast::Item { id, span, ref attrs, ref kind, ref vis, tokens: _ } = *item; self.ann.pre(self, AnnNode::SubItem(id)); self.hardbreak_if_not_bol(); @@ -548,7 +548,7 @@ impl<'a> State<'a> { } } - fn print_assoc_item(&mut self, item: &ast::AssocItem) { + pub(crate) fn print_assoc_item(&mut self, item: &ast::AssocItem) { let ast::Item { id, span, ref attrs, ref kind, ref vis, tokens: _ } = *item; self.ann.pre(self, AnnNode::SubItem(id)); self.hardbreak_if_not_bol(); diff --git a/compiler/rustc_attr_data_structures/src/attributes.rs b/compiler/rustc_attr_data_structures/src/attributes.rs index d2d1285b0756..845e4d5e5d0f 100644 --- a/compiler/rustc_attr_data_structures/src/attributes.rs +++ b/compiler/rustc_attr_data_structures/src/attributes.rs @@ -57,14 +57,6 @@ impl OptimizeAttr { } } -#[derive(Clone, Debug, Encodable, Decodable, HashStable_Generic, PrintAttribute)] -pub enum DiagnosticAttribute { - // tidy-alphabetical-start - DoNotRecommend, - OnUnimplemented, - // tidy-alphabetical-end -} - #[derive(PartialEq, Debug, Encodable, Decodable, Copy, Clone, HashStable_Generic, PrintAttribute)] pub enum ReprAttr { ReprInt(IntType), @@ -160,40 +152,52 @@ impl Deprecation { #[derive(Clone, Debug, HashStable_Generic, Encodable, Decodable, PrintAttribute)] pub enum AttributeKind { // tidy-alphabetical-start + /// Represents `#[rustc_allow_const_fn_unstable]`. AllowConstFnUnstable(ThinVec), + + /// Represents `#[allow_internal_unstable]`. AllowInternalUnstable(ThinVec<(Symbol, Span)>), + + /// Represents `#[rustc_default_body_unstable]`. BodyStability { stability: DefaultBodyStability, /// Span of the `#[rustc_default_body_unstable(...)]` attribute span: Span, }, + + /// Represents `#[rustc_confusables]`. Confusables { symbols: ThinVec, // FIXME(jdonszelmann): remove when target validation code is moved first_span: Span, }, + + /// Represents `#[rustc_const_stable]` and `#[rustc_const_unstable]`. ConstStability { stability: PartialConstStability, /// Span of the `#[rustc_const_stable(...)]` or `#[rustc_const_unstable(...)]` attribute span: Span, }, + + /// Represents `#[rustc_const_stable_indirect]`. ConstStabilityIndirect, - Deprecation { - deprecation: Deprecation, - span: Span, - }, - Diagnostic(DiagnosticAttribute), - DocComment { - style: AttrStyle, - kind: CommentKind, - span: Span, - comment: Symbol, - }, + + /// Represents [`#[deprecated]`](https://doc.rust-lang.org/stable/reference/attributes/diagnostics.html#the-deprecated-attribute). + Deprecation { deprecation: Deprecation, span: Span }, + + /// Represents [`#[doc]`](https://doc.rust-lang.org/stable/rustdoc/write-documentation/the-doc-attribute.html). + DocComment { style: AttrStyle, kind: CommentKind, span: Span, comment: Symbol }, + + /// Represents `#[rustc_macro_transparency]`. MacroTransparency(Transparency), + + /// Represents [`#[repr]`](https://doc.rust-lang.org/stable/reference/type-layout.html#representations). Repr(ThinVec<(ReprAttr, Span)>), + + /// Represents `#[stable]`, `#[unstable]` and `#[rustc_allowed_through_unstable_modules]`. Stability { stability: Stability, - /// Span of the `#[stable(...)]` or `#[unstable(...)]` attribute + /// Span of the attribute. span: Span, }, // tidy-alphabetical-end diff --git a/compiler/rustc_attr_data_structures/src/lib.rs b/compiler/rustc_attr_data_structures/src/lib.rs index dbfc95b047ae..b0fc19d1cd7b 100644 --- a/compiler/rustc_attr_data_structures/src/lib.rs +++ b/compiler/rustc_attr_data_structures/src/lib.rs @@ -8,6 +8,8 @@ mod attributes; mod stability; mod version; +pub mod lints; + use std::num::NonZero; pub use attributes::*; diff --git a/compiler/rustc_attr_data_structures/src/lints.rs b/compiler/rustc_attr_data_structures/src/lints.rs new file mode 100644 index 000000000000..7e3664b2263b --- /dev/null +++ b/compiler/rustc_attr_data_structures/src/lints.rs @@ -0,0 +1,14 @@ +use rustc_macros::HashStable_Generic; +use rustc_span::Span; + +#[derive(Clone, Debug, HashStable_Generic)] +pub struct AttributeLint { + pub id: Id, + pub span: Span, + pub kind: AttributeLintKind, +} + +#[derive(Clone, Debug, HashStable_Generic)] +pub enum AttributeLintKind { + UnusedDuplicate { this: Span, other: Span, warning: bool }, +} diff --git a/compiler/rustc_attr_data_structures/src/stability.rs b/compiler/rustc_attr_data_structures/src/stability.rs index c0ca08a60f8b..218e771c745a 100644 --- a/compiler/rustc_attr_data_structures/src/stability.rs +++ b/compiler/rustc_attr_data_structures/src/stability.rs @@ -132,6 +132,7 @@ pub enum StabilityLevel { /// fn foobar() {} /// ``` implied_by: Option, + old_name: Option, }, /// `#[stable]` Stable { diff --git a/compiler/rustc_attr_parsing/messages.ftl b/compiler/rustc_attr_parsing/messages.ftl index 45174c9582d3..c9443feb021b 100644 --- a/compiler/rustc_attr_parsing/messages.ftl +++ b/compiler/rustc_attr_parsing/messages.ftl @@ -131,7 +131,15 @@ attr_parsing_unsupported_literal_generic = attr_parsing_unsupported_literal_suggestion = consider removing the prefix +attr_parsing_unused_duplicate = + unused attribute + .suggestion = remove this attribute + .note = attribute also specified here + .warn = {-passes_previously_accepted} attr_parsing_unused_multiple = multiple `{$name}` attributes .suggestion = remove this attribute .note = attribute also specified here + +-attr_parsing_perviously_accepted = + this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! diff --git a/compiler/rustc_attr_parsing/src/attributes/allow_unstable.rs b/compiler/rustc_attr_parsing/src/attributes/allow_unstable.rs index d0465546b731..81192f902a23 100644 --- a/compiler/rustc_attr_parsing/src/attributes/allow_unstable.rs +++ b/compiler/rustc_attr_parsing/src/attributes/allow_unstable.rs @@ -4,41 +4,43 @@ use rustc_attr_data_structures::AttributeKind; use rustc_span::{Span, Symbol, sym}; use super::{CombineAttributeParser, ConvertFn}; -use crate::context::AcceptContext; +use crate::context::{AcceptContext, Stage}; use crate::parser::ArgParser; use crate::session_diagnostics; pub(crate) struct AllowInternalUnstableParser; -impl CombineAttributeParser for AllowInternalUnstableParser { - const PATH: &'static [Symbol] = &[sym::allow_internal_unstable]; +impl CombineAttributeParser for AllowInternalUnstableParser { + const PATH: &[Symbol] = &[sym::allow_internal_unstable]; type Item = (Symbol, Span); const CONVERT: ConvertFn = AttributeKind::AllowInternalUnstable; - fn extend<'a>( - cx: &'a AcceptContext<'a>, - args: &'a ArgParser<'a>, - ) -> impl IntoIterator + 'a { - parse_unstable(cx, args, Self::PATH[0]).into_iter().zip(iter::repeat(cx.attr_span)) + fn extend<'c>( + cx: &'c mut AcceptContext<'_, '_, S>, + args: &'c ArgParser<'_>, + ) -> impl IntoIterator { + parse_unstable(cx, args, >::PATH[0]) + .into_iter() + .zip(iter::repeat(cx.attr_span)) } } pub(crate) struct AllowConstFnUnstableParser; -impl CombineAttributeParser for AllowConstFnUnstableParser { - const PATH: &'static [Symbol] = &[sym::rustc_allow_const_fn_unstable]; +impl CombineAttributeParser for AllowConstFnUnstableParser { + const PATH: &[Symbol] = &[sym::rustc_allow_const_fn_unstable]; type Item = Symbol; const CONVERT: ConvertFn = AttributeKind::AllowConstFnUnstable; - fn extend<'a>( - cx: &'a AcceptContext<'a>, - args: &'a ArgParser<'a>, - ) -> impl IntoIterator + 'a { - parse_unstable(cx, args, Self::PATH[0]) + fn extend<'c>( + cx: &'c mut AcceptContext<'_, '_, S>, + args: &'c ArgParser<'_>, + ) -> impl IntoIterator + 'c { + parse_unstable(cx, args, >::PATH[0]) } } -fn parse_unstable<'a>( - cx: &AcceptContext<'_>, - args: &'a ArgParser<'a>, +fn parse_unstable( + cx: &AcceptContext<'_, '_, S>, + args: &ArgParser<'_>, symbol: Symbol, ) -> impl IntoIterator { let mut res = Vec::new(); diff --git a/compiler/rustc_attr_parsing/src/attributes/confusables.rs b/compiler/rustc_attr_parsing/src/attributes/confusables.rs index 6cff952fcf22..afd3c012f05a 100644 --- a/compiler/rustc_attr_parsing/src/attributes/confusables.rs +++ b/compiler/rustc_attr_parsing/src/attributes/confusables.rs @@ -3,7 +3,7 @@ use rustc_span::{Span, Symbol, sym}; use thin_vec::ThinVec; use super::{AcceptMapping, AttributeParser}; -use crate::context::FinalizeContext; +use crate::context::{FinalizeContext, Stage}; use crate::session_diagnostics; #[derive(Default)] @@ -12,8 +12,8 @@ pub(crate) struct ConfusablesParser { first_span: Option, } -impl AttributeParser for ConfusablesParser { - const ATTRIBUTES: AcceptMapping = &[(&[sym::rustc_confusables], |this, cx, args| { +impl AttributeParser for ConfusablesParser { + const ATTRIBUTES: AcceptMapping = &[(&[sym::rustc_confusables], |this, cx, args| { let Some(list) = args.list() else { // FIXME(jdonszelmann): error when not a list? Bring validation code here. // NOTE: currently subsequent attributes are silently ignored using @@ -45,7 +45,7 @@ impl AttributeParser for ConfusablesParser { this.first_span.get_or_insert(cx.attr_span); })]; - fn finalize(self, _cx: &FinalizeContext<'_>) -> Option { + fn finalize(self, _cx: &FinalizeContext<'_, '_, S>) -> Option { if self.confusables.is_empty() { return None; } diff --git a/compiler/rustc_attr_parsing/src/attributes/deprecation.rs b/compiler/rustc_attr_parsing/src/attributes/deprecation.rs index 006c1fe3b9c9..1faee41c2a9d 100644 --- a/compiler/rustc_attr_parsing/src/attributes/deprecation.rs +++ b/compiler/rustc_attr_parsing/src/attributes/deprecation.rs @@ -1,17 +1,17 @@ use rustc_attr_data_structures::{AttributeKind, DeprecatedSince, Deprecation}; use rustc_span::{Span, Symbol, sym}; -use super::SingleAttributeParser; use super::util::parse_version; -use crate::context::AcceptContext; +use super::{AttributeOrder, OnDuplicate, SingleAttributeParser}; +use crate::context::{AcceptContext, Stage}; use crate::parser::ArgParser; use crate::session_diagnostics; use crate::session_diagnostics::UnsupportedLiteralReason; pub(crate) struct DeprecationParser; -fn get( - cx: &AcceptContext<'_>, +fn get( + cx: &AcceptContext<'_, '_, S>, name: Symbol, param_span: Span, arg: &ArgParser<'_>, @@ -41,19 +41,12 @@ fn get( } } -impl SingleAttributeParser for DeprecationParser { - const PATH: &'static [Symbol] = &[sym::deprecated]; +impl SingleAttributeParser for DeprecationParser { + const PATH: &[Symbol] = &[sym::deprecated]; + const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepFirst; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::Error; - fn on_duplicate(cx: &AcceptContext<'_>, first_span: Span) { - // FIXME(jdonszelmann): merge with errors from check_attrs.rs - cx.emit_err(session_diagnostics::UnusedMultiple { - this: cx.attr_span, - other: first_span, - name: sym::deprecated, - }); - } - - fn convert(cx: &AcceptContext<'_>, args: &ArgParser<'_>) -> Option { + fn convert(cx: &mut AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option { let features = cx.features(); let mut since = None; diff --git a/compiler/rustc_attr_parsing/src/attributes/inline.rs b/compiler/rustc_attr_parsing/src/attributes/inline.rs new file mode 100644 index 000000000000..c7f82082c2ee --- /dev/null +++ b/compiler/rustc_attr_parsing/src/attributes/inline.rs @@ -0,0 +1,97 @@ +// FIXME(jdonszelmann): merge these two parsers and error when both attributes are present here. +// note: need to model better how duplicate attr errors work when not using +// SingleAttributeParser which is what we have two of here. + +use rustc_attr_data_structures::lints::AttributeLintKind; +use rustc_attr_data_structures::{AttributeKind, InlineAttr}; +use rustc_feature::{AttributeTemplate, template}; +use rustc_span::{Symbol, sym}; + +use super::{AcceptContext, AttributeOrder, OnDuplicate}; +use crate::attributes::SingleAttributeParser; +use crate::context::Stage; +use crate::parser::ArgParser; + +pub(crate) struct InlineParser; + +impl SingleAttributeParser for InlineParser { + const PATH: &'static [Symbol] = &[sym::inline]; + const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepLast; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::WarnButFutureError; + const TEMPLATE: AttributeTemplate = template!(Word, List: "always|never"); + + fn convert(cx: &mut AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option { + match args { + ArgParser::NoArgs => Some(AttributeKind::Inline(InlineAttr::Hint, cx.attr_span)), + ArgParser::List(list) => { + let Some(l) = list.single() else { + cx.expected_single_argument(list.span); + return None; + }; + + match l.meta_item().and_then(|i| i.word_without_args().map(|i| i.name)) { + Some(sym::always) => { + Some(AttributeKind::Inline(InlineAttr::Always, cx.attr_span)) + } + Some(sym::never) => { + Some(AttributeKind::Inline(InlineAttr::Never, cx.attr_span)) + } + _ => { + cx.expected_specific_argument(l.span(), vec!["always", "never"]); + return None; + } + } + } + ArgParser::NameValue(_) => { + let suggestions = + >::TEMPLATE.suggestions(false, "inline"); + cx.emit_lint( + AttributeLintKind::IllFormedAttributeInput { suggestions }, + cx.attr_span, + ); + return None; + } + } + } +} + +pub(crate) struct RustcForceInlineParser; + +impl SingleAttributeParser for RustcForceInlineParser { + const PATH: &'static [Symbol] = &[sym::rustc_force_inline]; + const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepLast; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::WarnButFutureError; + const TEMPLATE: AttributeTemplate = template!(Word, List: "reason", NameValueStr: "reason"); + + fn convert(cx: &AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option { + let reason = match args { + ArgParser::NoArgs => None, + ArgParser::List(list) => { + let Some(l) = list.single() else { + cx.expected_single_argument(list.span); + return None; + }; + + let Some(reason) = l.lit().and_then(|i| i.kind.str()) else { + cx.expected_string_literal(l.span()); + return None; + }; + + Some(reason) + } + ArgParser::NameValue(v) => { + let Some(reason) = v.value_as_str() else { + cx.expected_string_literal(v.value_span); + return None; + }; + + Some(reason) + } + }; + + Some(AttributeKind::Inline( + InlineAttr::Force { attr_span: cx.attr_span, reason }, + cx.attr_span, + )) + } +} diff --git a/compiler/rustc_attr_parsing/src/attributes/mod.rs b/compiler/rustc_attr_parsing/src/attributes/mod.rs index bf18e10e19fd..caf55e6685ef 100644 --- a/compiler/rustc_attr_parsing/src/attributes/mod.rs +++ b/compiler/rustc_attr_parsing/src/attributes/mod.rs @@ -12,16 +12,18 @@ //! - [`CombineAttributeParser`]: makes it easy to implement an attribute which should combine the //! contents of attributes, if an attribute appear multiple times in a list //! -//! Attributes should be added to [`ATTRIBUTE_MAPPING`](crate::context::ATTRIBUTE_MAPPING) to be parsed. +//! Attributes should be added to `crate::context::ATTRIBUTE_PARSERS` to be parsed. use std::marker::PhantomData; use rustc_attr_data_structures::AttributeKind; +use rustc_attr_data_structures::lints::AttributeLintKind; use rustc_span::{Span, Symbol}; use thin_vec::ThinVec; -use crate::context::{AcceptContext, FinalizeContext}; +use crate::context::{AcceptContext, FinalizeContext, Stage}; use crate::parser::ArgParser; +use crate::session_diagnostics::UnusedMultiple; pub(crate) mod allow_unstable; pub(crate) mod cfg; @@ -32,8 +34,8 @@ pub(crate) mod stability; pub(crate) mod transparency; pub(crate) mod util; -type AcceptFn = fn(&mut T, &AcceptContext<'_>, &ArgParser<'_>); -type AcceptMapping = &'static [(&'static [Symbol], AcceptFn)]; +type AcceptFn = for<'sess> fn(&mut T, &mut AcceptContext<'_, 'sess, S>, &ArgParser<'_>); +type AcceptMapping = &'static [(&'static [Symbol], AcceptFn)]; /// An [`AttributeParser`] is a type which searches for syntactic attributes. /// @@ -51,15 +53,24 @@ type AcceptMapping = &'static [(&'static [Symbol], AcceptFn)]; /// whether it has seen the attribute it has been looking for. /// /// The state machine is automatically reset to parse attributes on the next item. -pub(crate) trait AttributeParser: Default + 'static { +/// +/// For a simpler attribute parsing interface, consider using [`SingleAttributeParser`] +/// or [`CombineAttributeParser`] instead. +pub(crate) trait AttributeParser: Default + 'static { /// The symbols for the attributes that this parser is interested in. /// /// If an attribute has this symbol, the `accept` function will be called on it. - const ATTRIBUTES: AcceptMapping; + const ATTRIBUTES: AcceptMapping; /// The parser has gotten a chance to accept the attributes on an item, /// here it can produce an attribute. - fn finalize(self, cx: &FinalizeContext<'_>) -> Option; + /// + /// All finalize methods of all parsers are unconditionally called. + /// This means you can't unconditionally return `Some` here, + /// that'd be equivalent to unconditionally applying an attribute to + /// every single syntax item that could have attributes applied to it. + /// Your accept mappings should determine whether this returns something. + fn finalize(self, cx: &FinalizeContext<'_, '_, S>) -> Option; } /// Alternative to [`AttributeParser`] that automatically handles state management. @@ -71,44 +82,131 @@ pub(crate) trait AttributeParser: Default + 'static { /// /// [`SingleAttributeParser`] can only convert attributes one-to-one, and cannot combine multiple /// attributes together like is necessary for `#[stable()]` and `#[unstable()]` for example. -pub(crate) trait SingleAttributeParser: 'static { - const PATH: &'static [Symbol]; - - /// Called when a duplicate attribute is found. - /// - /// `first_span` is the span of the first occurrence of this attribute. - // FIXME(jdonszelmann): default error - fn on_duplicate(cx: &AcceptContext<'_>, first_span: Span); +pub(crate) trait SingleAttributeParser: 'static { + const PATH: &[Symbol]; + const ATTRIBUTE_ORDER: AttributeOrder; + const ON_DUPLICATE: OnDuplicate; /// Converts a single syntactical attribute to a single semantic attribute, or [`AttributeKind`] - fn convert(cx: &AcceptContext<'_>, args: &ArgParser<'_>) -> Option; + fn convert(cx: &mut AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option; } -pub(crate) struct Single(PhantomData, Option<(AttributeKind, Span)>); +pub(crate) struct Single, S: Stage>( + PhantomData<(S, T)>, + Option<(AttributeKind, Span)>, +); -impl Default for Single { +impl, S: Stage> Default for Single { fn default() -> Self { Self(Default::default(), Default::default()) } } -impl AttributeParser for Single { - const ATTRIBUTES: AcceptMapping = &[(T::PATH, |group: &mut Single, cx, args| { - if let Some((_, s)) = group.1 { - T::on_duplicate(cx, s); - return; - } +impl, S: Stage> AttributeParser for Single { + const ATTRIBUTES: AcceptMapping = + &[(T::PATH, |group: &mut Single, cx, args| { + if let Some(pa) = T::convert(cx, args) { + match T::ATTRIBUTE_ORDER { + // keep the first and report immediately. ignore this attribute + AttributeOrder::KeepFirst => { + if let Some((_, unused)) = group.1 { + T::ON_DUPLICATE.exec::(cx, cx.attr_span, unused); + return; + } + } + // keep the new one and warn about the previous, + // then replace + AttributeOrder::KeepLast => { + if let Some((_, used)) = group.1 { + T::ON_DUPLICATE.exec::(cx, used, cx.attr_span); + } + } + } - if let Some(pa) = T::convert(cx, args) { - group.1 = Some((pa, cx.attr_span)); - } - })]; + group.1 = Some((pa, cx.attr_span)); + } + })]; - fn finalize(self, _cx: &FinalizeContext<'_>) -> Option { + fn finalize(self, _cx: &FinalizeContext<'_, '_, S>) -> Option { Some(self.1?.0) } } +// FIXME(jdonszelmann): logic is implemented but the attribute parsers needing +// them will be merged in another PR +#[allow(unused)] +pub(crate) enum OnDuplicate { + /// Give a default warning + Warn, + + /// Duplicates will be a warning, with a note that this will be an error in the future. + WarnButFutureError, + + /// Give a default error + Error, + + /// Ignore duplicates + Ignore, + + /// Custom function called when a duplicate attribute is found. + /// + /// - `unused` is the span of the attribute that was unused or bad because of some + /// duplicate reason (see [`AttributeOrder`]) + /// - `used` is the span of the attribute that was used in favor of the unused attribute + Custom(fn(cx: &AcceptContext<'_, '_, S>, used: Span, unused: Span)), +} + +impl OnDuplicate { + fn exec>( + &self, + cx: &mut AcceptContext<'_, '_, S>, + used: Span, + unused: Span, + ) { + match self { + OnDuplicate::Warn => cx.emit_lint( + AttributeLintKind::UnusedDuplicate { this: unused, other: used, warning: false }, + unused, + ), + OnDuplicate::WarnButFutureError => cx.emit_lint( + AttributeLintKind::UnusedDuplicate { this: unused, other: used, warning: true }, + unused, + ), + OnDuplicate::Error => { + cx.emit_err(UnusedMultiple { + this: used, + other: unused, + name: Symbol::intern( + &P::PATH.into_iter().map(|i| i.to_string()).collect::>().join(".."), + ), + }); + } + OnDuplicate::Ignore => {} + OnDuplicate::Custom(f) => f(cx, used, unused), + } + } +} +// +// FIXME(jdonszelmann): logic is implemented but the attribute parsers needing +// them will be merged in another PR +#[allow(unused)] +pub(crate) enum AttributeOrder { + /// Duplicates after the first attribute will be an error. + /// + /// This should be used where duplicates would be ignored, but carry extra + /// meaning that could cause confusion. For example, `#[stable(since="1.0")] + /// #[stable(since="2.0")]`, which version should be used for `stable`? + KeepFirst, + + /// Duplicates preceding the last instance of the attribute will be a + /// warning, with a note that this will be an error in the future. + /// + /// This is the same as `FutureWarnFollowing`, except the last attribute is + /// the one that is "used". Ideally these can eventually migrate to + /// `ErrorPreceding`. + KeepLast, +} + type ConvertFn = fn(ThinVec) -> AttributeKind; /// Alternative to [`AttributeParser`] that automatically handles state management. @@ -118,35 +216,35 @@ type ConvertFn = fn(ThinVec) -> AttributeKind; /// /// [`CombineAttributeParser`] can only convert a single kind of attribute, and cannot combine multiple /// attributes together like is necessary for `#[stable()]` and `#[unstable()]` for example. -pub(crate) trait CombineAttributeParser: 'static { - const PATH: &'static [Symbol]; +pub(crate) trait CombineAttributeParser: 'static { + const PATH: &[rustc_span::Symbol]; type Item; const CONVERT: ConvertFn; /// Converts a single syntactical attribute to a number of elements of the semantic attribute, or [`AttributeKind`] - fn extend<'a>( - cx: &'a AcceptContext<'a>, - args: &'a ArgParser<'a>, - ) -> impl IntoIterator + 'a; + fn extend<'c>( + cx: &'c mut AcceptContext<'_, '_, S>, + args: &'c ArgParser<'_>, + ) -> impl IntoIterator + 'c; } -pub(crate) struct Combine( - PhantomData, - ThinVec<::Item>, +pub(crate) struct Combine, S: Stage>( + PhantomData<(S, T)>, + ThinVec<>::Item>, ); -impl Default for Combine { +impl, S: Stage> Default for Combine { fn default() -> Self { Self(Default::default(), Default::default()) } } -impl AttributeParser for Combine { - const ATTRIBUTES: AcceptMapping = - &[(T::PATH, |group: &mut Combine, cx, args| group.1.extend(T::extend(cx, args)))]; +impl, S: Stage> AttributeParser for Combine { + const ATTRIBUTES: AcceptMapping = + &[(T::PATH, |group: &mut Combine, cx, args| group.1.extend(T::extend(cx, args)))]; - fn finalize(self, _cx: &FinalizeContext<'_>) -> Option { + fn finalize(self, _cx: &FinalizeContext<'_, '_, S>) -> Option { if self.1.is_empty() { None } else { Some(T::CONVERT(self.1)) } } } diff --git a/compiler/rustc_attr_parsing/src/attributes/repr.rs b/compiler/rustc_attr_parsing/src/attributes/repr.rs index 69316541e191..753b2366b410 100644 --- a/compiler/rustc_attr_parsing/src/attributes/repr.rs +++ b/compiler/rustc_attr_parsing/src/attributes/repr.rs @@ -4,7 +4,7 @@ use rustc_attr_data_structures::{AttributeKind, IntType, ReprAttr}; use rustc_span::{DUMMY_SP, Span, Symbol, sym}; use super::{CombineAttributeParser, ConvertFn}; -use crate::context::AcceptContext; +use crate::context::{AcceptContext, Stage}; use crate::parser::{ArgParser, MetaItemListParser, MetaItemParser}; use crate::session_diagnostics; use crate::session_diagnostics::IncorrectReprFormatGenericCause; @@ -19,15 +19,15 @@ use crate::session_diagnostics::IncorrectReprFormatGenericCause; // FIXME(jdonszelmann): is a vec the right representation here even? isn't it just a struct? pub(crate) struct ReprParser; -impl CombineAttributeParser for ReprParser { +impl CombineAttributeParser for ReprParser { type Item = (ReprAttr, Span); - const PATH: &'static [Symbol] = &[sym::repr]; + const PATH: &[Symbol] = &[sym::repr]; const CONVERT: ConvertFn = AttributeKind::Repr; - fn extend<'a>( - cx: &'a AcceptContext<'a>, - args: &'a ArgParser<'a>, - ) -> impl IntoIterator + 'a { + fn extend<'c>( + cx: &'c mut AcceptContext<'_, '_, S>, + args: &'c ArgParser<'_>, + ) -> impl IntoIterator + 'c { let mut reprs = Vec::new(); let Some(list) = args.list() else { @@ -91,7 +91,10 @@ fn int_type_of_word(s: Symbol) -> Option { } } -fn parse_repr(cx: &AcceptContext<'_>, param: &MetaItemParser<'_>) -> Option { +fn parse_repr( + cx: &AcceptContext<'_, '_, S>, + param: &MetaItemParser<'_>, +) -> Option { use ReprAttr::*; // FIXME(jdonszelmann): invert the parsing here to match on the word first and then the @@ -180,8 +183,8 @@ enum AlignKind { Align, } -fn parse_repr_align( - cx: &AcceptContext<'_>, +fn parse_repr_align( + cx: &AcceptContext<'_, '_, S>, list: &MetaItemListParser<'_>, param_span: Span, align_kind: AlignKind, diff --git a/compiler/rustc_attr_parsing/src/attributes/stability.rs b/compiler/rustc_attr_parsing/src/attributes/stability.rs index ce69a54513d2..6589a51db2b4 100644 --- a/compiler/rustc_attr_parsing/src/attributes/stability.rs +++ b/compiler/rustc_attr_parsing/src/attributes/stability.rs @@ -8,8 +8,8 @@ use rustc_errors::ErrorGuaranteed; use rustc_span::{Span, Symbol, sym}; use super::util::parse_version; -use super::{AcceptMapping, AttributeParser, SingleAttributeParser}; -use crate::context::{AcceptContext, FinalizeContext}; +use super::{AcceptMapping, AttributeOrder, AttributeParser, OnDuplicate, SingleAttributeParser}; +use crate::context::{AcceptContext, FinalizeContext, Stage}; use crate::parser::{ArgParser, MetaItemParser}; use crate::session_diagnostics::{self, UnsupportedLiteralReason}; @@ -31,7 +31,7 @@ pub(crate) struct StabilityParser { impl StabilityParser { /// Checks, and emits an error when a stability (or unstability) was already set, which would be a duplicate. - fn check_duplicate(&self, cx: &AcceptContext<'_>) -> bool { + fn check_duplicate(&self, cx: &AcceptContext<'_, '_, S>) -> bool { if let Some((_, _)) = self.stability { cx.emit_err(session_diagnostics::MultipleStabilityLevels { span: cx.attr_span }); true @@ -41,8 +41,8 @@ impl StabilityParser { } } -impl AttributeParser for StabilityParser { - const ATTRIBUTES: AcceptMapping = &[ +impl AttributeParser for StabilityParser { + const ATTRIBUTES: AcceptMapping = &[ (&[sym::stable], |this, cx, args| { reject_outside_std!(cx); if !this.check_duplicate(cx) @@ -65,7 +65,7 @@ impl AttributeParser for StabilityParser { }), ]; - fn finalize(mut self, cx: &FinalizeContext<'_>) -> Option { + fn finalize(mut self, cx: &FinalizeContext<'_, '_, S>) -> Option { if let Some(atum) = self.allowed_through_unstable_modules { if let Some(( Stability { @@ -95,8 +95,8 @@ pub(crate) struct BodyStabilityParser { stability: Option<(DefaultBodyStability, Span)>, } -impl AttributeParser for BodyStabilityParser { - const ATTRIBUTES: AcceptMapping = +impl AttributeParser for BodyStabilityParser { + const ATTRIBUTES: AcceptMapping = &[(&[sym::rustc_default_body_unstable], |this, cx, args| { reject_outside_std!(cx); if this.stability.is_some() { @@ -107,7 +107,7 @@ impl AttributeParser for BodyStabilityParser { } })]; - fn finalize(self, _cx: &FinalizeContext<'_>) -> Option { + fn finalize(self, _cx: &FinalizeContext<'_, '_, S>) -> Option { let (stability, span) = self.stability?; Some(AttributeKind::BodyStability { stability, span }) @@ -116,13 +116,12 @@ impl AttributeParser for BodyStabilityParser { pub(crate) struct ConstStabilityIndirectParser; // FIXME(jdonszelmann): single word attribute group when we have these -impl SingleAttributeParser for ConstStabilityIndirectParser { - const PATH: &'static [Symbol] = &[sym::rustc_const_stable_indirect]; +impl SingleAttributeParser for ConstStabilityIndirectParser { + const PATH: &[Symbol] = &[sym::rustc_const_stable_indirect]; + const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepFirst; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::Ignore; - // ignore - fn on_duplicate(_cx: &AcceptContext<'_>, _first_span: Span) {} - - fn convert(_cx: &AcceptContext<'_>, _args: &ArgParser<'_>) -> Option { + fn convert(_cx: &mut AcceptContext<'_, '_, S>, _args: &ArgParser<'_>) -> Option { Some(AttributeKind::ConstStabilityIndirect) } } @@ -135,7 +134,7 @@ pub(crate) struct ConstStabilityParser { impl ConstStabilityParser { /// Checks, and emits an error when a stability (or unstability) was already set, which would be a duplicate. - fn check_duplicate(&self, cx: &AcceptContext<'_>) -> bool { + fn check_duplicate(&self, cx: &AcceptContext<'_, '_, S>) -> bool { if let Some((_, _)) = self.stability { cx.emit_err(session_diagnostics::MultipleStabilityLevels { span: cx.attr_span }); true @@ -145,8 +144,8 @@ impl ConstStabilityParser { } } -impl AttributeParser for ConstStabilityParser { - const ATTRIBUTES: AcceptMapping = &[ +impl AttributeParser for ConstStabilityParser { + const ATTRIBUTES: AcceptMapping = &[ (&[sym::rustc_const_stable], |this, cx, args| { reject_outside_std!(cx); @@ -176,7 +175,7 @@ impl AttributeParser for ConstStabilityParser { }), ]; - fn finalize(mut self, cx: &FinalizeContext<'_>) -> Option { + fn finalize(mut self, cx: &FinalizeContext<'_, '_, S>) -> Option { if self.promotable { if let Some((ref mut stab, _)) = self.stability { stab.promotable = true; @@ -196,8 +195,8 @@ impl AttributeParser for ConstStabilityParser { /// /// Emits an error when either the option was already Some, or the arguments weren't of form /// `name = value` -fn insert_value_into_option_or_error( - cx: &AcceptContext<'_>, +fn insert_value_into_option_or_error( + cx: &AcceptContext<'_, '_, S>, param: &MetaItemParser<'_>, item: &mut Option, ) -> Option<()> { @@ -223,8 +222,8 @@ fn insert_value_into_option_or_error( /// Read the content of a `stable`/`rustc_const_stable` attribute, and return the feature name and /// its stability information. -pub(crate) fn parse_stability( - cx: &AcceptContext<'_>, +pub(crate) fn parse_stability( + cx: &AcceptContext<'_, '_, S>, args: &ArgParser<'_>, ) -> Option<(Symbol, StabilityLevel)> { let mut feature = None; @@ -289,8 +288,8 @@ pub(crate) fn parse_stability( // Read the content of a `unstable`/`rustc_const_unstable`/`rustc_default_body_unstable` /// attribute, and return the feature name and its stability information. -pub(crate) fn parse_unstability( - cx: &AcceptContext<'_>, +pub(crate) fn parse_unstability( + cx: &AcceptContext<'_, '_, S>, args: &ArgParser<'_>, ) -> Option<(Symbol, StabilityLevel)> { let mut feature = None; @@ -299,6 +298,7 @@ pub(crate) fn parse_unstability( let mut issue_num = None; let mut is_soft = false; let mut implied_by = None; + let mut old_name = None; for param in args.list()?.mixed() { let Some(param) = param.meta_item() else { cx.emit_err(session_diagnostics::UnsupportedLiteral { @@ -346,11 +346,12 @@ pub(crate) fn parse_unstability( Some(sym::implied_by) => { insert_value_into_option_or_error(cx, ¶m, &mut implied_by)? } + Some(sym::old_name) => insert_value_into_option_or_error(cx, ¶m, &mut old_name)?, _ => { cx.emit_err(session_diagnostics::UnknownMetaItem { span: param.span(), item: param.path().to_string(), - expected: &["feature", "reason", "issue", "soft", "implied_by"], + expected: &["feature", "reason", "issue", "soft", "implied_by", "old_name"], }); return None; } @@ -375,6 +376,7 @@ pub(crate) fn parse_unstability( issue: issue_num, is_soft, implied_by, + old_name, }; Some((feature, level)) } diff --git a/compiler/rustc_attr_parsing/src/attributes/transparency.rs b/compiler/rustc_attr_parsing/src/attributes/transparency.rs index d229fc097401..16ad9d03e500 100644 --- a/compiler/rustc_attr_parsing/src/attributes/transparency.rs +++ b/compiler/rustc_attr_parsing/src/attributes/transparency.rs @@ -1,8 +1,9 @@ use rustc_attr_data_structures::AttributeKind; use rustc_span::hygiene::Transparency; -use rustc_span::{Span, Symbol, sym}; +use rustc_span::{Symbol, sym}; -use super::{AcceptContext, SingleAttributeParser}; +use super::{AttributeOrder, OnDuplicate, SingleAttributeParser}; +use crate::context::{AcceptContext, Stage}; use crate::parser::ArgParser; pub(crate) struct TransparencyParser; @@ -10,14 +11,14 @@ pub(crate) struct TransparencyParser; // FIXME(jdonszelmann): make these proper diagnostics #[allow(rustc::untranslatable_diagnostic)] #[allow(rustc::diagnostic_outside_of_impl)] -impl SingleAttributeParser for TransparencyParser { - const PATH: &'static [Symbol] = &[sym::rustc_macro_transparency]; +impl SingleAttributeParser for TransparencyParser { + const PATH: &[Symbol] = &[sym::rustc_macro_transparency]; + const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepFirst; + const ON_DUPLICATE: OnDuplicate = OnDuplicate::Custom(|cx, used, unused| { + cx.dcx().span_err(vec![used, unused], "multiple macro transparency attributes"); + }); - fn on_duplicate(cx: &crate::context::AcceptContext<'_>, first_span: Span) { - cx.dcx().span_err(vec![first_span, cx.attr_span], "multiple macro transparency attributes"); - } - - fn convert(cx: &AcceptContext<'_>, args: &ArgParser<'_>) -> Option { + fn convert(cx: &mut AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option { match args.name_value().and_then(|nv| nv.value_as_str()) { Some(sym::transparent) => Some(Transparency::Transparent), Some(sym::semiopaque | sym::semitransparent) => Some(Transparency::SemiOpaque), diff --git a/compiler/rustc_attr_parsing/src/context.rs b/compiler/rustc_attr_parsing/src/context.rs index c02760d830c2..47f72232828e 100644 --- a/compiler/rustc_attr_parsing/src/context.rs +++ b/compiler/rustc_attr_parsing/src/context.rs @@ -1,13 +1,17 @@ use std::cell::RefCell; use std::collections::BTreeMap; -use std::ops::Deref; +use std::marker::PhantomData; +use std::ops::{Deref, DerefMut}; use std::sync::LazyLock; +use private::Sealed; use rustc_ast as ast; +use rustc_ast::NodeId; use rustc_attr_data_structures::AttributeKind; +use rustc_attr_data_structures::lints::{AttributeLint, AttributeLintKind}; use rustc_errors::{DiagCtxtHandle, Diagnostic}; use rustc_feature::Features; -use rustc_hir::{AttrArgs, AttrItem, AttrPath, Attribute, HashIgnoredAttrId}; +use rustc_hir::{AttrArgs, AttrItem, AttrPath, Attribute, HashIgnoredAttrId, HirId}; use rustc_session::Session; use rustc_span::{DUMMY_SP, ErrorGuaranteed, Span, Symbol, sym}; @@ -22,20 +26,40 @@ use crate::attributes::transparency::TransparencyParser; use crate::attributes::{AttributeParser as _, Combine, Single}; use crate::parser::{ArgParser, MetaItemParser}; -macro_rules! attribute_groups { +macro_rules! group_type { + ($stage: ty) => { + LazyLock<( + BTreeMap<&'static [Symbol], Box Fn(&mut AcceptContext<'_, 'sess, $stage>, &ArgParser<'a>) + Send + Sync>>, + Vec) -> Option>> + )> + }; +} + +macro_rules! attribute_parsers { ( pub(crate) static $name: ident = [$($names: ty),* $(,)?]; ) => { - type Accepts = BTreeMap< - &'static [Symbol], - Box, &ArgParser<'_>)> - >; - type Finalizes = Vec< - Box) -> Option> - >; - pub(crate) static $name: LazyLock<(Accepts, Finalizes)> = LazyLock::new(|| { - let mut accepts = Accepts::new(); - let mut finalizes = Finalizes::new(); + mod early { + use super::*; + type Combine = super::Combine; + type Single = super::Single; + + attribute_parsers!(@[Early] pub(crate) static $name = [$($names),*];); + } + mod late { + use super::*; + type Combine = super::Combine; + type Single = super::Single; + + attribute_parsers!(@[Late] pub(crate) static $name = [$($names),*];); + } + }; + ( + @[$ty: ty] pub(crate) static $name: ident = [$($names: ty),* $(,)?]; + ) => { + pub(crate) static $name: group_type!($ty) = LazyLock::new(|| { + let mut accepts = BTreeMap::<_, Box Fn(&mut AcceptContext<'_, 'sess, $ty>, &ArgParser<'a>) + Send + Sync>>::new(); + let mut finalizes = Vec::) -> Option>>::new(); $( { thread_local! { @@ -62,9 +86,8 @@ macro_rules! attribute_groups { }); }; } - -attribute_groups!( - pub(crate) static ATTRIBUTE_MAPPING = [ +attribute_parsers!( + pub(crate) static ATTRIBUTE_PARSERS = [ // tidy-alphabetical-start BodyStabilityParser, ConfusablesParser, @@ -86,30 +109,84 @@ attribute_groups!( ]; ); +mod private { + pub trait Sealed {} + impl Sealed for super::Early {} + impl Sealed for super::Late {} +} + +// allow because it's a sealed trait +#[allow(private_interfaces)] +pub trait Stage: Sized + 'static + Sealed { + type Id: Copy; + + fn parsers() -> &'static group_type!(Self); + + fn emit_err<'sess>(sess: &'sess Session, diag: impl for<'x> Diagnostic<'x>) -> ErrorGuaranteed; +} + +// allow because it's a sealed trait +#[allow(private_interfaces)] +impl Stage for Early { + type Id = NodeId; + + fn parsers() -> &'static group_type!(Self) { + &early::ATTRIBUTE_PARSERS + } + fn emit_err<'sess>(sess: &'sess Session, diag: impl for<'x> Diagnostic<'x>) -> ErrorGuaranteed { + sess.dcx().create_err(diag).delay_as_bug() + } +} + +// allow because it's a sealed trait +#[allow(private_interfaces)] +impl Stage for Late { + type Id = HirId; + + fn parsers() -> &'static group_type!(Self) { + &late::ATTRIBUTE_PARSERS + } + fn emit_err<'sess>(tcx: &'sess Session, diag: impl for<'x> Diagnostic<'x>) -> ErrorGuaranteed { + tcx.dcx().emit_err(diag) + } +} + +/// used when parsing attributes for miscelaneous things *before* ast lowering +pub struct Early; +/// used when parsing attributes during ast lowering +pub struct Late; + /// Context given to every attribute parser when accepting /// /// Gives [`AttributeParser`]s enough information to create errors, for example. -pub(crate) struct AcceptContext<'a> { - pub(crate) group_cx: &'a FinalizeContext<'a>, +pub(crate) struct AcceptContext<'f, 'sess, S: Stage> { + pub(crate) finalize_cx: FinalizeContext<'f, 'sess, S>, /// The span of the attribute currently being parsed pub(crate) attr_span: Span, } -impl<'a> AcceptContext<'a> { - pub(crate) fn emit_err(&self, diag: impl Diagnostic<'a>) -> ErrorGuaranteed { - if self.limit_diagnostics { - self.dcx().create_err(diag).delay_as_bug() - } else { - self.dcx().emit_err(diag) - } +impl<'f, 'sess: 'f, S: Stage> AcceptContext<'f, 'sess, S> { + pub(crate) fn emit_err(&self, diag: impl for<'x> Diagnostic<'x>) -> ErrorGuaranteed { + S::emit_err(&self.sess, diag) + } + + pub(crate) fn emit_lint(&mut self, lint: AttributeLintKind, span: Span) { + let id = self.target_id; + (self.emit_lint)(AttributeLint { id, span, kind: lint }); } } -impl<'a> Deref for AcceptContext<'a> { - type Target = FinalizeContext<'a>; +impl<'f, 'sess, S: Stage> Deref for AcceptContext<'f, 'sess, S> { + type Target = FinalizeContext<'f, 'sess, S>; fn deref(&self) -> &Self::Target { - &self.group_cx + &self.finalize_cx + } +} + +impl<'f, 'sess, S: Stage> DerefMut for AcceptContext<'f, 'sess, S> { + fn deref_mut(&mut self) -> &mut Self::Target { + &mut self.finalize_cx } } @@ -117,19 +194,29 @@ impl<'a> Deref for AcceptContext<'a> { /// /// Gives [`AttributeParser`](crate::attributes::AttributeParser)s enough information to create /// errors, for example. -pub(crate) struct FinalizeContext<'a> { +pub(crate) struct FinalizeContext<'p, 'sess, S: Stage> { /// The parse context, gives access to the session and the /// diagnostics context. - pub(crate) cx: &'a AttributeParser<'a>, + pub(crate) cx: &'p mut AttributeParser<'sess, S>, /// The span of the syntactical component this attribute was applied to pub(crate) target_span: Span, + /// The id ([`NodeId`] if `S` is `Early`, [`HirId`] if `S` is `Late`) of the syntactical component this attribute was applied to + pub(crate) target_id: S::Id, + + pub(crate) emit_lint: &'p mut dyn FnMut(AttributeLint), } -impl<'a> Deref for FinalizeContext<'a> { - type Target = AttributeParser<'a>; +impl<'p, 'sess: 'p, S: Stage> Deref for FinalizeContext<'p, 'sess, S> { + type Target = AttributeParser<'sess, S>; fn deref(&self) -> &Self::Target { - &self.cx + self.cx + } +} + +impl<'p, 'sess: 'p, S: Stage> DerefMut for FinalizeContext<'p, 'sess, S> { + fn deref_mut(&mut self) -> &mut Self::Target { + self.cx } } @@ -141,23 +228,20 @@ pub enum OmitDoc { /// Context created once, for example as part of the ast lowering /// context, through which all attributes can be lowered. -pub struct AttributeParser<'sess> { +pub struct AttributeParser<'sess, S: Stage = Late> { #[expect(dead_code)] // FIXME(jdonszelmann): needed later to verify we parsed all attributes tools: Vec, - sess: &'sess Session, features: Option<&'sess Features>, + sess: &'sess Session, + stage: PhantomData, /// *Only* parse attributes with this symbol. /// /// Used in cases where we want the lowering infrastructure for parse just a single attribute. parse_only: Option, - - /// Can be used to instruct parsers to reduce the number of diagnostics it emits. - /// Useful when using `parse_limited` and you know the attr will be reparsed later. - pub(crate) limit_diagnostics: bool, } -impl<'sess> AttributeParser<'sess> { +impl<'sess> AttributeParser<'sess, Early> { /// This method allows you to parse attributes *before* you have access to features or tools. /// One example where this is necessary, is to parse `feature` attributes themselves for /// example. @@ -168,33 +252,53 @@ impl<'sess> AttributeParser<'sess> { /// /// To make sure use is limited, supply a `Symbol` you'd like to parse. Only attributes with /// that symbol are picked out of the list of instructions and parsed. Those are returned. + /// + /// No diagnostics will be emitted when parsing limited. Lints are not emitted at all, while + /// errors will be emitted as a delayed bugs. in other words, we *expect* attributes parsed + /// with `parse_limited` to be reparsed later during ast lowering where we *do* emit the errors pub fn parse_limited( sess: &'sess Session, attrs: &[ast::Attribute], sym: Symbol, target_span: Span, - limit_diagnostics: bool, + target_node_id: NodeId, ) -> Option { - let mut parsed = Self { - sess, + let mut p = Self { features: None, tools: Vec::new(), parse_only: Some(sym), - limit_diagnostics, - } - .parse_attribute_list(attrs, target_span, OmitDoc::Skip, std::convert::identity); - + sess, + stage: PhantomData, + }; + let mut parsed = p.parse_attribute_list( + attrs, + target_span, + target_node_id, + OmitDoc::Skip, + std::convert::identity, + |_lint| { + panic!("can't emit lints here for now (nothing uses this atm)"); + }, + ); assert!(parsed.len() <= 1); parsed.pop() } - pub fn new(sess: &'sess Session, features: &'sess Features, tools: Vec) -> Self { - Self { sess, features: Some(features), tools, parse_only: None, limit_diagnostics: false } + pub fn new_early(sess: &'sess Session, features: &'sess Features, tools: Vec) -> Self { + Self { features: Some(features), tools, parse_only: None, sess, stage: PhantomData } } +} +impl<'sess> AttributeParser<'sess, Late> { + pub fn new(sess: &'sess Session, features: &'sess Features, tools: Vec) -> Self { + Self { features: Some(features), tools, parse_only: None, sess, stage: PhantomData } + } +} + +impl<'sess, S: Stage> AttributeParser<'sess, S> { pub(crate) fn sess(&self) -> &'sess Session { - self.sess + &self.sess } pub(crate) fn features(&self) -> &'sess Features { @@ -202,25 +306,25 @@ impl<'sess> AttributeParser<'sess> { } pub(crate) fn dcx(&self) -> DiagCtxtHandle<'sess> { - self.sess.dcx() + self.sess().dcx() } /// Parse a list of attributes. /// /// `target_span` is the span of the thing this list of attributes is applied to, /// and when `omit_doc` is set, doc attributes are filtered out. - pub fn parse_attribute_list<'a>( - &'a self, - attrs: &'a [ast::Attribute], + pub fn parse_attribute_list( + &mut self, + attrs: &[ast::Attribute], target_span: Span, + target_id: S::Id, omit_doc: OmitDoc, lower_span: impl Copy + Fn(Span) -> Span, + mut emit_lint: impl FnMut(AttributeLint), ) -> Vec { let mut attributes = Vec::new(); - let group_cx = FinalizeContext { cx: self, target_span }; - for attr in attrs { // If we're only looking for a single attribute, skip all the ones we don't care about. if let Some(expected) = self.parse_only { @@ -268,11 +372,18 @@ impl<'sess> AttributeParser<'sess> { let args = parser.args(); let parts = path.segments().map(|i| i.name).collect::>(); - if let Some(accept) = ATTRIBUTE_MAPPING.0.get(parts.as_slice()) { - let cx = - AcceptContext { group_cx: &group_cx, attr_span: lower_span(attr.span) }; + if let Some(accept) = S::parsers().0.get(parts.as_slice()) { + let mut cx: AcceptContext<'_, 'sess, S> = AcceptContext { + finalize_cx: FinalizeContext { + cx: self, + target_span, + target_id, + emit_lint: &mut emit_lint, + }, + attr_span: lower_span(attr.span), + }; - accept(&cx, &args) + accept(&mut cx, args) } else { // If we're here, we must be compiling a tool attribute... Or someone // forgot to parse their fancy new attribute. Let's warn them in any case. @@ -302,8 +413,13 @@ impl<'sess> AttributeParser<'sess> { } let mut parsed_attributes = Vec::new(); - for f in &ATTRIBUTE_MAPPING.1 { - if let Some(attr) = f(&group_cx) { + for f in &S::parsers().1 { + if let Some(attr) = f(&mut FinalizeContext { + cx: self, + target_span, + target_id, + emit_lint: &mut emit_lint, + }) { parsed_attributes.push(Attribute::Parsed(attr)); } } diff --git a/compiler/rustc_attr_parsing/src/lib.rs b/compiler/rustc_attr_parsing/src/lib.rs index 15037e802ff5..47eeb63bad3d 100644 --- a/compiler/rustc_attr_parsing/src/lib.rs +++ b/compiler/rustc_attr_parsing/src/lib.rs @@ -85,7 +85,8 @@ #[macro_use] mod attributes; -mod context; +pub(crate) mod context; +mod lints; pub mod parser; mod session_diagnostics; @@ -93,6 +94,7 @@ pub use attributes::cfg::*; pub use attributes::util::{ find_crate_name, is_builtin_attr, is_doc_alias_attrs_contain_symbol, parse_version, }; -pub use context::{AttributeParser, OmitDoc}; +pub use context::{AttributeParser, Early, Late, OmitDoc}; +pub use lints::emit_attribute_lint; rustc_fluent_macro::fluent_messages! { "../messages.ftl" } diff --git a/compiler/rustc_attr_parsing/src/lints.rs b/compiler/rustc_attr_parsing/src/lints.rs new file mode 100644 index 000000000000..d0d112446b4d --- /dev/null +++ b/compiler/rustc_attr_parsing/src/lints.rs @@ -0,0 +1,19 @@ +use rustc_attr_data_structures::lints::{AttributeLint, AttributeLintKind}; +use rustc_errors::LintEmitter; +use rustc_hir::HirId; + +use crate::session_diagnostics; + +pub fn emit_attribute_lint(lint: &AttributeLint, lint_emitter: L) { + let AttributeLint { id, span, kind } = lint; + + match kind { + &AttributeLintKind::UnusedDuplicate { this, other, warning } => lint_emitter + .emit_node_span_lint( + rustc_session::lint::builtin::UNUSED_ATTRIBUTES, + *id, + *span, + session_diagnostics::UnusedDuplicate { this, other, warning }, + ), + } +} diff --git a/compiler/rustc_attr_parsing/src/parser.rs b/compiler/rustc_attr_parsing/src/parser.rs index e10e3b511db6..1edbe3a9d27a 100644 --- a/compiler/rustc_attr_parsing/src/parser.rs +++ b/compiler/rustc_attr_parsing/src/parser.rs @@ -115,7 +115,7 @@ impl<'a> ArgParser<'a> { } } - pub fn from_attr_args(value: &'a AttrArgs, dcx: DiagCtxtHandle<'a>) -> Self { + pub fn from_attr_args<'sess>(value: &'a AttrArgs, dcx: DiagCtxtHandle<'sess>) -> Self { match value { AttrArgs::Empty => Self::NoArgs, AttrArgs::Delimited(args) if args.delim == Delimiter::Parenthesis => { @@ -235,7 +235,7 @@ impl<'a> Debug for MetaItemParser<'a> { impl<'a> MetaItemParser<'a> { /// Create a new parser from a [`NormalAttr`], which is stored inside of any /// [`ast::Attribute`](rustc_ast::Attribute) - pub fn from_attr(attr: &'a NormalAttr, dcx: DiagCtxtHandle<'a>) -> Self { + pub fn from_attr<'sess>(attr: &'a NormalAttr, dcx: DiagCtxtHandle<'sess>) -> Self { Self { path: PathParser::Ast(&attr.item.path), args: ArgParser::from_attr_args(&attr.item.args, dcx), @@ -320,13 +320,13 @@ fn expr_to_lit(dcx: DiagCtxtHandle<'_>, expr: &Expr, span: Span) -> MetaItemLit } } -struct MetaItemListParserContext<'a> { +struct MetaItemListParserContext<'a, 'sess> { // the tokens inside the delimiters, so `#[some::attr(a b c)]` would have `a b c` inside inside_delimiters: Peekable>, - dcx: DiagCtxtHandle<'a>, + dcx: DiagCtxtHandle<'sess>, } -impl<'a> MetaItemListParserContext<'a> { +impl<'a, 'sess> MetaItemListParserContext<'a, 'sess> { fn done(&mut self) -> bool { self.inside_delimiters.peek().is_none() } @@ -507,11 +507,11 @@ pub struct MetaItemListParser<'a> { } impl<'a> MetaItemListParser<'a> { - fn new(delim: &'a DelimArgs, dcx: DiagCtxtHandle<'a>) -> MetaItemListParser<'a> { + fn new<'sess>(delim: &'a DelimArgs, dcx: DiagCtxtHandle<'sess>) -> Self { MetaItemListParser::new_tts(delim.tokens.iter(), delim.dspan.entire(), dcx) } - fn new_tts(tts: TokenStreamIter<'a>, span: Span, dcx: DiagCtxtHandle<'a>) -> Self { + fn new_tts<'sess>(tts: TokenStreamIter<'a>, span: Span, dcx: DiagCtxtHandle<'sess>) -> Self { MetaItemListParserContext { inside_delimiters: tts.peekable(), dcx }.parse(span) } diff --git a/compiler/rustc_attr_parsing/src/session_diagnostics.rs b/compiler/rustc_attr_parsing/src/session_diagnostics.rs index 2c434175b4b6..7f847d3dd4c5 100644 --- a/compiler/rustc_attr_parsing/src/session_diagnostics.rs +++ b/compiler/rustc_attr_parsing/src/session_diagnostics.rs @@ -3,7 +3,7 @@ use std::num::IntErrorKind; use rustc_ast as ast; use rustc_errors::codes::*; use rustc_errors::{Applicability, Diag, DiagCtxtHandle, Diagnostic, EmissionGuarantee, Level}; -use rustc_macros::{Diagnostic, Subdiagnostic}; +use rustc_macros::{Diagnostic, LintDiagnostic, Subdiagnostic}; use rustc_span::{Span, Symbol}; use crate::fluent_generated as fluent; @@ -451,6 +451,17 @@ pub(crate) struct UnusedMultiple { pub name: Symbol, } +#[derive(LintDiagnostic)] +#[diag(attr_parsing_unused_duplicate)] +pub(crate) struct UnusedDuplicate { + #[suggestion(code = "", applicability = "machine-applicable")] + pub this: Span, + #[note] + pub other: Span, + #[warning] + pub warning: bool, +} + #[derive(Diagnostic)] #[diag(attr_parsing_stability_outside_std, code = E0734)] pub(crate) struct StabilityOutsideStd { diff --git a/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs b/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs index 1b4bb11d87b3..34d368499397 100644 --- a/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs +++ b/compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs @@ -3229,8 +3229,20 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> { Applicability::MaybeIncorrect, ); } + + let mutability = if matches!(borrow.kind(), BorrowKind::Mut { .. }) { + "mut " + } else { + "" + }; + if !is_format_arguments_item { - let addition = format!("let binding = {};\n{}", s, " ".repeat(p)); + let addition = format!( + "let {}binding = {};\n{}", + mutability, + s, + " ".repeat(p) + ); err.multipart_suggestion_verbose( msg, vec![ diff --git a/compiler/rustc_borrowck/src/type_check/constraint_conversion.rs b/compiler/rustc_borrowck/src/type_check/constraint_conversion.rs index a1c74672157b..0a114467f432 100644 --- a/compiler/rustc_borrowck/src/type_check/constraint_conversion.rs +++ b/compiler/rustc_borrowck/src/type_check/constraint_conversion.rs @@ -141,8 +141,11 @@ impl<'a, 'tcx> ConstraintConversion<'a, 'tcx> { } if !tcx.recursion_limit().value_within_limit(iteration) { + // This may actually be reachable. If so, we should convert + // this to a proper error/consider whether we should detect + // this somewhere else. bug!( - "FIXME(-Znext-solver): Overflowed when processing region obligations: {outlives_predicates:#?}" + "unexpected overflowed when processing region obligations: {outlives_predicates:#?}" ); } diff --git a/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs b/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs index 6dd3adf750db..d642851bb77b 100644 --- a/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs +++ b/compiler/rustc_builtin_macros/src/deriving/generic/mod.rs @@ -484,7 +484,7 @@ impl<'a> TraitDef<'a> { match item { Annotatable::Item(item) => { let is_packed = matches!( - AttributeParser::parse_limited(cx.sess, &item.attrs, sym::repr, item.span, true), + AttributeParser::parse_limited(cx.sess, &item.attrs, sym::repr, item.span, item.id), Some(Attribute::Parsed(AttributeKind::Repr(r))) if r.iter().any(|(x, _)| matches!(x, ReprPacked(..))) ); diff --git a/compiler/rustc_codegen_cranelift/example/mini_core.rs b/compiler/rustc_codegen_cranelift/example/mini_core.rs index 1dc799c0aeea..012e4dbc3ec9 100644 --- a/compiler/rustc_codegen_cranelift/example/mini_core.rs +++ b/compiler/rustc_codegen_cranelift/example/mini_core.rs @@ -644,9 +644,9 @@ pub mod intrinsics { #[rustc_intrinsic] pub unsafe fn size_of_val(val: *const T) -> usize; #[rustc_intrinsic] - pub fn min_align_of() -> usize; + pub fn align_of() -> usize; #[rustc_intrinsic] - pub unsafe fn min_align_of_val(val: *const T) -> usize; + pub unsafe fn align_of_val(val: *const T) -> usize; #[rustc_intrinsic] pub unsafe fn copy(src: *const T, dst: *mut T, count: usize); #[rustc_intrinsic] diff --git a/compiler/rustc_codegen_cranelift/example/mini_core_hello_world.rs b/compiler/rustc_codegen_cranelift/example/mini_core_hello_world.rs index 93ca2e0e4218..1499f948deb3 100644 --- a/compiler/rustc_codegen_cranelift/example/mini_core_hello_world.rs +++ b/compiler/rustc_codegen_cranelift/example/mini_core_hello_world.rs @@ -204,11 +204,8 @@ fn main() { assert_eq!(intrinsics::size_of_val(a) as u8, 16); assert_eq!(intrinsics::size_of_val(&0u32) as u8, 4); - assert_eq!(intrinsics::min_align_of::() as u8, 2); - assert_eq!( - intrinsics::min_align_of_val(&a) as u8, - intrinsics::min_align_of::<&str>() as u8 - ); + assert_eq!(intrinsics::align_of::() as u8, 2); + assert_eq!(intrinsics::align_of_val(&a) as u8, intrinsics::align_of::<&str>() as u8); assert!(!intrinsics::needs_drop::()); assert!(!intrinsics::needs_drop::<[u8]>()); diff --git a/compiler/rustc_codegen_cranelift/src/abi/mod.rs b/compiler/rustc_codegen_cranelift/src/abi/mod.rs index fe5b220117f3..4c6fd9078154 100644 --- a/compiler/rustc_codegen_cranelift/src/abi/mod.rs +++ b/compiler/rustc_codegen_cranelift/src/abi/mod.rs @@ -51,6 +51,11 @@ pub(crate) fn conv_to_call_conv( CanonAbi::Rust | CanonAbi::C => default_call_conv, CanonAbi::RustCold => CallConv::Cold, + // Functions with this calling convention can only be called from assembly, but it is + // possible to declare an `extern "custom"` block, so the backend still needs a calling + // convention for declaring foreign functions. + CanonAbi::Custom => default_call_conv, + CanonAbi::X86(x86_call) => match x86_call { X86Call::SysV64 => CallConv::SystemV, X86Call::Win64 => CallConv::WindowsFastcall, diff --git a/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs b/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs index 1d1cf884e48b..df5748c34d11 100644 --- a/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs +++ b/compiler/rustc_codegen_cranelift/src/intrinsics/mod.rs @@ -586,7 +586,7 @@ fn codegen_regular_intrinsic_call<'tcx>( let (size, _align) = crate::unsize::size_and_align_of(fx, layout, meta); ret.write_cvalue(fx, CValue::by_val(size, usize_layout)); } - sym::min_align_of_val => { + sym::align_of_val => { intrinsic_args!(fx, args => (ptr); intrinsic); let layout = fx.layout_of(generic_args.type_at(0)); @@ -613,7 +613,7 @@ fn codegen_regular_intrinsic_call<'tcx>( intrinsic_args!(fx, args => (vtable); intrinsic); let vtable = vtable.load_scalar(fx); - let align = crate::vtable::min_align_of_obj(fx, vtable); + let align = crate::vtable::align_of_obj(fx, vtable); ret.write_cvalue(fx, CValue::by_val(align, usize_layout)); } diff --git a/compiler/rustc_codegen_cranelift/src/unsize.rs b/compiler/rustc_codegen_cranelift/src/unsize.rs index 662546e49998..df60b05c4636 100644 --- a/compiler/rustc_codegen_cranelift/src/unsize.rs +++ b/compiler/rustc_codegen_cranelift/src/unsize.rs @@ -212,7 +212,7 @@ pub(crate) fn size_and_align_of<'tcx>( // load size/align from vtable ( crate::vtable::size_of_obj(fx, info.unwrap()), - crate::vtable::min_align_of_obj(fx, info.unwrap()), + crate::vtable::align_of_obj(fx, info.unwrap()), ) } ty::Slice(_) | ty::Str => { diff --git a/compiler/rustc_codegen_cranelift/src/vtable.rs b/compiler/rustc_codegen_cranelift/src/vtable.rs index 05a8e3c33421..1fae56949bc0 100644 --- a/compiler/rustc_codegen_cranelift/src/vtable.rs +++ b/compiler/rustc_codegen_cranelift/src/vtable.rs @@ -31,7 +31,7 @@ pub(crate) fn size_of_obj(fx: &mut FunctionCx<'_, '_, '_>, vtable: Value) -> Val ) } -pub(crate) fn min_align_of_obj(fx: &mut FunctionCx<'_, '_, '_>, vtable: Value) -> Value { +pub(crate) fn align_of_obj(fx: &mut FunctionCx<'_, '_, '_>, vtable: Value) -> Value { let usize_size = fx.layout_of(fx.tcx.types.usize).size.bytes() as usize; fx.bcx.ins().load( fx.pointer_type, diff --git a/compiler/rustc_codegen_gcc/example/mini_core.rs b/compiler/rustc_codegen_gcc/example/mini_core.rs index d1d8e8fd5bc4..aca1f0080efd 100644 --- a/compiler/rustc_codegen_gcc/example/mini_core.rs +++ b/compiler/rustc_codegen_gcc/example/mini_core.rs @@ -655,9 +655,9 @@ pub mod intrinsics { #[rustc_intrinsic] pub unsafe fn size_of_val(val: *const T) -> usize; #[rustc_intrinsic] - pub fn min_align_of() -> usize; + pub fn align_of() -> usize; #[rustc_intrinsic] - pub unsafe fn min_align_of_val(val: *const T) -> usize; + pub unsafe fn align_of_val(val: *const T) -> usize; #[rustc_intrinsic] pub unsafe fn copy(src: *const T, dst: *mut T, count: usize); #[rustc_intrinsic] diff --git a/compiler/rustc_codegen_gcc/example/mini_core_hello_world.rs b/compiler/rustc_codegen_gcc/example/mini_core_hello_world.rs index 4cbe66c5e4c6..c3bd62e5897c 100644 --- a/compiler/rustc_codegen_gcc/example/mini_core_hello_world.rs +++ b/compiler/rustc_codegen_gcc/example/mini_core_hello_world.rs @@ -153,7 +153,7 @@ fn main() { let slice = &[0, 1] as &[i32]; let slice_ptr = slice as *const [i32] as *const i32; - let align = intrinsics::min_align_of::<*const i32>(); + let align = intrinsics::align_of::<*const i32>(); assert_eq!(slice_ptr as usize % align, 0); //return; @@ -194,8 +194,8 @@ fn main() { assert_eq!(intrinsics::size_of_val(a) as u8, 8); assert_eq!(intrinsics::size_of_val(&0u32) as u8, 4); - assert_eq!(intrinsics::min_align_of::() as u8, 2); - assert_eq!(intrinsics::min_align_of_val(&a) as u8, intrinsics::min_align_of::<&str>() as u8); + assert_eq!(intrinsics::align_of::() as u8, 2); + assert_eq!(intrinsics::align_of_val(&a) as u8, intrinsics::align_of::<&str>() as u8); assert!(!intrinsics::needs_drop::()); assert!(!intrinsics::needs_drop::<[u8]>()); diff --git a/compiler/rustc_codegen_gcc/messages.ftl b/compiler/rustc_codegen_gcc/messages.ftl index 546bfc87b689..18a8a5a1e048 100644 --- a/compiler/rustc_codegen_gcc/messages.ftl +++ b/compiler/rustc_codegen_gcc/messages.ftl @@ -2,9 +2,6 @@ codegen_gcc_unknown_ctarget_feature_prefix = unknown feature specified for `-Ctarget-feature`: `{$feature}` .note = features must begin with a `+` to enable or `-` to disable it -codegen_gcc_forbidden_ctarget_feature = - target feature `{$feature}` cannot be toggled with `-Ctarget-feature`: {$reason} - codegen_gcc_unwinding_inline_asm = GCC backend does not support unwinding from inline asm @@ -26,10 +23,6 @@ codegen_gcc_unknown_ctarget_feature = .possible_feature = you might have meant: `{$rust_feature}` .consider_filing_feature_request = consider filing a feature request -codegen_gcc_unstable_ctarget_feature = - unstable feature specified for `-Ctarget-feature`: `{$feature}` - .note = this feature is not stably supported; its behavior can change in the future - codegen_gcc_missing_features = add the missing features in a `target_feature` attribute diff --git a/compiler/rustc_codegen_gcc/src/abi.rs b/compiler/rustc_codegen_gcc/src/abi.rs index 3d0c258f576d..08f3d2819040 100644 --- a/compiler/rustc_codegen_gcc/src/abi.rs +++ b/compiler/rustc_codegen_gcc/src/abi.rs @@ -239,12 +239,16 @@ impl<'gcc, 'tcx> FnAbiGccExt<'gcc, 'tcx> for FnAbi<'tcx, Ty<'tcx>> { pub fn conv_to_fn_attribute<'gcc>(conv: CanonAbi, arch: &str) -> Option> { let attribute = match conv { CanonAbi::C | CanonAbi::Rust => return None, + CanonAbi::RustCold => FnAttribute::Cold, + // Functions with this calling convention can only be called from assembly, but it is + // possible to declare an `extern "custom"` block, so the backend still needs a calling + // convention for declaring foreign functions. + CanonAbi::Custom => return None, CanonAbi::Arm(arm_call) => match arm_call { ArmCall::CCmseNonSecureCall => FnAttribute::ArmCmseNonsecureCall, ArmCall::CCmseNonSecureEntry => FnAttribute::ArmCmseNonsecureEntry, ArmCall::Aapcs => FnAttribute::ArmPcs("aapcs"), }, - CanonAbi::RustCold => FnAttribute::Cold, CanonAbi::GpuKernel => { if arch == "amdgpu" { FnAttribute::GcnAmdGpuHsaKernel diff --git a/compiler/rustc_codegen_gcc/src/errors.rs b/compiler/rustc_codegen_gcc/src/errors.rs index ccd9abe38049..7786be9ae5de 100644 --- a/compiler/rustc_codegen_gcc/src/errors.rs +++ b/compiler/rustc_codegen_gcc/src/errors.rs @@ -17,21 +17,6 @@ pub(crate) struct UnknownCTargetFeature<'a> { pub rust_feature: PossibleFeature<'a>, } -#[derive(Diagnostic)] -#[diag(codegen_gcc_unstable_ctarget_feature)] -#[note] -pub(crate) struct UnstableCTargetFeature<'a> { - pub feature: &'a str, -} - -#[derive(Diagnostic)] -#[diag(codegen_gcc_forbidden_ctarget_feature)] -pub(crate) struct ForbiddenCTargetFeature<'a> { - pub feature: &'a str, - pub enabled: &'a str, - pub reason: &'a str, -} - #[derive(Subdiagnostic)] pub(crate) enum PossibleFeature<'a> { #[help(codegen_gcc_possible_feature)] diff --git a/compiler/rustc_codegen_gcc/src/gcc_util.rs b/compiler/rustc_codegen_gcc/src/gcc_util.rs index 2b053abdd190..d90e66aea31e 100644 --- a/compiler/rustc_codegen_gcc/src/gcc_util.rs +++ b/compiler/rustc_codegen_gcc/src/gcc_util.rs @@ -5,13 +5,17 @@ use rustc_codegen_ssa::errors::TargetFeatureDisableOrEnable; use rustc_data_structures::fx::FxHashMap; use rustc_data_structures::unord::UnordSet; use rustc_session::Session; +use rustc_session::features::{StabilityExt, retpoline_features_by_flags}; use rustc_target::target_features::RUSTC_SPECIFIC_FEATURES; use smallvec::{SmallVec, smallvec}; -use crate::errors::{ - ForbiddenCTargetFeature, PossibleFeature, UnknownCTargetFeature, UnknownCTargetFeaturePrefix, - UnstableCTargetFeature, -}; +use crate::errors::{PossibleFeature, UnknownCTargetFeature, UnknownCTargetFeaturePrefix}; + +fn gcc_features_by_flags(sess: &Session) -> Vec<&str> { + let mut features: Vec<&str> = Vec::new(); + retpoline_features_by_flags(sess, &mut features); + features +} /// The list of GCC features computed from CLI flags (`-Ctarget-cpu`, `-Ctarget-feature`, /// `--target` and similar). @@ -45,7 +49,7 @@ pub(crate) fn global_gcc_features(sess: &Session, diagnostics: bool) -> Vec Vec { - if let Err(reason) = stability.toggle_allowed() { - sess.dcx().emit_warn(ForbiddenCTargetFeature { - feature, - enabled: if enable { "enabled" } else { "disabled" }, - reason, - }); - } else if stability.requires_nightly().is_some() { - // An unstable feature. Warn about using it. (It makes little sense - // to hard-error here since we just warn about fully unknown - // features above). - sess.dcx().emit_warn(UnstableCTargetFeature { feature }); - } + stability.verify_feature_enabled_by_flag(sess, enable, feature); } } diff --git a/compiler/rustc_codegen_llvm/messages.ftl b/compiler/rustc_codegen_llvm/messages.ftl index bda121c67fb6..3faeb9b3b221 100644 --- a/compiler/rustc_codegen_llvm/messages.ftl +++ b/compiler/rustc_codegen_llvm/messages.ftl @@ -10,11 +10,6 @@ codegen_llvm_dynamic_linking_with_lto = codegen_llvm_fixed_x18_invalid_arch = the `-Zfixed-x18` flag is not supported on the `{$arch}` architecture -codegen_llvm_forbidden_ctarget_feature = - target feature `{$feature}` cannot be {$enabled} with `-Ctarget-feature`: {$reason} - .note = this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! -codegen_llvm_forbidden_ctarget_feature_issue = for more information, see issue #116344 - codegen_llvm_from_llvm_diag = {$message} codegen_llvm_from_llvm_optimization_diag = {$filename}:{$line}:{$column} {$pass_name} ({$kind}): {$message} @@ -76,10 +71,6 @@ codegen_llvm_unknown_ctarget_feature_prefix = codegen_llvm_unknown_debuginfo_compression = unknown debuginfo compression algorithm {$algorithm} - will fall back to uncompressed debuginfo -codegen_llvm_unstable_ctarget_feature = - unstable feature specified for `-Ctarget-feature`: `{$feature}` - .note = this feature is not stably supported; its behavior can change in the future - codegen_llvm_write_bytecode = failed to write bytecode to {$path}: {$err} codegen_llvm_write_ir = failed to write LLVM IR to {$path} diff --git a/compiler/rustc_codegen_llvm/src/abi.rs b/compiler/rustc_codegen_llvm/src/abi.rs index 119cd634f982..aba63d75f1df 100644 --- a/compiler/rustc_codegen_llvm/src/abi.rs +++ b/compiler/rustc_codegen_llvm/src/abi.rs @@ -649,6 +649,10 @@ impl llvm::CallConv { match conv { CanonAbi::C | CanonAbi::Rust => llvm::CCallConv, CanonAbi::RustCold => llvm::PreserveMost, + // Functions with this calling convention can only be called from assembly, but it is + // possible to declare an `extern "custom"` block, so the backend still needs a calling + // convention for declaring foreign functions. + CanonAbi::Custom => llvm::CCallConv, CanonAbi::GpuKernel => { if arch == "amdgpu" { llvm::AmdgpuKernel diff --git a/compiler/rustc_codegen_llvm/src/attributes.rs b/compiler/rustc_codegen_llvm/src/attributes.rs index 443c2eace554..27fd09745ff0 100644 --- a/compiler/rustc_codegen_llvm/src/attributes.rs +++ b/compiler/rustc_codegen_llvm/src/attributes.rs @@ -5,6 +5,7 @@ use rustc_hir::def_id::DefId; use rustc_middle::middle::codegen_fn_attrs::{CodegenFnAttrFlags, PatchableFunctionEntry}; use rustc_middle::ty::{self, TyCtxt}; use rustc_session::config::{BranchProtection, FunctionReturn, OptLevel, PAuthKey, PacRet}; +use rustc_symbol_mangling::mangle_internal_symbol; use rustc_target::spec::{FramePointer, SanitizerSet, StackProbeType, StackProtector}; use smallvec::SmallVec; @@ -256,11 +257,11 @@ fn probestack_attr<'ll>(cx: &CodegenCx<'ll, '_>) -> Option<&'ll Attribute> { StackProbeType::Inline => "inline-asm", // Flag our internal `__rust_probestack` function as the stack probe symbol. // This is defined in the `compiler-builtins` crate for each architecture. - StackProbeType::Call => "__rust_probestack", + StackProbeType::Call => &mangle_internal_symbol(cx.tcx, "__rust_probestack"), // Pick from the two above based on the LLVM version. StackProbeType::InlineOrCall { min_llvm_version_for_inline } => { if llvm_util::get_version() < min_llvm_version_for_inline { - "__rust_probestack" + &mangle_internal_symbol(cx.tcx, "__rust_probestack") } else { "inline-asm" } diff --git a/compiler/rustc_codegen_llvm/src/errors.rs b/compiler/rustc_codegen_llvm/src/errors.rs index eaafc6807129..8bc74fbec7ec 100644 --- a/compiler/rustc_codegen_llvm/src/errors.rs +++ b/compiler/rustc_codegen_llvm/src/errors.rs @@ -24,23 +24,6 @@ pub(crate) struct UnknownCTargetFeature<'a> { pub rust_feature: PossibleFeature<'a>, } -#[derive(Diagnostic)] -#[diag(codegen_llvm_unstable_ctarget_feature)] -#[note] -pub(crate) struct UnstableCTargetFeature<'a> { - pub feature: &'a str, -} - -#[derive(Diagnostic)] -#[diag(codegen_llvm_forbidden_ctarget_feature)] -#[note] -#[note(codegen_llvm_forbidden_ctarget_feature_issue)] -pub(crate) struct ForbiddenCTargetFeature<'a> { - pub feature: &'a str, - pub enabled: &'a str, - pub reason: &'a str, -} - #[derive(Subdiagnostic)] pub(crate) enum PossibleFeature<'a> { #[help(codegen_llvm_possible_feature)] diff --git a/compiler/rustc_codegen_llvm/src/llvm_util.rs b/compiler/rustc_codegen_llvm/src/llvm_util.rs index 9718c95f38a8..0e77bc43df80 100644 --- a/compiler/rustc_codegen_llvm/src/llvm_util.rs +++ b/compiler/rustc_codegen_llvm/src/llvm_util.rs @@ -16,6 +16,7 @@ use rustc_fs_util::path_to_c_string; use rustc_middle::bug; use rustc_session::Session; use rustc_session::config::{PrintKind, PrintRequest}; +use rustc_session::features::{StabilityExt, retpoline_features_by_flags}; use rustc_span::Symbol; use rustc_target::spec::{MergeFunctions, PanicStrategy, SmallDataThresholdSupport}; use rustc_target::target_features::{RUSTC_SPECIAL_FEATURES, RUSTC_SPECIFIC_FEATURES}; @@ -23,8 +24,7 @@ use smallvec::{SmallVec, smallvec}; use crate::back::write::create_informational_target_machine; use crate::errors::{ - FixedX18InvalidArch, ForbiddenCTargetFeature, PossibleFeature, UnknownCTargetFeature, - UnknownCTargetFeaturePrefix, UnstableCTargetFeature, + FixedX18InvalidArch, PossibleFeature, UnknownCTargetFeature, UnknownCTargetFeaturePrefix, }; use crate::llvm; @@ -707,6 +707,12 @@ pub(crate) fn target_cpu(sess: &Session) -> &str { handle_native(cpu_name) } +fn llvm_features_by_flags(sess: &Session) -> Vec<&str> { + let mut features: Vec<&str> = Vec::new(); + retpoline_features_by_flags(sess, &mut features); + features +} + /// The list of LLVM features computed from CLI flags (`-Ctarget-cpu`, `-Ctarget-feature`, /// `--target` and similar). pub(crate) fn global_llvm_features( @@ -787,7 +793,7 @@ pub(crate) fn global_llvm_features( // Compute implied features let mut all_rust_features = vec![]; - for feature in sess.opts.cg.target_feature.split(',') { + for feature in sess.opts.cg.target_feature.split(',').chain(llvm_features_by_flags(sess)) { if let Some(feature) = feature.strip_prefix('+') { all_rust_features.extend( UnordSet::from(sess.target.implied_target_features(feature)) @@ -840,18 +846,7 @@ pub(crate) fn global_llvm_features( sess.dcx().emit_warn(unknown_feature); } Some((_, stability, _)) => { - if let Err(reason) = stability.toggle_allowed() { - sess.dcx().emit_warn(ForbiddenCTargetFeature { - feature, - enabled: if enable { "enabled" } else { "disabled" }, - reason, - }); - } else if stability.requires_nightly().is_some() { - // An unstable feature. Warn about using it. It makes little sense - // to hard-error here since we just warn about fully unknown - // features above. - sess.dcx().emit_warn(UnstableCTargetFeature { feature }); - } + stability.verify_feature_enabled_by_flag(sess, enable, feature); } } diff --git a/compiler/rustc_codegen_ssa/src/back/link.rs b/compiler/rustc_codegen_ssa/src/back/link.rs index 168077260a69..18b76b337576 100644 --- a/compiler/rustc_codegen_ssa/src/back/link.rs +++ b/compiler/rustc_codegen_ssa/src/back/link.rs @@ -1065,11 +1065,11 @@ fn link_natively( match strip { Strip::Debuginfo => { // FIXME: AIX's strip utility only offers option to strip line number information. - strip_with_external_utility(sess, stripcmd, out_filename, &["-X32_64", "-l"]) + strip_with_external_utility(sess, stripcmd, temp_filename, &["-X32_64", "-l"]) } Strip::Symbols => { // Must be noted this option might remove symbol __aix_rust_metadata and thus removes .info section which contains metadata. - strip_with_external_utility(sess, stripcmd, out_filename, &["-X32_64", "-r"]) + strip_with_external_utility(sess, stripcmd, temp_filename, &["-X32_64", "-r"]) } Strip::None => {} } diff --git a/compiler/rustc_codegen_ssa/src/mir/intrinsic.rs b/compiler/rustc_codegen_ssa/src/mir/intrinsic.rs index e217c09939ea..27fcab8ed2d6 100644 --- a/compiler/rustc_codegen_ssa/src/mir/intrinsic.rs +++ b/compiler/rustc_codegen_ssa/src/mir/intrinsic.rs @@ -118,7 +118,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { let (llsize, _) = size_of_val::size_and_align_of_dst(bx, tp_ty, meta); llsize } - sym::min_align_of_val => { + sym::align_of_val => { let tp_ty = fn_args.type_at(0); let (_, meta) = args[0].val.pointer_parts(); let (_, llalign) = size_of_val::size_and_align_of_dst(bx, tp_ty, meta); diff --git a/compiler/rustc_codegen_ssa/src/mir/rvalue.rs b/compiler/rustc_codegen_ssa/src/mir/rvalue.rs index 5c14fe5cd10b..b62ac89661f2 100644 --- a/compiler/rustc_codegen_ssa/src/mir/rvalue.rs +++ b/compiler/rustc_codegen_ssa/src/mir/rvalue.rs @@ -278,7 +278,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { { let from_backend_ty = bx.backend_type(operand.layout); let to_backend_ty = bx.backend_type(cast); - Some(OperandValue::Immediate(self.transmute_immediate( + Some(OperandValue::Immediate(transmute_immediate( bx, imm, from_scalar, @@ -303,8 +303,8 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { let out_a_ibty = bx.scalar_pair_element_backend_type(cast, 0, false); let out_b_ibty = bx.scalar_pair_element_backend_type(cast, 1, false); Some(OperandValue::Pair( - self.transmute_immediate(bx, imm_a, in_a, in_a_ibty, out_a, out_a_ibty), - self.transmute_immediate(bx, imm_b, in_b, in_b_ibty, out_b, out_b_ibty), + transmute_immediate(bx, imm_a, in_a, in_a_ibty, out_a, out_a_ibty), + transmute_immediate(bx, imm_b, in_b, in_b_ibty, out_b, out_b_ibty), )) } else { None @@ -332,7 +332,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { // valid ranges. For example, `char`s are passed as just `i32`, with no // way for LLVM to know that they're 0x10FFFF at most. Thus we assume // the range of the input value too, not just the output range. - self.assume_scalar_range(bx, imm, from_scalar, from_backend_ty); + assume_scalar_range(bx, imm, from_scalar, from_backend_ty); imm = match (from_scalar.primitive(), to_scalar.primitive()) { (Int(_, is_signed), Int(..)) => bx.intcast(imm, to_backend_ty, is_signed), @@ -365,98 +365,6 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { Some(imm) } - /// Transmutes one of the immediates from an [`OperandValue::Immediate`] - /// or an [`OperandValue::Pair`] to an immediate of the target type. - /// - /// `to_backend_ty` must be the *non*-immediate backend type (so it will be - /// `i8`, not `i1`, for `bool`-like types.) - fn transmute_immediate( - &self, - bx: &mut Bx, - mut imm: Bx::Value, - from_scalar: abi::Scalar, - from_backend_ty: Bx::Type, - to_scalar: abi::Scalar, - to_backend_ty: Bx::Type, - ) -> Bx::Value { - assert_eq!(from_scalar.size(self.cx), to_scalar.size(self.cx)); - - // While optimizations will remove no-op transmutes, they might still be - // there in debug or things that aren't no-op in MIR because they change - // the Rust type but not the underlying layout/niche. - if from_scalar == to_scalar && from_backend_ty == to_backend_ty { - return imm; - } - - use abi::Primitive::*; - imm = bx.from_immediate(imm); - - // If we have a scalar, we must already know its range. Either - // - // 1) It's a parameter with `range` parameter metadata, - // 2) It's something we `load`ed with `!range` metadata, or - // 3) After a transmute we `assume`d the range (see below). - // - // That said, last time we tried removing this, it didn't actually help - // the rustc-perf results, so might as well keep doing it - // - self.assume_scalar_range(bx, imm, from_scalar, from_backend_ty); - - imm = match (from_scalar.primitive(), to_scalar.primitive()) { - (Int(..) | Float(_), Int(..) | Float(_)) => bx.bitcast(imm, to_backend_ty), - (Pointer(..), Pointer(..)) => bx.pointercast(imm, to_backend_ty), - (Int(..), Pointer(..)) => bx.ptradd(bx.const_null(bx.type_ptr()), imm), - (Pointer(..), Int(..)) => { - // FIXME: this exposes the provenance, which shouldn't be necessary. - bx.ptrtoint(imm, to_backend_ty) - } - (Float(_), Pointer(..)) => { - let int_imm = bx.bitcast(imm, bx.cx().type_isize()); - bx.ptradd(bx.const_null(bx.type_ptr()), int_imm) - } - (Pointer(..), Float(_)) => { - // FIXME: this exposes the provenance, which shouldn't be necessary. - let int_imm = bx.ptrtoint(imm, bx.cx().type_isize()); - bx.bitcast(int_imm, to_backend_ty) - } - }; - - // This `assume` remains important for cases like (a conceptual) - // transmute::(x) == 0 - // since it's never passed to something with parameter metadata (especially - // after MIR inlining) so the only way to tell the backend about the - // constraint that the `transmute` introduced is to `assume` it. - self.assume_scalar_range(bx, imm, to_scalar, to_backend_ty); - - imm = bx.to_immediate_scalar(imm, to_scalar); - imm - } - - fn assume_scalar_range( - &self, - bx: &mut Bx, - imm: Bx::Value, - scalar: abi::Scalar, - backend_ty: Bx::Type, - ) { - if matches!(self.cx.sess().opts.optimize, OptLevel::No) || scalar.is_always_valid(self.cx) { - return; - } - - match scalar.primitive() { - abi::Primitive::Int(..) => { - let range = scalar.valid_range(self.cx); - bx.assume_integer_range(imm, backend_ty, range); - } - abi::Primitive::Pointer(abi::AddressSpace::DATA) - if !scalar.valid_range(self.cx).contains(0) => - { - bx.assume_nonnull(imm); - } - abi::Primitive::Pointer(..) | abi::Primitive::Float(..) => {} - } - } - pub(crate) fn codegen_rvalue_unsized( &mut self, bx: &mut Bx, @@ -1231,3 +1139,93 @@ impl OperandValueKind { }) } } + +/// Transmutes one of the immediates from an [`OperandValue::Immediate`] +/// or an [`OperandValue::Pair`] to an immediate of the target type. +/// +/// `to_backend_ty` must be the *non*-immediate backend type (so it will be +/// `i8`, not `i1`, for `bool`-like types.) +fn transmute_immediate<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>( + bx: &mut Bx, + mut imm: Bx::Value, + from_scalar: abi::Scalar, + from_backend_ty: Bx::Type, + to_scalar: abi::Scalar, + to_backend_ty: Bx::Type, +) -> Bx::Value { + assert_eq!(from_scalar.size(bx.cx()), to_scalar.size(bx.cx())); + + // While optimizations will remove no-op transmutes, they might still be + // there in debug or things that aren't no-op in MIR because they change + // the Rust type but not the underlying layout/niche. + if from_scalar == to_scalar && from_backend_ty == to_backend_ty { + return imm; + } + + use abi::Primitive::*; + imm = bx.from_immediate(imm); + + // If we have a scalar, we must already know its range. Either + // + // 1) It's a parameter with `range` parameter metadata, + // 2) It's something we `load`ed with `!range` metadata, or + // 3) After a transmute we `assume`d the range (see below). + // + // That said, last time we tried removing this, it didn't actually help + // the rustc-perf results, so might as well keep doing it + // + assume_scalar_range(bx, imm, from_scalar, from_backend_ty); + + imm = match (from_scalar.primitive(), to_scalar.primitive()) { + (Int(..) | Float(_), Int(..) | Float(_)) => bx.bitcast(imm, to_backend_ty), + (Pointer(..), Pointer(..)) => bx.pointercast(imm, to_backend_ty), + (Int(..), Pointer(..)) => bx.ptradd(bx.const_null(bx.type_ptr()), imm), + (Pointer(..), Int(..)) => { + // FIXME: this exposes the provenance, which shouldn't be necessary. + bx.ptrtoint(imm, to_backend_ty) + } + (Float(_), Pointer(..)) => { + let int_imm = bx.bitcast(imm, bx.cx().type_isize()); + bx.ptradd(bx.const_null(bx.type_ptr()), int_imm) + } + (Pointer(..), Float(_)) => { + // FIXME: this exposes the provenance, which shouldn't be necessary. + let int_imm = bx.ptrtoint(imm, bx.cx().type_isize()); + bx.bitcast(int_imm, to_backend_ty) + } + }; + + // This `assume` remains important for cases like (a conceptual) + // transmute::(x) == 0 + // since it's never passed to something with parameter metadata (especially + // after MIR inlining) so the only way to tell the backend about the + // constraint that the `transmute` introduced is to `assume` it. + assume_scalar_range(bx, imm, to_scalar, to_backend_ty); + + imm = bx.to_immediate_scalar(imm, to_scalar); + imm +} + +fn assume_scalar_range<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>( + bx: &mut Bx, + imm: Bx::Value, + scalar: abi::Scalar, + backend_ty: Bx::Type, +) { + if matches!(bx.cx().sess().opts.optimize, OptLevel::No) || scalar.is_always_valid(bx.cx()) { + return; + } + + match scalar.primitive() { + abi::Primitive::Int(..) => { + let range = scalar.valid_range(bx.cx()); + bx.assume_integer_range(imm, backend_ty, range); + } + abi::Primitive::Pointer(abi::AddressSpace::DATA) + if !scalar.valid_range(bx.cx()).contains(0) => + { + bx.assume_nonnull(imm); + } + abi::Primitive::Pointer(..) | abi::Primitive::Float(..) => {} + } +} diff --git a/compiler/rustc_codegen_ssa/src/target_features.rs b/compiler/rustc_codegen_ssa/src/target_features.rs index 6bb3150c1c57..640d197c219a 100644 --- a/compiler/rustc_codegen_ssa/src/target_features.rs +++ b/compiler/rustc_codegen_ssa/src/target_features.rs @@ -8,6 +8,7 @@ use rustc_hir::def_id::{DefId, LOCAL_CRATE, LocalDefId}; use rustc_middle::middle::codegen_fn_attrs::TargetFeature; use rustc_middle::query::Providers; use rustc_middle::ty::TyCtxt; +use rustc_session::features::StabilityExt; use rustc_session::lint::builtin::AARCH64_SOFTFLOAT_NEON; use rustc_session::parse::feature_err; use rustc_span::{Span, Symbol, sym}; @@ -66,7 +67,7 @@ pub(crate) fn from_target_feature_attr( // Only allow target features whose feature gates have been enabled // and which are permitted to be toggled. - if let Err(reason) = stability.toggle_allowed() { + if let Err(reason) = stability.is_toggle_permitted(tcx.sess) { tcx.dcx().emit_err(errors::ForbiddenTargetFeatureAttr { span: item.span(), feature, diff --git a/compiler/rustc_codegen_ssa/src/traits/type_.rs b/compiler/rustc_codegen_ssa/src/traits/type_.rs index c3fc21a92854..70331b72353e 100644 --- a/compiler/rustc_codegen_ssa/src/traits/type_.rs +++ b/compiler/rustc_codegen_ssa/src/traits/type_.rs @@ -44,10 +44,10 @@ pub trait DerivedTypeCodegenMethods<'tcx>: BaseTypeCodegenMethods + MiscCodegenMethods<'tcx> + HasTyCtxt<'tcx> + HasTypingEnv<'tcx> { fn type_int(&self) -> Self::Type { - match &self.sess().target.c_int_width[..] { - "16" => self.type_i16(), - "32" => self.type_i32(), - "64" => self.type_i64(), + match &self.sess().target.c_int_width { + 16 => self.type_i16(), + 32 => self.type_i32(), + 64 => self.type_i64(), width => bug!("Unsupported c_int_width: {}", width), } } diff --git a/compiler/rustc_const_eval/src/check_consts/check.rs b/compiler/rustc_const_eval/src/check_consts/check.rs index 9719d4052590..4f252f3ccd48 100644 --- a/compiler/rustc_const_eval/src/check_consts/check.rs +++ b/compiler/rustc_const_eval/src/check_consts/check.rs @@ -356,10 +356,7 @@ impl<'mir, 'tcx> Checker<'mir, 'tcx> { hir::ConstContext::ConstFn => true, _ => { // For indirect places, we are not creating a new permanent borrow, it's just as - // transient as the already existing one. For reborrowing references this is handled - // at the top of `visit_rvalue`, but for raw pointers we handle it here. - // Pointers/references to `static mut` and cases where the `*` is not the first - // projection also end up here. + // transient as the already existing one. // Locals with StorageDead do not live beyond the evaluation and can // thus safely be borrowed without being able to be leaked to the final // value of the constant. diff --git a/compiler/rustc_const_eval/src/interpret/intern.rs b/compiler/rustc_const_eval/src/interpret/intern.rs index 1dd96297d1fd..f0f958d069ee 100644 --- a/compiler/rustc_const_eval/src/interpret/intern.rs +++ b/compiler/rustc_const_eval/src/interpret/intern.rs @@ -227,12 +227,11 @@ pub fn intern_const_alloc_recursive<'tcx, M: CompileTimeMachine<'tcx, const_eval // Keep interning as long as there are things to intern. // We show errors if there are dangling pointers, or mutable pointers in immutable contexts - // (i.e., everything except for `static mut`). When these errors affect references, it is - // unfortunate that we show these errors here and not during validation, since validation can - // show much nicer errors. However, we do need these checks to be run on all pointers, including - // raw pointers, so we cannot rely on validation to catch them -- and since interning runs - // before validation, and interning doesn't know the type of anything, this means we can't show - // better errors. Maybe we should consider doing validation before interning in the future. + // (i.e., everything except for `static mut`). We only return these errors as a `Result` + // so that the caller can run validation, and subsequently only report interning errors + // if validation fails. Validation has the better error messages so we prefer those, but + // interning has better coverage since it "sees" *all* pointers, including raw pointers and + // references stored in unions. while let Some(prov) = todo.pop() { trace!(?prov); let alloc_id = prov.alloc_id(); @@ -279,12 +278,12 @@ pub fn intern_const_alloc_recursive<'tcx, M: CompileTimeMachine<'tcx, const_eval // when there is memory there that someone might expect to be mutable, but we make it immutable. let dangling = !is_already_global && !ecx.memory.alloc_map.contains_key(&alloc_id); if !dangling { - // Found a mutable reference inside a const where inner allocations should be + // Found a mutable pointer inside a const where inner allocations should be // immutable. if !ecx.tcx.sess.opts.unstable_opts.unleash_the_miri_inside_of_you { span_bug!( ecx.tcx.span, - "the static const safety checks accepted mutable references they should not have accepted" + "the static const safety checks accepted a mutable pointer they should not have accepted" ); } // Prefer dangling pointer errors over mutable pointer errors diff --git a/compiler/rustc_const_eval/src/interpret/intrinsics.rs b/compiler/rustc_const_eval/src/interpret/intrinsics.rs index ab27182c211a..754b2ba0d760 100644 --- a/compiler/rustc_const_eval/src/interpret/intrinsics.rs +++ b/compiler/rustc_const_eval/src/interpret/intrinsics.rs @@ -120,7 +120,7 @@ impl<'tcx, M: Machine<'tcx>> InterpCx<'tcx, M> { self.copy_op(&val, dest)?; } - sym::min_align_of_val | sym::size_of_val => { + sym::align_of_val | sym::size_of_val => { // Avoid `deref_pointer` -- this is not a deref, the ptr does not have to be // dereferenceable! let place = self.ref_to_mplace(&self.read_immediate(&args[0])?)?; @@ -129,7 +129,7 @@ impl<'tcx, M: Machine<'tcx>> InterpCx<'tcx, M> { .ok_or_else(|| err_unsup_format!("`extern type` does not have known layout"))?; let result = match intrinsic_name { - sym::min_align_of_val => align.bytes(), + sym::align_of_val => align.bytes(), sym::size_of_val => size.bytes(), _ => bug!(), }; diff --git a/compiler/rustc_const_eval/src/interpret/util.rs b/compiler/rustc_const_eval/src/interpret/util.rs index 83a170926191..99add01f95c6 100644 --- a/compiler/rustc_const_eval/src/interpret/util.rs +++ b/compiler/rustc_const_eval/src/interpret/util.rs @@ -58,9 +58,9 @@ pub enum MaybeEnteredSpan { macro_rules! enter_trace_span { ($machine:ident, $($tt:tt)*) => { if $machine::TRACING_ENABLED { - $crate::interpret::tracing_utils::MaybeEnteredSpan::Some(tracing::info_span!($($tt)*).entered()) + $crate::interpret::util::MaybeEnteredSpan::Some(tracing::info_span!($($tt)*).entered()) } else { - $crate::interpret::tracing_utils::MaybeEnteredSpan::None + $crate::interpret::util::MaybeEnteredSpan::None } } } diff --git a/compiler/rustc_data_structures/src/thousands/mod.rs b/compiler/rustc_data_structures/src/thousands/mod.rs index e7ab7ec2932d..b251ebe58f6b 100644 --- a/compiler/rustc_data_structures/src/thousands/mod.rs +++ b/compiler/rustc_data_structures/src/thousands/mod.rs @@ -1,16 +1,37 @@ -//! This is an extremely bare-bones alternative to the `thousands` crate on -//! crates.io, for printing large numbers in a readable fashion. +//! This is a bare-bones alternative to the `thousands` crate on crates.io, for +//! printing large numbers in a readable fashion. #[cfg(test)] mod tests; -// Converts the number to a string, with underscores as the thousands separator. -pub fn format_with_underscores(n: usize) -> String { - let mut s = n.to_string(); - let mut i = s.len(); - while i > 3 { +fn format_with_underscores(mut s: String) -> String { + // Ignore a leading '-'. + let start = if s.starts_with('-') { 1 } else { 0 }; + + // Stop after the first non-digit, e.g. '.' or 'e' for floats. + let non_digit = s[start..].find(|c: char| !c.is_digit(10)); + let end = if let Some(non_digit) = non_digit { start + non_digit } else { s.len() }; + + // Insert underscores within `start..end`. + let mut i = end; + while i > start + 3 { i -= 3; s.insert(i, '_'); } s } + +/// Print a `usize` with underscore separators. +pub fn usize_with_underscores(n: usize) -> String { + format_with_underscores(format!("{n}")) +} + +/// Print an `isize` with underscore separators. +pub fn isize_with_underscores(n: isize) -> String { + format_with_underscores(format!("{n}")) +} + +/// Print an `f64` with precision 1 (one decimal place) and underscore separators. +pub fn f64p1_with_underscores(n: f64) -> String { + format_with_underscores(format!("{n:.1}")) +} diff --git a/compiler/rustc_data_structures/src/thousands/tests.rs b/compiler/rustc_data_structures/src/thousands/tests.rs index 906605d9a935..0f9a648802b8 100644 --- a/compiler/rustc_data_structures/src/thousands/tests.rs +++ b/compiler/rustc_data_structures/src/thousands/tests.rs @@ -2,13 +2,51 @@ use super::*; #[test] fn test_format_with_underscores() { - assert_eq!("0", format_with_underscores(0)); - assert_eq!("1", format_with_underscores(1)); - assert_eq!("99", format_with_underscores(99)); - assert_eq!("345", format_with_underscores(345)); - assert_eq!("1_000", format_with_underscores(1_000)); - assert_eq!("12_001", format_with_underscores(12_001)); - assert_eq!("999_999", format_with_underscores(999_999)); - assert_eq!("1_000_000", format_with_underscores(1_000_000)); - assert_eq!("12_345_678", format_with_underscores(12_345_678)); + assert_eq!("", format_with_underscores("".to_string())); + assert_eq!("0", format_with_underscores("0".to_string())); + assert_eq!("12_345.67e14", format_with_underscores("12345.67e14".to_string())); + assert_eq!("-1_234.5678e10", format_with_underscores("-1234.5678e10".to_string())); + assert_eq!("------", format_with_underscores("------".to_string())); + assert_eq!("abcdefgh", format_with_underscores("abcdefgh".to_string())); + assert_eq!("-1b", format_with_underscores("-1b".to_string())); + assert_eq!("-3_456xyz", format_with_underscores("-3456xyz".to_string())); +} + +#[test] +fn test_usize_with_underscores() { + assert_eq!("0", usize_with_underscores(0)); + assert_eq!("1", usize_with_underscores(1)); + assert_eq!("99", usize_with_underscores(99)); + assert_eq!("345", usize_with_underscores(345)); + assert_eq!("1_000", usize_with_underscores(1_000)); + assert_eq!("12_001", usize_with_underscores(12_001)); + assert_eq!("999_999", usize_with_underscores(999_999)); + assert_eq!("1_000_000", usize_with_underscores(1_000_000)); + assert_eq!("12_345_678", usize_with_underscores(12_345_678)); +} + +#[test] +fn test_isize_with_underscores() { + assert_eq!("0", isize_with_underscores(0)); + assert_eq!("-1", isize_with_underscores(-1)); + assert_eq!("99", isize_with_underscores(99)); + assert_eq!("345", isize_with_underscores(345)); + assert_eq!("-1_000", isize_with_underscores(-1_000)); + assert_eq!("12_001", isize_with_underscores(12_001)); + assert_eq!("-999_999", isize_with_underscores(-999_999)); + assert_eq!("1_000_000", isize_with_underscores(1_000_000)); + assert_eq!("-12_345_678", isize_with_underscores(-12_345_678)); +} + +#[test] +fn test_f64p1_with_underscores() { + assert_eq!("0.0", f64p1_with_underscores(0f64)); + assert_eq!("0.0", f64p1_with_underscores(0.00000001)); + assert_eq!("-0.0", f64p1_with_underscores(-0.00000001)); + assert_eq!("1.0", f64p1_with_underscores(0.9999999)); + assert_eq!("-1.0", f64p1_with_underscores(-0.9999999)); + assert_eq!("345.5", f64p1_with_underscores(345.4999999)); + assert_eq!("-100_000.0", f64p1_with_underscores(-100_000f64)); + assert_eq!("123_456_789.1", f64p1_with_underscores(123456789.123456789)); + assert_eq!("-123_456_789.1", f64p1_with_underscores(-123456789.123456789)); } diff --git a/compiler/rustc_errors/src/lib.rs b/compiler/rustc_errors/src/lib.rs index 133bd361ee77..9f72fc4705ae 100644 --- a/compiler/rustc_errors/src/lib.rs +++ b/compiler/rustc_errors/src/lib.rs @@ -60,8 +60,9 @@ pub use rustc_error_messages::{ SubdiagMessage, fallback_fluent_bundle, fluent_bundle, }; use rustc_hashes::Hash128; -use rustc_lint_defs::LintExpectationId; +use rustc_hir::HirId; pub use rustc_lint_defs::{Applicability, listify, pluralize}; +use rustc_lint_defs::{Lint, LintExpectationId}; use rustc_macros::{Decodable, Encodable}; pub use rustc_span::ErrorGuaranteed; pub use rustc_span::fatal_error::{FatalError, FatalErrorMarker}; @@ -101,6 +102,19 @@ rustc_data_structures::static_assert_size!(PResult<'_, ()>, 24); #[cfg(target_pointer_width = "64")] rustc_data_structures::static_assert_size!(PResult<'_, bool>, 24); +/// Used to avoid depending on `rustc_middle` in `rustc_attr_parsing`. +/// Always the `TyCtxt`. +pub trait LintEmitter: Copy { + #[track_caller] + fn emit_node_span_lint( + self, + lint: &'static Lint, + hir_id: HirId, + span: impl Into, + decorator: impl for<'a> LintDiagnostic<'a, ()>, + ); +} + #[derive(Debug, PartialEq, Eq, Clone, Copy, Hash, Encodable, Decodable)] pub enum SuggestionStyle { /// Hide the suggested code when displaying this suggestion inline. diff --git a/compiler/rustc_expand/messages.ftl b/compiler/rustc_expand/messages.ftl index f26c7c1ba0bc..8b7c47dad991 100644 --- a/compiler/rustc_expand/messages.ftl +++ b/compiler/rustc_expand/messages.ftl @@ -62,6 +62,7 @@ expand_feature_not_allowed = expand_feature_removed = feature has been removed .label = feature has been removed + .note = removed in {$removed_rustc_version} (you are using {$current_rustc_version}){$pull_note} .reason = {$reason} expand_glob_delegation_outside_impls = @@ -112,7 +113,7 @@ expand_meta_var_expr_unrecognized_var = variable `{$key}` is not recognized in meta-variable expression expand_missing_fragment_specifier = missing fragment specifier - .note = fragment specifiers must be specified in the 2024 edition + .note = fragment specifiers must be provided .suggestion_add_fragspec = try adding a specifier here .valid = {$valid} diff --git a/compiler/rustc_expand/src/base.rs b/compiler/rustc_expand/src/base.rs index c7b975d8f3e4..311dadb53c42 100644 --- a/compiler/rustc_expand/src/base.rs +++ b/compiler/rustc_expand/src/base.rs @@ -12,7 +12,7 @@ use rustc_ast::tokenstream::TokenStream; use rustc_ast::visit::{AssocCtxt, Visitor}; use rustc_ast::{self as ast, AttrVec, Attribute, HasAttrs, Item, NodeId, PatKind}; use rustc_attr_data_structures::{AttributeKind, Deprecation, Stability, find_attr}; -use rustc_data_structures::fx::FxIndexMap; +use rustc_data_structures::fx::{FxHashMap, FxIndexMap}; use rustc_data_structures::sync; use rustc_errors::{DiagCtxtHandle, ErrorGuaranteed, PResult}; use rustc_feature::Features; @@ -727,6 +727,7 @@ pub enum SyntaxExtensionKind { /// A trivial attribute "macro" that does nothing, /// only keeps the attribute and marks it as inert, /// thus making it ineligible for further expansion. + /// E.g. `#[default]`, `#[rustfmt::skip]`. NonMacroAttr, /// A token-based derive macro. @@ -1189,6 +1190,8 @@ pub struct ExtCtxt<'a> { /// in the AST, but insert it here so that we know /// not to expand it again. pub(super) expanded_inert_attrs: MarkedAttrs, + /// `-Zmacro-stats` data. + pub macro_stats: FxHashMap<(Symbol, MacroKind), crate::stats::MacroStat>, // njn: quals } impl<'a> ExtCtxt<'a> { @@ -1218,6 +1221,7 @@ impl<'a> ExtCtxt<'a> { expansions: FxIndexMap::default(), expanded_inert_attrs: MarkedAttrs::new(), buffered_early_lint: vec![], + macro_stats: Default::default(), } } diff --git a/compiler/rustc_expand/src/config.rs b/compiler/rustc_expand/src/config.rs index c50ab5959e25..9a359e9b0310 100644 --- a/compiler/rustc_expand/src/config.rs +++ b/compiler/rustc_expand/src/config.rs @@ -80,9 +80,20 @@ pub fn features(sess: &Session, krate_attrs: &[Attribute], crate_name: Symbol) - // If the enabled feature has been removed, issue an error. if let Some(f) = REMOVED_LANG_FEATURES.iter().find(|f| name == f.feature.name) { + let pull_note = if let Some(pull) = f.pull { + format!( + "; see for more information", + pull + ) + } else { + "".to_owned() + }; sess.dcx().emit_err(FeatureRemoved { span: mi.span(), reason: f.reason.map(|reason| FeatureRemovedReason { reason }), + removed_rustc_version: f.feature.since, + current_rustc_version: sess.cfg_version, + pull_note, }); continue; } diff --git a/compiler/rustc_expand/src/errors.rs b/compiler/rustc_expand/src/errors.rs index 89bdc7b6dfa5..ec0af67c0463 100644 --- a/compiler/rustc_expand/src/errors.rs +++ b/compiler/rustc_expand/src/errors.rs @@ -154,12 +154,16 @@ pub(crate) struct HelperAttributeNameInvalid { #[derive(Diagnostic)] #[diag(expand_feature_removed, code = E0557)] +#[note] pub(crate) struct FeatureRemoved<'a> { #[primary_span] #[label] pub span: Span, #[subdiagnostic] pub reason: Option>, + pub removed_rustc_version: &'a str, + pub current_rustc_version: &'a str, + pub pull_note: String, } #[derive(Subdiagnostic)] diff --git a/compiler/rustc_expand/src/expand.rs b/compiler/rustc_expand/src/expand.rs index 569165a64e52..3cfeb01ea477 100644 --- a/compiler/rustc_expand/src/expand.rs +++ b/compiler/rustc_expand/src/expand.rs @@ -42,13 +42,22 @@ use crate::module::{ DirOwnership, ParsedExternalMod, mod_dir_path, mod_file_path_from_attr, parse_external_mod, }; use crate::placeholders::{PlaceholderExpander, placeholder}; +use crate::stats::*; macro_rules! ast_fragments { ( $($Kind:ident($AstTy:ty) { $kind_name:expr; - $(one fn $mut_visit_ast:ident; fn $visit_ast:ident;)? - $(many fn $flat_map_ast_elt:ident; fn $visit_ast_elt:ident($($args:tt)*);)? + $(one + fn $mut_visit_ast:ident; + fn $visit_ast:ident; + fn $ast_to_string:path; + )? + $(many + fn $flat_map_ast_elt:ident; + fn $visit_ast_elt:ident($($args:tt)*); + fn $ast_to_string_elt:path; + )? fn $make_ast:ident; })* ) => { @@ -61,7 +70,7 @@ macro_rules! ast_fragments { } /// "Discriminant" of an AST fragment. - #[derive(Copy, Clone, PartialEq, Eq)] + #[derive(Copy, Clone, Debug, PartialEq, Eq)] pub enum AstFragmentKind { OptExpr, MethodReceiverExpr, @@ -151,6 +160,21 @@ macro_rules! ast_fragments { } V::Result::output() } + + pub(crate) fn to_string(&self) -> String { + match self { + AstFragment::OptExpr(Some(expr)) => pprust::expr_to_string(expr), + AstFragment::OptExpr(None) => unreachable!(), + AstFragment::MethodReceiverExpr(expr) => pprust::expr_to_string(expr), + $($(AstFragment::$Kind(ast) => $ast_to_string(ast),)?)* + $($( + AstFragment::$Kind(ast) => { + // The closure unwraps a `P` if present, or does nothing otherwise. + elems_to_string(&*ast, |ast| $ast_to_string_elt(&*ast)) + } + )?)* + } + } } impl<'a> MacResult for crate::mbe::macro_rules::ParserAnyMacro<'a> { @@ -163,76 +187,98 @@ macro_rules! ast_fragments { } ast_fragments! { - Expr(P) { "expression"; one fn visit_expr; fn visit_expr; fn make_expr; } - Pat(P) { "pattern"; one fn visit_pat; fn visit_pat; fn make_pat; } - Ty(P) { "type"; one fn visit_ty; fn visit_ty; fn make_ty; } + Expr(P) { + "expression"; + one fn visit_expr; fn visit_expr; fn pprust::expr_to_string; + fn make_expr; + } + Pat(P) { + "pattern"; + one fn visit_pat; fn visit_pat; fn pprust::pat_to_string; + fn make_pat; + } + Ty(P) { + "type"; + one fn visit_ty; fn visit_ty; fn pprust::ty_to_string; + fn make_ty; + } Stmts(SmallVec<[ast::Stmt; 1]>) { - "statement"; many fn flat_map_stmt; fn visit_stmt(); fn make_stmts; + "statement"; + many fn flat_map_stmt; fn visit_stmt(); fn pprust::stmt_to_string; + fn make_stmts; } Items(SmallVec<[P; 1]>) { - "item"; many fn flat_map_item; fn visit_item(); fn make_items; + "item"; + many fn flat_map_item; fn visit_item(); fn pprust::item_to_string; + fn make_items; } TraitItems(SmallVec<[P; 1]>) { "trait item"; - many fn flat_map_assoc_item; - fn visit_assoc_item(AssocCtxt::Trait); + many fn flat_map_assoc_item; fn visit_assoc_item(AssocCtxt::Trait); + fn pprust::assoc_item_to_string; fn make_trait_items; } ImplItems(SmallVec<[P; 1]>) { "impl item"; - many fn flat_map_assoc_item; - fn visit_assoc_item(AssocCtxt::Impl { of_trait: false }); + many fn flat_map_assoc_item; fn visit_assoc_item(AssocCtxt::Impl { of_trait: false }); + fn pprust::assoc_item_to_string; fn make_impl_items; } TraitImplItems(SmallVec<[P; 1]>) { "impl item"; - many fn flat_map_assoc_item; - fn visit_assoc_item(AssocCtxt::Impl { of_trait: true }); + many fn flat_map_assoc_item; fn visit_assoc_item(AssocCtxt::Impl { of_trait: true }); + fn pprust::assoc_item_to_string; fn make_trait_impl_items; } ForeignItems(SmallVec<[P; 1]>) { "foreign item"; - many fn flat_map_foreign_item; - fn visit_foreign_item(); + many fn flat_map_foreign_item; fn visit_foreign_item(); fn pprust::foreign_item_to_string; fn make_foreign_items; } Arms(SmallVec<[ast::Arm; 1]>) { - "match arm"; many fn flat_map_arm; fn visit_arm(); fn make_arms; + "match arm"; + many fn flat_map_arm; fn visit_arm(); fn unreachable_to_string; + fn make_arms; } ExprFields(SmallVec<[ast::ExprField; 1]>) { - "field expression"; many fn flat_map_expr_field; fn visit_expr_field(); fn make_expr_fields; + "field expression"; + many fn flat_map_expr_field; fn visit_expr_field(); fn unreachable_to_string; + fn make_expr_fields; } PatFields(SmallVec<[ast::PatField; 1]>) { "field pattern"; - many fn flat_map_pat_field; - fn visit_pat_field(); + many fn flat_map_pat_field; fn visit_pat_field(); fn unreachable_to_string; fn make_pat_fields; } GenericParams(SmallVec<[ast::GenericParam; 1]>) { "generic parameter"; - many fn flat_map_generic_param; - fn visit_generic_param(); + many fn flat_map_generic_param; fn visit_generic_param(); fn unreachable_to_string; fn make_generic_params; } Params(SmallVec<[ast::Param; 1]>) { - "function parameter"; many fn flat_map_param; fn visit_param(); fn make_params; + "function parameter"; + many fn flat_map_param; fn visit_param(); fn unreachable_to_string; + fn make_params; } FieldDefs(SmallVec<[ast::FieldDef; 1]>) { "field"; - many fn flat_map_field_def; - fn visit_field_def(); + many fn flat_map_field_def; fn visit_field_def(); fn unreachable_to_string; fn make_field_defs; } Variants(SmallVec<[ast::Variant; 1]>) { - "variant"; many fn flat_map_variant; fn visit_variant(); fn make_variants; + "variant"; many fn flat_map_variant; fn visit_variant(); fn unreachable_to_string; + fn make_variants; } WherePredicates(SmallVec<[ast::WherePredicate; 1]>) { "where predicate"; - many fn flat_map_where_predicate; - fn visit_where_predicate(); + many fn flat_map_where_predicate; fn visit_where_predicate(); fn unreachable_to_string; fn make_where_predicates; - } - Crate(ast::Crate) { "crate"; one fn visit_crate; fn visit_crate; fn make_crate; } + } + Crate(ast::Crate) { + "crate"; + one fn visit_crate; fn visit_crate; fn unreachable_to_string; + fn make_crate; + } } pub enum SupportsMacroExpansion { @@ -270,7 +316,7 @@ impl AstFragmentKind { } } - fn expect_from_annotatables>( + pub(crate) fn expect_from_annotatables>( self, items: I, ) -> AstFragment { @@ -686,13 +732,26 @@ impl<'a, 'b> MacroExpander<'a, 'b> { return ExpandResult::Ready(invoc.fragment_kind.dummy(invoc.span(), guar)); } + let macro_stats = self.cx.sess.opts.unstable_opts.macro_stats; + let (fragment_kind, span) = (invoc.fragment_kind, invoc.span()); ExpandResult::Ready(match invoc.kind { InvocationKind::Bang { mac, span } => match ext { SyntaxExtensionKind::Bang(expander) => { match expander.expand(self.cx, span, mac.args.tokens.clone()) { Ok(tok_result) => { - self.parse_ast_fragment(tok_result, fragment_kind, &mac.path, span) + let fragment = + self.parse_ast_fragment(tok_result, fragment_kind, &mac.path, span); + if macro_stats { + update_bang_macro_stats( + self.cx, + fragment_kind, + span, + mac, + &fragment, + ); + } + fragment } Err(guar) => return ExpandResult::Ready(fragment_kind.dummy(span, guar)), } @@ -708,13 +767,15 @@ impl<'a, 'b> MacroExpander<'a, 'b> { }); } }; - let result = if let Some(result) = fragment_kind.make_from(tok_result) { - result + if let Some(fragment) = fragment_kind.make_from(tok_result) { + if macro_stats { + update_bang_macro_stats(self.cx, fragment_kind, span, mac, &fragment); + } + fragment } else { let guar = self.error_wrong_fragment_kind(fragment_kind, &mac, span); fragment_kind.dummy(span, guar) - }; - result + } } _ => unreachable!(), }, @@ -746,24 +807,39 @@ impl<'a, 'b> MacroExpander<'a, 'b> { } _ => item.to_tokens(), }; - let attr_item = attr.unwrap_normal_item(); + let attr_item = attr.get_normal_item(); if let AttrArgs::Eq { .. } = attr_item.args { self.cx.dcx().emit_err(UnsupportedKeyValue { span }); } let inner_tokens = attr_item.args.inner_tokens(); match expander.expand(self.cx, span, inner_tokens, tokens) { - Ok(tok_result) => self.parse_ast_fragment( - tok_result, - fragment_kind, - &attr_item.path, - span, - ), + Ok(tok_result) => { + let fragment = self.parse_ast_fragment( + tok_result, + fragment_kind, + &attr_item.path, + span, + ); + if macro_stats { + update_attr_macro_stats( + self.cx, + fragment_kind, + span, + &attr_item.path, + &attr, + item, + &fragment, + ); + } + fragment + } Err(guar) => return ExpandResult::Ready(fragment_kind.dummy(span, guar)), } } SyntaxExtensionKind::LegacyAttr(expander) => { match validate_attr::parse_meta(&self.cx.sess.psess, &attr) { Ok(meta) => { + let item_clone = macro_stats.then(|| item.clone()); let items = match expander.expand(self.cx, span, &meta, item, false) { ExpandResult::Ready(items) => items, ExpandResult::Retry(item) => { @@ -782,7 +858,19 @@ impl<'a, 'b> MacroExpander<'a, 'b> { let guar = self.cx.dcx().emit_err(RemoveExprNotSupported { span }); fragment_kind.dummy(span, guar) } else { - fragment_kind.expect_from_annotatables(items) + let fragment = fragment_kind.expect_from_annotatables(items); + if macro_stats { + update_attr_macro_stats( + self.cx, + fragment_kind, + span, + &meta.path, + &attr, + item_clone.unwrap(), + &fragment, + ); + } + fragment } } Err(err) => { @@ -792,6 +880,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> { } } SyntaxExtensionKind::NonMacroAttr => { + // `-Zmacro-stats` ignores these because they don't do any real expansion. self.cx.expanded_inert_attrs.mark(&attr); item.visit_attrs(|attrs| attrs.insert(pos, attr)); fragment_kind.expect_from_annotatables(iter::once(item)) @@ -822,7 +911,17 @@ impl<'a, 'b> MacroExpander<'a, 'b> { }); } }; - fragment_kind.expect_from_annotatables(items) + let fragment = fragment_kind.expect_from_annotatables(items); + if macro_stats { + update_derive_macro_stats( + self.cx, + fragment_kind, + span, + &meta.path, + &fragment, + ); + } + fragment } _ => unreachable!(), }, @@ -852,6 +951,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> { let single_delegations = build_single_delegations::( self.cx, deleg, &item, &suffixes, item.span, true, ); + // `-Zmacro-stats` ignores these because they don't seem important. fragment_kind.expect_from_annotatables( single_delegations .map(|item| Annotatable::AssocItem(P(item), AssocCtxt::Impl { of_trait })), diff --git a/compiler/rustc_expand/src/lib.rs b/compiler/rustc_expand/src/lib.rs index 515d82296caf..64be7649775f 100644 --- a/compiler/rustc_expand/src/lib.rs +++ b/compiler/rustc_expand/src/lib.rs @@ -20,6 +20,7 @@ mod errors; mod mbe; mod placeholders; mod proc_macro_server; +mod stats; pub use mbe::macro_rules::compile_declarative_macro; pub mod base; diff --git a/compiler/rustc_expand/src/mbe/macro_check.rs b/compiler/rustc_expand/src/mbe/macro_check.rs index 1a2db233b7a6..3cd803c3e848 100644 --- a/compiler/rustc_expand/src/mbe/macro_check.rs +++ b/compiler/rustc_expand/src/mbe/macro_check.rs @@ -112,9 +112,8 @@ use rustc_ast::{DUMMY_NODE_ID, NodeId}; use rustc_data_structures::fx::FxHashMap; use rustc_errors::MultiSpan; use rustc_lint_defs::BuiltinLintDiag; -use rustc_session::lint::builtin::{META_VARIABLE_MISUSE, MISSING_FRAGMENT_SPECIFIER}; +use rustc_session::lint::builtin::META_VARIABLE_MISUSE; use rustc_session::parse::ParseSess; -use rustc_span::edition::Edition; use rustc_span::{ErrorGuaranteed, MacroRulesNormalizedIdent, Span, kw}; use smallvec::SmallVec; @@ -266,23 +265,11 @@ fn check_binders( // Similarly, this can only happen when checking a toplevel macro. TokenTree::MetaVarDecl(span, name, kind) => { if kind.is_none() && node_id != DUMMY_NODE_ID { - // FIXME: Report this as a hard error eventually and remove equivalent errors from - // `parse_tt_inner` and `nameize`. Until then the error may be reported twice, once - // as a hard error and then once as a buffered lint. - if span.edition() >= Edition::Edition2024 { - psess.dcx().emit_err(errors::MissingFragmentSpecifier { - span, - add_span: span.shrink_to_hi(), - valid: VALID_FRAGMENT_NAMES_MSG, - }); - } else { - psess.buffer_lint( - MISSING_FRAGMENT_SPECIFIER, - span, - node_id, - BuiltinLintDiag::MissingFragmentSpecifier, - ); - } + psess.dcx().emit_err(errors::MissingFragmentSpecifier { + span, + add_span: span.shrink_to_hi(), + valid: VALID_FRAGMENT_NAMES_MSG, + }); } if !macros.is_empty() { psess.dcx().span_bug(span, "unexpected MetaVarDecl in nested lhs"); diff --git a/compiler/rustc_expand/src/stats.rs b/compiler/rustc_expand/src/stats.rs new file mode 100644 index 000000000000..6b2ad30dffd0 --- /dev/null +++ b/compiler/rustc_expand/src/stats.rs @@ -0,0 +1,171 @@ +use std::iter; + +use rustc_ast::ptr::P; +use rustc_ast::{self as ast, DUMMY_NODE_ID, Expr, ExprKind}; +use rustc_ast_pretty::pprust; +use rustc_span::hygiene::{ExpnKind, MacroKind}; +use rustc_span::{Span, Symbol, kw, sym}; +use smallvec::SmallVec; + +use crate::base::{Annotatable, ExtCtxt}; +use crate::expand::{AstFragment, AstFragmentKind}; + +#[derive(Default)] +pub struct MacroStat { + /// Number of uses of the macro. + pub uses: usize, + + /// Net increase in number of lines of code (when pretty-printed), i.e. + /// `lines(output) - lines(invocation)`. Can be negative because a macro + /// output may be smaller than the invocation. + pub lines: isize, + + /// Net increase in number of lines of code (when pretty-printed), i.e. + /// `bytes(output) - bytes(invocation)`. Can be negative because a macro + /// output may be smaller than the invocation. + pub bytes: isize, +} + +pub(crate) fn elems_to_string(elems: &SmallVec<[T; 1]>, f: impl Fn(&T) -> String) -> String { + let mut s = String::new(); + for (i, elem) in elems.iter().enumerate() { + if i > 0 { + s.push('\n'); + } + s.push_str(&f(elem)); + } + s +} + +pub(crate) fn unreachable_to_string(_: &T) -> String { + unreachable!() +} + +pub(crate) fn update_bang_macro_stats( + ecx: &mut ExtCtxt<'_>, + fragment_kind: AstFragmentKind, + span: Span, + mac: P, + fragment: &AstFragment, +) { + // Does this path match any of the include macros, e.g. `include!`? + // Ignore them. They would have large numbers but are entirely + // unsurprising and uninteresting. + let is_include_path = mac.path == sym::include + || mac.path == sym::include_bytes + || mac.path == sym::include_str + || mac.path == [sym::std, sym::include].as_slice() // std::include + || mac.path == [sym::std, sym::include_bytes].as_slice() // std::include_bytes + || mac.path == [sym::std, sym::include_str].as_slice(); // std::include_str + if is_include_path { + return; + } + + // The call itself (e.g. `println!("hi")`) is the input. Need to wrap + // `mac` in something printable; `ast::Expr` is as good as anything + // else. + let expr = Expr { + id: DUMMY_NODE_ID, + kind: ExprKind::MacCall(mac), + span: Default::default(), + attrs: Default::default(), + tokens: None, + }; + let input = pprust::expr_to_string(&expr); + + // Get `mac` back out of `expr`. + let ast::Expr { kind: ExprKind::MacCall(mac), .. } = expr else { unreachable!() }; + + update_macro_stats(ecx, MacroKind::Bang, fragment_kind, span, &mac.path, &input, fragment); +} + +pub(crate) fn update_attr_macro_stats( + ecx: &mut ExtCtxt<'_>, + fragment_kind: AstFragmentKind, + span: Span, + path: &ast::Path, + attr: &ast::Attribute, + item: Annotatable, + fragment: &AstFragment, +) { + // Does this path match `#[derive(...)]` in any of its forms? If so, + // ignore it because the individual derives will go through the + // `Invocation::Derive` handling separately. + let is_derive_path = *path == sym::derive + // ::core::prelude::v1::derive + || *path == [kw::PathRoot, sym::core, sym::prelude, sym::v1, sym::derive].as_slice(); + if is_derive_path { + return; + } + + // The attribute plus the item itself constitute the input, which we + // measure. + let input = format!( + "{}\n{}", + pprust::attribute_to_string(attr), + fragment_kind.expect_from_annotatables(iter::once(item)).to_string(), + ); + update_macro_stats(ecx, MacroKind::Attr, fragment_kind, span, path, &input, fragment); +} + +pub(crate) fn update_derive_macro_stats( + ecx: &mut ExtCtxt<'_>, + fragment_kind: AstFragmentKind, + span: Span, + path: &ast::Path, + fragment: &AstFragment, +) { + // Use something like `#[derive(Clone)]` for the measured input, even + // though it may have actually appeared in a multi-derive attribute + // like `#[derive(Clone, Copy, Debug)]`. + let input = format!("#[derive({})]", pprust::path_to_string(path)); + update_macro_stats(ecx, MacroKind::Derive, fragment_kind, span, path, &input, fragment); +} + +pub(crate) fn update_macro_stats( + ecx: &mut ExtCtxt<'_>, + macro_kind: MacroKind, + fragment_kind: AstFragmentKind, + span: Span, + path: &ast::Path, + input: &str, + fragment: &AstFragment, +) { + fn lines_and_bytes(s: &str) -> (usize, usize) { + (s.trim_end().split('\n').count(), s.len()) + } + + // Measure the size of the output by pretty-printing it and counting + // the lines and bytes. + let name = Symbol::intern(&pprust::path_to_string(path)); + let output = fragment.to_string(); + let (in_l, in_b) = lines_and_bytes(input); + let (out_l, out_b) = lines_and_bytes(&output); + + // This code is useful for debugging `-Zmacro-stats`. For every + // invocation it prints the full input and output. + if false { + let name = ExpnKind::Macro(macro_kind, name).descr(); + let crate_name = &ecx.ecfg.crate_name; + let span = ecx + .sess + .source_map() + .span_to_string(span, rustc_span::FileNameDisplayPreference::Local); + eprint!( + "\ + -------------------------------\n\ + {name}: [{crate_name}] ({fragment_kind:?}) {span}\n\ + -------------------------------\n\ + {input}\n\ + -- ({in_l} lines, {in_b} bytes) --> ({out_l} lines, {out_b} bytes) --\n\ + {output}\n\ + " + ); + } + + // The recorded size is the difference between the input and the output. + let entry = ecx.macro_stats.entry((name, macro_kind)).or_insert(MacroStat::default()); + entry.uses += 1; + entry.lines += out_l as isize - in_l as isize; + entry.bytes += out_b as isize - in_b as isize; +} diff --git a/compiler/rustc_feature/src/accepted.rs b/compiler/rustc_feature/src/accepted.rs index 10c5cb194f40..b1c185220f45 100644 --- a/compiler/rustc_feature/src/accepted.rs +++ b/compiler/rustc_feature/src/accepted.rs @@ -259,6 +259,8 @@ declare_features! ( /// Allows some increased flexibility in the name resolution rules, /// especially around globs and shadowing (RFC 1560). (accepted, item_like_imports, "1.15.0", Some(35120)), + // Allows using the `kl` and `widekl` target features and the associated intrinsics + (accepted, keylocker_x86, "CURRENT_RUSTC_VERSION", Some(134813)), /// Allows `'a: { break 'a; }`. (accepted, label_break_value, "1.65.0", Some(48594)), /// Allows `let...else` statements. diff --git a/compiler/rustc_feature/src/builtin_attrs.rs b/compiler/rustc_feature/src/builtin_attrs.rs index c117e0fcf7cc..73a21789c5d2 100644 --- a/compiler/rustc_feature/src/builtin_attrs.rs +++ b/compiler/rustc_feature/src/builtin_attrs.rs @@ -9,7 +9,7 @@ use rustc_data_structures::fx::FxHashMap; use rustc_span::edition::Edition; use rustc_span::{Symbol, sym}; -use crate::{Features, Stability}; +use crate::Features; type GateFn = fn(&Features) -> bool; @@ -94,34 +94,23 @@ pub enum AttributeSafety { Unsafe { unsafe_since: Option }, } -#[derive(Clone, Copy)] +#[derive(Clone, Debug, Copy)] pub enum AttributeGate { - /// Is gated by a given feature gate, reason - /// and function to check if enabled - Gated(Stability, Symbol, &'static str, fn(&Features) -> bool), - + /// A gated attribute which requires a feature gate to be enabled. + Gated { + /// The feature gate, for example `#![feature(rustc_attrs)]` for rustc_* attributes. + feature: Symbol, + /// The error message displayed when an attempt is made to use the attribute without its feature gate. + message: &'static str, + /// Check function to be called during the `PostExpansionVisitor` pass. + check: fn(&Features) -> bool, + /// Notes to be displayed when an attempt is made to use the attribute without its feature gate. + notes: &'static [&'static str], + }, /// Ungated attribute, can be used on all release channels Ungated, } -// fn() is not Debug -impl std::fmt::Debug for AttributeGate { - fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match *self { - Self::Gated(ref stab, name, expl, _) => { - write!(fmt, "Gated({stab:?}, {name}, {expl})") - } - Self::Ungated => write!(fmt, "Ungated"), - } - } -} - -impl AttributeGate { - fn is_deprecated(&self) -> bool { - matches!(*self, Self::Gated(Stability::Deprecated(_, _), ..)) - } -} - /// A template that the attribute input must match. /// Only top-level shape (`#[attr]` vs `#[attr(...)]` vs `#[attr = ...]`) is considered now. #[derive(Clone, Copy, Default)] @@ -247,7 +236,7 @@ macro_rules! ungated { } macro_rules! gated { - (unsafe $attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $gate:ident, $msg:expr $(,)?) => { + (unsafe $attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $gate:ident, $message:expr $(,)?) => { BuiltinAttribute { name: sym::$attr, encode_cross_crate: $encode_cross_crate, @@ -255,10 +244,15 @@ macro_rules! gated { safety: AttributeSafety::Unsafe { unsafe_since: None }, template: $tpl, duplicates: $duplicates, - gate: Gated(Stability::Unstable, sym::$gate, $msg, Features::$gate), + gate: Gated { + feature: sym::$gate, + message: $message, + check: Features::$gate, + notes: &[], + }, } }; - (unsafe $attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $msg:expr $(,)?) => { + (unsafe $attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $message:expr $(,)?) => { BuiltinAttribute { name: sym::$attr, encode_cross_crate: $encode_cross_crate, @@ -266,10 +260,15 @@ macro_rules! gated { safety: AttributeSafety::Unsafe { unsafe_since: None }, template: $tpl, duplicates: $duplicates, - gate: Gated(Stability::Unstable, sym::$attr, $msg, Features::$attr), + gate: Gated { + feature: sym::$attr, + message: $message, + check: Features::$attr, + notes: &[], + }, } }; - ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $gate:ident, $msg:expr $(,)?) => { + ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $gate:ident, $message:expr $(,)?) => { BuiltinAttribute { name: sym::$attr, encode_cross_crate: $encode_cross_crate, @@ -277,10 +276,15 @@ macro_rules! gated { safety: AttributeSafety::Normal, template: $tpl, duplicates: $duplicates, - gate: Gated(Stability::Unstable, sym::$gate, $msg, Features::$gate), + gate: Gated { + feature: sym::$gate, + message: $message, + check: Features::$gate, + notes: &[], + }, } }; - ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $msg:expr $(,)?) => { + ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $message:expr $(,)?) => { BuiltinAttribute { name: sym::$attr, encode_cross_crate: $encode_cross_crate, @@ -288,7 +292,12 @@ macro_rules! gated { safety: AttributeSafety::Normal, template: $tpl, duplicates: $duplicates, - gate: Gated(Stability::Unstable, sym::$attr, $msg, Features::$attr), + gate: Gated { + feature: sym::$attr, + message: $message, + check: Features::$attr, + notes: &[], + }, } }; } @@ -304,12 +313,11 @@ macro_rules! rustc_attr { concat!( "the `#[", stringify!($attr), - "]` attribute is just used for rustc unit tests \ - and will never be stable", + "]` attribute is used for rustc unit tests" ), ) }; - ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $msg:expr $(,)?) => { + ($attr:ident, $typ:expr, $tpl:expr, $duplicates:expr, $encode_cross_crate:expr, $($notes:expr),* $(,)?) => { BuiltinAttribute { name: sym::$attr, encode_cross_crate: $encode_cross_crate, @@ -317,7 +325,17 @@ macro_rules! rustc_attr { safety: AttributeSafety::Normal, template: $tpl, duplicates: $duplicates, - gate: Gated(Stability::Unstable, sym::rustc_attrs, $msg, Features::rustc_attrs), + gate: Gated { + feature: sym::rustc_attrs, + message: "use of an internal attribute", + check: Features::rustc_attrs, + notes: &[ + concat!("the `#[", + stringify!($attr), + "]` attribute is an internal implementation detail that will never be stable"), + $($notes),* + ] + }, } }; } @@ -328,9 +346,6 @@ macro_rules! experimental { }; } -const IMPL_DETAIL: &str = "internal implementation detail"; -const INTERNAL_UNSTABLE: &str = "this is an internal attribute that will never be stable"; - #[derive(PartialEq)] pub enum EncodeCrossCrate { Yes, @@ -668,7 +683,7 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_deprecated_safe_2024, Normal, template!(List: r#"audit_that = "...""#), ErrorFollowing, EncodeCrossCrate::Yes, - "rustc_deprecated_safe_2024 is supposed to be used in libstd only", + "`#[rustc_deprecated_safe_2024]` is used to declare functions unsafe across the edition 2024 boundary", ), rustc_attr!( rustc_pub_transparent, Normal, template!(Word), @@ -695,7 +710,7 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ErrorFollowing, EncodeCrossCrate::No, "`rustc_never_type_options` is used to experiment with never type fallback and work on \ - never type stabilization, and will never be stable" + never type stabilization" ), // ========================================================================== @@ -704,23 +719,23 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_allocator, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL + EncodeCrossCrate::No, ), rustc_attr!( rustc_nounwind, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL + EncodeCrossCrate::No, ), rustc_attr!( rustc_reallocator, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL + EncodeCrossCrate::No, ), rustc_attr!( rustc_deallocator, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL + EncodeCrossCrate::No, ), rustc_attr!( rustc_allocator_zeroed, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL + EncodeCrossCrate::No, ), gated!( default_lib_allocator, Normal, template!(Word), WarnFollowing, @@ -762,7 +777,7 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), rustc_attr!( rustc_std_internal_symbol, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, INTERNAL_UNSTABLE + EncodeCrossCrate::No, ), // ========================================================================== @@ -772,11 +787,11 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_builtin_macro, Normal, template!(Word, List: "name, /*opt*/ attributes(name1, name2, ...)"), ErrorFollowing, - EncodeCrossCrate::Yes, IMPL_DETAIL + EncodeCrossCrate::Yes, ), rustc_attr!( rustc_proc_macro_decls, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, INTERNAL_UNSTABLE + EncodeCrossCrate::No, ), rustc_attr!( rustc_macro_transparency, Normal, @@ -786,7 +801,7 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_autodiff, Normal, template!(Word, List: r#""...""#), DuplicatesOk, - EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + EncodeCrossCrate::Yes, ), // Traces that are left when `cfg` and `cfg_attr` attributes are expanded. // The attributes are not gated, to avoid stability errors, but they cannot be used in stable @@ -812,54 +827,53 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ NameValueStr: "message" ), ErrorFollowing, EncodeCrossCrate::Yes, - INTERNAL_UNSTABLE + "see `#[diagnostic::on_unimplemented]` for the stable equivalent of this attribute" ), rustc_attr!( rustc_confusables, Normal, template!(List: r#""name1", "name2", ..."#), ErrorFollowing, EncodeCrossCrate::Yes, - INTERNAL_UNSTABLE, ), // Enumerates "identity-like" conversion methods to suggest on type mismatch. rustc_attr!( rustc_conversion_suggestion, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Prevents field reads in the marked trait or method to be considered // during dead code analysis. rustc_attr!( rustc_trivial_field_reads, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Used by the `rustc::potential_query_instability` lint to warn methods which // might not be stable during incremental compilation. rustc_attr!( rustc_lint_query_instability, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Used by the `rustc::untracked_query_information` lint to warn methods which // might not be stable during incremental compilation. rustc_attr!( rustc_lint_untracked_query_information, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Used by the `rustc::diagnostic_outside_of_impl` lints to assist in changes to diagnostic // APIs. Any function with this attribute will be checked by that lint. rustc_attr!( rustc_lint_diagnostics, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Used by the `rustc::bad_opt_access` lint to identify `DebuggingOptions` and `CodegenOptions` // types (as well as any others in future). rustc_attr!( rustc_lint_opt_ty, Normal, template!(Word), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // Used by the `rustc::bad_opt_access` lint on fields // types (as well as any others in future). rustc_attr!( rustc_lint_opt_deny_field_access, Normal, template!(List: "message"), - WarnFollowing, EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + WarnFollowing, EncodeCrossCrate::Yes, ), // ========================================================================== @@ -868,28 +882,30 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_promotable, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::No, IMPL_DETAIL), + EncodeCrossCrate::No, ), rustc_attr!( rustc_legacy_const_generics, Normal, template!(List: "N"), ErrorFollowing, - EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + EncodeCrossCrate::Yes, ), // Do not const-check this function's body. It will always get replaced during CTFE. rustc_attr!( rustc_do_not_const_check, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + EncodeCrossCrate::Yes, "`#[rustc_do_not_const_check]` skips const-check for this function's body", ), - // Ensure the argument to this function is &&str during const-check. rustc_attr!( rustc_const_panic_str, Normal, template!(Word), WarnFollowing, - EncodeCrossCrate::Yes, INTERNAL_UNSTABLE + EncodeCrossCrate::Yes, "`#[rustc_const_panic_str]` ensures the argument to this function is &&str during const-check", ), rustc_attr!( rustc_const_stable_indirect, Normal, - template!(Word), WarnFollowing, EncodeCrossCrate::No, IMPL_DETAIL, + template!(Word), + WarnFollowing, + EncodeCrossCrate::No, + "this is an internal implementation detail", ), rustc_attr!( rustc_intrinsic_const_stable_indirect, Normal, - template!(Word), WarnFollowing, EncodeCrossCrate::No, IMPL_DETAIL, + template!(Word), WarnFollowing, EncodeCrossCrate::No, "this is an internal implementation detail", ), gated!( rustc_allow_const_fn_unstable, Normal, @@ -905,21 +921,21 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_layout_scalar_valid_range_start, Normal, template!(List: "value"), ErrorFollowing, EncodeCrossCrate::Yes, "the `#[rustc_layout_scalar_valid_range_start]` attribute is just used to enable \ - niche optimizations in libcore and libstd and will never be stable", + niche optimizations in the standard library", ), rustc_attr!( rustc_layout_scalar_valid_range_end, Normal, template!(List: "value"), ErrorFollowing, EncodeCrossCrate::Yes, "the `#[rustc_layout_scalar_valid_range_end]` attribute is just used to enable \ - niche optimizations in libcore and libstd and will never be stable", + niche optimizations in the standard library", ), rustc_attr!( rustc_nonnull_optimization_guaranteed, Normal, template!(Word), WarnFollowing, EncodeCrossCrate::Yes, "the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document \ - guaranteed niche optimizations in libcore and libstd and will never be stable\n\ - (note that the compiler does not even check whether the type indeed is being non-null-optimized; \ - it is your responsibility to ensure that the attribute is only used on types that are optimized)", + guaranteed niche optimizations in the standard library", + "the compiler does not even check whether the type indeed is being non-null-optimized; \ + it is your responsibility to ensure that the attribute is only used on types that are optimized", ), // ========================================================================== @@ -932,17 +948,17 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_as_ptr, Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, - "#[rustc_as_ptr] is used to mark functions returning pointers to their inner allocations." + "`#[rustc_as_ptr]` is used to mark functions returning pointers to their inner allocations." ), rustc_attr!( rustc_pass_by_value, Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, - "#[rustc_pass_by_value] is used to mark types that must be passed by value instead of reference." + "`#[rustc_pass_by_value]` is used to mark types that must be passed by value instead of reference." ), rustc_attr!( rustc_never_returns_null_ptr, Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, - "#[rustc_never_returns_null_ptr] is used to mark functions returning non-null pointers." + "`#[rustc_never_returns_null_ptr]` is used to mark functions returning non-null pointers." ), rustc_attr!( rustc_no_implicit_autorefs, AttributeType::Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, @@ -950,15 +966,15 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), rustc_attr!( rustc_coherence_is_core, AttributeType::CrateLevel, template!(Word), ErrorFollowing, EncodeCrossCrate::No, - "#![rustc_coherence_is_core] allows inherent methods on builtin types, only intended to be used in `core`." + "`#![rustc_coherence_is_core]` allows inherent methods on builtin types, only intended to be used in `core`." ), rustc_attr!( rustc_coinductive, AttributeType::Normal, template!(Word), WarnFollowing, EncodeCrossCrate::No, - "#![rustc_coinductive] changes a trait to be coinductive, allowing cycles in the trait solver." + "`#[rustc_coinductive]` changes a trait to be coinductive, allowing cycles in the trait solver." ), rustc_attr!( rustc_allow_incoherent_impl, AttributeType::Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::No, - "#[rustc_allow_incoherent_impl] has to be added to all impl items of an incoherent inherent impl." + "`#[rustc_allow_incoherent_impl]` has to be added to all impl items of an incoherent inherent impl." ), rustc_attr!( rustc_preserve_ub_checks, AttributeType::CrateLevel, template!(Word), ErrorFollowing, EncodeCrossCrate::No, @@ -970,7 +986,7 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ template!(Word), ErrorFollowing, EncodeCrossCrate::No, - "#[rustc_deny_explicit_impl] enforces that a trait can have no user-provided impls" + "`#[rustc_deny_explicit_impl]` enforces that a trait can have no user-provided impls" ), rustc_attr!( rustc_do_not_implement_via_object, @@ -978,14 +994,14 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ template!(Word), ErrorFollowing, EncodeCrossCrate::No, - "#[rustc_do_not_implement_via_object] opts out of the automatic trait impl for trait objects \ + "`#[rustc_do_not_implement_via_object]` opts out of the automatic trait impl for trait objects \ (`impl Trait for dyn Trait`)" ), rustc_attr!( rustc_has_incoherent_inherent_impls, AttributeType::Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, - "#[rustc_has_incoherent_inherent_impls] allows the addition of incoherent inherent impls for \ - the given type by annotating all impl items with #[rustc_allow_incoherent_impl]." + "`#[rustc_has_incoherent_inherent_impls]` allows the addition of incoherent inherent impls for \ + the given type by annotating all impl items with `#[rustc_allow_incoherent_impl]`." ), BuiltinAttribute { @@ -996,12 +1012,13 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ safety: AttributeSafety::Normal, template: template!(NameValueStr: "name"), duplicates: ErrorFollowing, - gate: Gated( - Stability::Unstable, - sym::rustc_attrs, - "diagnostic items compiler internal support for linting", - Features::rustc_attrs, - ), + gate: Gated{ + feature: sym::rustc_attrs, + message: "use of an internal attribute", + check: Features::rustc_attrs, + notes: &["the `#[rustc_diagnostic_item]` attribute allows the compiler to reference types \ + from the standard library for diagnostic purposes"], + }, }, gated!( // Used in resolve: @@ -1015,14 +1032,14 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_attr!( rustc_inherit_overflow_checks, Normal, template!(Word), WarnFollowing, EncodeCrossCrate::No, "the `#[rustc_inherit_overflow_checks]` attribute is just used to control \ - overflow checking behavior of several libcore functions that are inlined \ - across crates and will never be stable", + overflow checking behavior of several functions in the standard library that are inlined \ + across crates", ), rustc_attr!( rustc_reservation_impl, Normal, template!(NameValueStr: "reservation message"), ErrorFollowing, EncodeCrossCrate::Yes, "the `#[rustc_reservation_impl]` attribute is internally used \ - for reserving for `for From for T` impl" + for reserving `impl From for T` as part of the effort to stabilize `!`" ), rustc_attr!( rustc_test_marker, Normal, template!(NameValueStr: "name"), WarnFollowing, @@ -1053,12 +1070,13 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ rustc_must_implement_one_of, Normal, template!(List: "function1, function2, ..."), ErrorFollowing, EncodeCrossCrate::No, "the `#[rustc_must_implement_one_of]` attribute is used to change minimal complete \ - definition of a trait, it's currently in experimental form and should be changed before \ - being exposed outside of the std" + definition of a trait. Its syntax and semantics are highly experimental and will be \ + subject to change before stabilization", ), rustc_attr!( rustc_doc_primitive, Normal, template!(NameValueStr: "primitive name"), ErrorFollowing, - EncodeCrossCrate::Yes, r#"`rustc_doc_primitive` is a rustc internal attribute"#, + EncodeCrossCrate::Yes, "the `#[rustc_doc_primitive]` attribute is used by the standard library \ + to provide a way to generate documentation for primitive types", ), gated!( rustc_intrinsic, Normal, template!(Word), ErrorFollowing, EncodeCrossCrate::Yes, intrinsics, @@ -1066,11 +1084,11 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), rustc_attr!( rustc_no_mir_inline, Normal, template!(Word), WarnFollowing, EncodeCrossCrate::Yes, - "#[rustc_no_mir_inline] prevents the MIR inliner from inlining a function while not affecting codegen" + "`#[rustc_no_mir_inline]` prevents the MIR inliner from inlining a function while not affecting codegen" ), rustc_attr!( rustc_force_inline, Normal, template!(Word, NameValueStr: "reason"), WarnFollowing, EncodeCrossCrate::Yes, - "#[rustc_force_inline] forces a free function to be inlined" + "`#[rustc_force_inline]` forces a free function to be inlined" ), // ========================================================================== @@ -1209,10 +1227,6 @@ pub static BUILTIN_ATTRIBUTES: &[BuiltinAttribute] = &[ ), ]; -pub fn deprecated_attributes() -> Vec<&'static BuiltinAttribute> { - BUILTIN_ATTRIBUTES.iter().filter(|attr| attr.gate.is_deprecated()).collect() -} - pub fn is_builtin_attr_name(name: Symbol) -> bool { BUILTIN_ATTRIBUTE_MAP.get(&name).is_some() } diff --git a/compiler/rustc_feature/src/lib.rs b/compiler/rustc_feature/src/lib.rs index 25764755a8fc..dbc0daa3d838 100644 --- a/compiler/rustc_feature/src/lib.rs +++ b/compiler/rustc_feature/src/lib.rs @@ -40,14 +40,6 @@ pub struct Feature { issue: Option>, } -#[derive(Copy, Clone, Debug)] -pub enum Stability { - Unstable, - // First argument is tracking issue link; second argument is an optional - // help message, which defaults to "remove this attribute". - Deprecated(&'static str, Option<&'static str>), -} - #[derive(Clone, Copy, Debug, Hash)] pub enum UnstableFeatures { /// Disallow use of unstable features, as on beta/stable channels. @@ -144,9 +136,8 @@ pub fn find_feature_issue(feature: Symbol, issue: GateIssue) -> Option, + pub pull: Option>, +} + +macro_rules! opt_nonzero_u32 { + () => { + None + }; + ($val:expr) => { + Some(NonZeroU32::new($val).unwrap()) + }; } macro_rules! declare_features { ($( - $(#[doc = $doc:tt])* (removed, $feature:ident, $ver:expr, $issue:expr, $reason:expr), + $(#[doc = $doc:tt])* (removed, $feature:ident, $ver:expr, $issue:expr, $reason:expr $(, $pull:expr)?), )+) => { /// Formerly unstable features that have now been removed. pub static REMOVED_LANG_FEATURES: &[RemovedFeature] = &[ @@ -21,7 +33,8 @@ macro_rules! declare_features { since: $ver, issue: to_nonzero($issue), }, - reason: $reason + reason: $reason, + pull: opt_nonzero_u32!($($pull)?), }),+ ]; }; @@ -40,64 +53,64 @@ declare_features! ( // version they got originally added in.) /// Allows using the `amdgpu-kernel` ABI. - (removed, abi_amdgpu_kernel, "1.77.0", Some(51575), None), - (removed, advanced_slice_patterns, "1.0.0", Some(62254), - Some("merged into `#![feature(slice_patterns)]`")), + (removed, abi_amdgpu_kernel, "1.77.0", Some(51575), None, 120495), + (removed, advanced_slice_patterns, "1.42.0", Some(62254), + Some("merged into `#![feature(slice_patterns)]`"), 67712), (removed, allocator, "1.0.0", None, None), /// Allows a test to fail without failing the whole suite. - (removed, allow_fail, "1.19.0", Some(46488), Some("removed due to no clear use cases")), + (removed, allow_fail, "1.60.0", Some(46488), Some("removed due to no clear use cases"), 93416), (removed, await_macro, "1.38.0", Some(50547), - Some("subsumed by `.await` syntax")), + Some("subsumed by `.await` syntax"), 62293), /// Allows using the `box $expr` syntax. - (removed, box_syntax, "1.70.0", Some(49733), Some("replaced with `#[rustc_box]`")), + (removed, box_syntax, "1.70.0", Some(49733), Some("replaced with `#[rustc_box]`"), 108471), /// Allows capturing disjoint fields in a closure/coroutine (RFC 2229). - (removed, capture_disjoint_fields, "1.49.0", Some(53488), Some("stabilized in Rust 2021")), + (removed, capture_disjoint_fields, "1.69.0", Some(53488), Some("stabilized in Rust 2021"), 108550), /// Allows comparing raw pointers during const eval. (removed, const_compare_raw_pointers, "1.46.0", Some(53020), - Some("cannot be allowed in const eval in any meaningful way")), + Some("cannot be allowed in const eval in any meaningful way"), 73398), /// Allows limiting the evaluation steps of const expressions - (removed, const_eval_limit, "1.43.0", Some(67217), Some("removed the limit entirely")), + (removed, const_eval_limit, "1.72.0", Some(67217), Some("removed the limit entirely"), 103877), /// Allows non-trivial generic constants which have to be manually propagated upwards. - (removed, const_evaluatable_checked, "1.48.0", Some(76560), Some("renamed to `generic_const_exprs`")), + (removed, const_evaluatable_checked, "1.56.0", Some(76560), Some("renamed to `generic_const_exprs`"), 88369), /// Allows the definition of `const` functions with some advanced features. (removed, const_fn, "1.54.0", Some(57563), - Some("split into finer-grained feature gates")), + Some("split into finer-grained feature gates"), 85109), /// Allows const generic types (e.g. `struct Foo(...);`). - (removed, const_generics, "1.34.0", Some(44580), - Some("removed in favor of `#![feature(adt_const_params)]` and `#![feature(generic_const_exprs)]`")), + (removed, const_generics, "1.56.0", Some(44580), + Some("removed in favor of `#![feature(adt_const_params)]` and `#![feature(generic_const_exprs)]`"), 88369), /// Allows `[x; N]` where `x` is a constant (RFC 2203). - (removed, const_in_array_repeat_expressions, "1.37.0", Some(49147), - Some("removed due to causing promotable bugs")), + (removed, const_in_array_repeat_expressions, "1.51.0", Some(49147), + Some("removed due to causing promotable bugs"), 80404), /// Allows casting raw pointers to `usize` during const eval. (removed, const_raw_ptr_to_usize_cast, "1.55.0", Some(51910), - Some("at compile-time, pointers do not have an integer value, so these casts cannot be properly supported")), + Some("at compile-time, pointers do not have an integer value, so these casts cannot be properly supported"), 87020), /// Allows `T: ?const Trait` syntax in bounds. - (removed, const_trait_bound_opt_out, "1.42.0", Some(67794), - Some("Removed in favor of `~const` bound in #![feature(const_trait_impl)]")), + (removed, const_trait_bound_opt_out, "1.56.0", Some(67794), + Some("Removed in favor of `~const` bound in #![feature(const_trait_impl)]"), 88328), /// Allows using `crate` as visibility modifier, synonymous with `pub(crate)`. - (removed, crate_visibility_modifier, "1.63.0", Some(53120), Some("removed in favor of `pub(crate)`")), + (removed, crate_visibility_modifier, "1.63.0", Some(53120), Some("removed in favor of `pub(crate)`"), 97254), /// Allows using custom attributes (RFC 572). (removed, custom_attribute, "1.0.0", Some(29642), - Some("removed in favor of `#![register_tool]` and `#![register_attr]`")), + Some("removed in favor of `#![register_tool]` and `#![register_attr]`"), 66070), /// Allows the use of `#[derive(Anything)]` as sugar for `#[derive_Anything]`. (removed, custom_derive, "1.32.0", Some(29644), Some("subsumed by `#[proc_macro_derive]`")), /// Allows default type parameters to influence type inference. (removed, default_type_parameter_fallback, "1.82.0", Some(27336), - Some("never properly implemented; requires significant design work")), + Some("never properly implemented; requires significant design work"), 127655), /// Allows deriving traits as per `SmartPointer` specification - (removed, derive_smart_pointer, "1.79.0", Some(123430), Some("replaced by `CoercePointee`")), + (removed, derive_smart_pointer, "1.84.0", Some(123430), Some("replaced by `CoercePointee`"), 131284), /// Allows using `#[doc(keyword = "...")]`. - (removed, doc_keyword, "1.28.0", Some(51315), - Some("merged into `#![feature(rustdoc_internals)]`")), + (removed, doc_keyword, "1.58.0", Some(51315), + Some("merged into `#![feature(rustdoc_internals)]`"), 90420), /// Allows using `doc(primitive)` without a future-incompat warning. - (removed, doc_primitive, "1.56.0", Some(88070), - Some("merged into `#![feature(rustdoc_internals)]`")), + (removed, doc_primitive, "1.58.0", Some(88070), + Some("merged into `#![feature(rustdoc_internals)]`"), 90420), /// Allows `#[doc(spotlight)]`. /// The attribute was renamed to `#[doc(notable_trait)]` /// and the feature to `doc_notable_trait`. - (removed, doc_spotlight, "1.22.0", Some(45040), - Some("renamed to `doc_notable_trait`")), + (removed, doc_spotlight, "1.53.0", Some(45040), + Some("renamed to `doc_notable_trait`"), 80965), /// Allows using `#[unsafe_destructor_blind_to_params]` (RFC 1238). (removed, dropck_parametricity, "1.38.0", Some(28498), None), /// Allows making `dyn Trait` well-formed even if `Trait` is not dyn compatible[^1]. @@ -107,161 +120,162 @@ declare_features! ( /// Renamed from `object_safe_for_dispatch`. /// /// [^1]: Formerly known as "object safe". - (removed, dyn_compatible_for_dispatch, "1.83.0", Some(43561), - Some("removed, not used heavily and represented additional complexity in dyn compatibility")), + (removed, dyn_compatible_for_dispatch, "1.87.0", Some(43561), + Some("removed, not used heavily and represented additional complexity in dyn compatibility"), 136522), /// Uses generic effect parameters for ~const bounds (removed, effects, "1.84.0", Some(102090), - Some("removed, redundant with `#![feature(const_trait_impl)]`")), + Some("removed, redundant with `#![feature(const_trait_impl)]`"), 132479), /// Allows defining `existential type`s. (removed, existential_type, "1.38.0", Some(63063), Some("removed in favor of `#![feature(type_alias_impl_trait)]`")), /// Paths of the form: `extern::foo::bar` (removed, extern_in_paths, "1.33.0", Some(55600), - Some("subsumed by `::foo::bar` paths")), + Some("subsumed by `::foo::bar` paths"), 57572), /// Allows `#[doc(include = "some-file")]`. (removed, external_doc, "1.54.0", Some(44732), - Some("use #[doc = include_str!(\"filename\")] instead, which handles macro invocations")), + Some("use #[doc = include_str!(\"filename\")] instead, which handles macro invocations"), 85457), /// Allows using `#[ffi_returns_twice]` on foreign functions. (removed, ffi_returns_twice, "1.78.0", Some(58314), - Some("being investigated by the ffi-unwind project group")), + Some("being investigated by the ffi-unwind project group"), 120502), /// Allows generators to be cloned. - (removed, generator_clone, "1.65.0", Some(95360), Some("renamed to `coroutine_clone`")), + (removed, generator_clone, "1.75.0", Some(95360), Some("renamed to `coroutine_clone`"), 116958), /// Allows defining generators. - (removed, generators, "1.21.0", Some(43122), Some("renamed to `coroutines`")), + (removed, generators, "1.75.0", Some(43122), Some("renamed to `coroutines`"), 116958), /// An extension to the `generic_associated_types` feature, allowing incomplete features. (removed, generic_associated_types_extended, "1.85.0", Some(95451), Some( "feature needs overhaul and reimplementation pending \ better implied higher-ranked implied bounds support" - ) + ), + 133768 ), (removed, import_shadowing, "1.0.0", None, None), /// Allows in-band quantification of lifetime bindings (e.g., `fn foo(x: &'a u8) -> &'a u8`). - (removed, in_band_lifetimes, "1.23.0", Some(44524), - Some("removed due to unsolved ergonomic questions and added lifetime resolution complexity")), + (removed, in_band_lifetimes, "1.61.0", Some(44524), + Some("removed due to unsolved ergonomic questions and added lifetime resolution complexity"), 93845), /// Allows inferring `'static` outlives requirements (RFC 2093). (removed, infer_static_outlives_requirements, "1.63.0", Some(54185), - Some("removed as it caused some confusion and discussion was inactive for years")), + Some("removed as it caused some confusion and discussion was inactive for years"), 97875), /// Allow anonymous constants from an inline `const` block in pattern position (removed, inline_const_pat, "1.88.0", Some(76001), - Some("removed due to implementation concerns as it requires significant refactorings")), + Some("removed due to implementation concerns as it requires significant refactorings"), 138492), /// Lazily evaluate constants. This allows constants to depend on type parameters. - (removed, lazy_normalization_consts, "1.46.0", Some(72219), Some("superseded by `generic_const_exprs`")), + (removed, lazy_normalization_consts, "1.56.0", Some(72219), Some("superseded by `generic_const_exprs`"), 88369), /// Changes `impl Trait` to capture all lifetimes in scope. - (removed, lifetime_capture_rules_2024, "1.76.0", None, Some("unnecessary -- use edition 2024 instead")), + (removed, lifetime_capture_rules_2024, "1.87.0", None, Some("unnecessary -- use edition 2024 instead"), 136787), /// Allows using the `#[link_args]` attribute. (removed, link_args, "1.53.0", Some(29596), Some("removed in favor of using `-C link-arg=ARG` on command line, \ - which is available from cargo build scripts with `cargo:rustc-link-arg` now")), + which is available from cargo build scripts with `cargo:rustc-link-arg` now"), 83820), (removed, macro_reexport, "1.0.0", Some(29638), - Some("subsumed by `pub use`")), + Some("subsumed by `pub use`"), 49982), /// Allows using `#[main]` to replace the entrypoint `#[lang = "start"]` calls. - (removed, main, "1.53.0", Some(29634), None), + (removed, main, "1.53.0", Some(29634), None, 84217), (removed, managed_boxes, "1.0.0", None, None), /// Allows the use of type alias impl trait in function return positions (removed, min_type_alias_impl_trait, "1.56.0", Some(63063), - Some("removed in favor of full type_alias_impl_trait")), + Some("removed in favor of full type_alias_impl_trait"), 87564), /// Make `mut` not reset the binding mode on edition >= 2024. - (removed, mut_preserve_binding_mode_2024, "1.79.0", Some(123076), Some("superseded by `ref_pat_eat_one_layer_2024`")), + (removed, mut_preserve_binding_mode_2024, "1.80.0", Some(123076), Some("superseded by `ref_pat_eat_one_layer_2024`"), 125168), (removed, needs_allocator, "1.4.0", Some(27389), Some("subsumed by `#![feature(allocator_internals)]`")), /// Allows use of unary negate on unsigned integers, e.g., -e for e: u8 (removed, negate_unsigned, "1.0.0", Some(29645), None), /// Allows `#[no_coverage]` on functions. /// The feature was renamed to `coverage_attribute` and the attribute to `#[coverage(on|off)]` - (removed, no_coverage, "1.74.0", Some(84605), Some("renamed to `coverage_attribute`")), + (removed, no_coverage, "1.74.0", Some(84605), Some("renamed to `coverage_attribute`"), 114656), /// Allows `#[no_debug]`. - (removed, no_debug, "1.43.0", Some(29721), Some("removed due to lack of demand")), + (removed, no_debug, "1.43.0", Some(29721), Some("removed due to lack of demand"), 69667), /// Note: this feature was previously recorded in a separate /// `STABLE_REMOVED` list because it, uniquely, was once stable but was /// then removed. But there was no utility storing it separately, so now /// it's in this list. - (removed, no_stack_check, "1.0.0", None, None), + (removed, no_stack_check, "1.0.0", None, None, 40110), /// Allows making `dyn Trait` well-formed even if `Trait` is not dyn compatible (object safe). /// Renamed to `dyn_compatible_for_dispatch`. (removed, object_safe_for_dispatch, "1.83.0", Some(43561), - Some("renamed to `dyn_compatible_for_dispatch`")), + Some("renamed to `dyn_compatible_for_dispatch`"), 131511), /// Allows using `#[on_unimplemented(..)]` on traits. /// (Moved to `rustc_attrs`.) - (removed, on_unimplemented, "1.40.0", None, None), + (removed, on_unimplemented, "1.40.0", None, None, 65794), /// A way to temporarily opt out of opt-in copy. This will *never* be accepted. - (removed, opt_out_copy, "1.0.0", None, None), + (removed, opt_out_copy, "1.0.0", None, None, 20740), /// Allows features specific to OIBIT (now called auto traits). /// Renamed to `auto_traits`. - (removed, optin_builtin_traits, "1.0.0", Some(13231), - Some("renamed to `auto_traits`")), + (removed, optin_builtin_traits, "1.50.0", Some(13231), + Some("renamed to `auto_traits`"), 79336), /// Allows overlapping impls of marker traits. (removed, overlapping_marker_traits, "1.42.0", Some(29864), - Some("removed in favor of `#![feature(marker_trait_attr)]`")), + Some("removed in favor of `#![feature(marker_trait_attr)]`"), 68544), (removed, panic_implementation, "1.28.0", Some(44489), - Some("subsumed by `#[panic_handler]`")), + Some("subsumed by `#[panic_handler]`"), 53619), /// Allows `extern "platform-intrinsic" { ... }`. - (removed, platform_intrinsics, "1.4.0", Some(27731), - Some("SIMD intrinsics use the regular intrinsics ABI now")), + (removed, platform_intrinsics, "1.78.0", Some(27731), + Some("SIMD intrinsics use the regular intrinsics ABI now"), 121516), /// Allows using `#![plugin(myplugin)]`. (removed, plugin, "1.75.0", Some(29597), - Some("plugins are no longer supported")), + Some("plugins are no longer supported"), 116412), /// Allows using `#[plugin_registrar]` on functions. - (removed, plugin_registrar, "1.54.0", Some(29597), - Some("plugins are no longer supported")), + (removed, plugin_registrar, "1.75.0", Some(29597), + Some("plugins are no longer supported"), 116412), /// Allows exhaustive integer pattern matching with `usize::MAX`/`isize::MIN`/`isize::MAX`. - (removed, precise_pointer_size_matching, "1.32.0", Some(56354), - Some("removed in favor of half-open ranges")), + (removed, precise_pointer_size_matching, "1.76.0", Some(56354), + Some("removed in favor of half-open ranges"), 118598), (removed, pref_align_of, "CURRENT_RUSTC_VERSION", Some(91971), Some("removed due to marginal use and inducing compiler complications")), (removed, proc_macro_expr, "1.27.0", Some(54727), - Some("subsumed by `#![feature(proc_macro_hygiene)]`")), + Some("subsumed by `#![feature(proc_macro_hygiene)]`"), 52121), (removed, proc_macro_gen, "1.27.0", Some(54727), - Some("subsumed by `#![feature(proc_macro_hygiene)]`")), + Some("subsumed by `#![feature(proc_macro_hygiene)]`"), 52121), (removed, proc_macro_mod, "1.27.0", Some(54727), - Some("subsumed by `#![feature(proc_macro_hygiene)]`")), + Some("subsumed by `#![feature(proc_macro_hygiene)]`"), 52121), (removed, proc_macro_non_items, "1.27.0", Some(54727), - Some("subsumed by `#![feature(proc_macro_hygiene)]`")), + Some("subsumed by `#![feature(proc_macro_hygiene)]`"), 52121), (removed, pub_macro_rules, "1.53.0", Some(78855), Some("removed due to being incomplete, in particular it does not work across crates")), (removed, pushpop_unsafe, "1.2.0", None, None), (removed, quad_precision_float, "1.0.0", None, None), (removed, quote, "1.33.0", Some(29601), None), - (removed, ref_pat_everywhere, "1.79.0", Some(123076), Some("superseded by `ref_pat_eat_one_layer_2024")), + (removed, ref_pat_everywhere, "1.80.0", Some(123076), Some("superseded by `ref_pat_eat_one_layer_2024"), 125168), (removed, reflect, "1.0.0", Some(27749), None), /// Allows using the `#[register_attr]` attribute. (removed, register_attr, "1.65.0", Some(66080), - Some("removed in favor of `#![register_tool]`")), + Some("removed in favor of `#![register_tool]`"), 66070), (removed, rust_2018_preview, "1.76.0", None, Some("2018 Edition preview is no longer relevant")), /// Allows using the macros: /// + `__diagnostic_used` /// + `__register_diagnostic` /// +`__build_diagnostic_array` - (removed, rustc_diagnostic_macros, "1.38.0", None, None), + (removed, rustc_diagnostic_macros, "1.38.0", None, None, 64139), /// Allows identifying crates that contain sanitizer runtimes. - (removed, sanitizer_runtime, "1.17.0", None, None), + (removed, sanitizer_runtime, "1.17.0", None, None, 65241), (removed, simd, "1.0.0", Some(27731), Some("removed in favor of `#[repr(simd)]`")), /// Allows using `#[start]` on a function indicating that it is the program entrypoint. - (removed, start, "1.0.0", Some(29633), Some("not portable enough and never RFC'd")), + (removed, start, "1.86.0", Some(29633), Some("not portable enough and never RFC'd"), 134299), /// Allows `#[link(kind = "static-nobundle", ...)]`. - (removed, static_nobundle, "1.16.0", Some(37403), - Some(r#"subsumed by `#[link(kind = "static", modifiers = "-bundle", ...)]`"#)), + (removed, static_nobundle, "1.63.0", Some(37403), + Some(r#"subsumed by `#[link(kind = "static", modifiers = "-bundle", ...)]`"#), 95818), (removed, struct_inherit, "1.0.0", None, None), (removed, test_removed_feature, "1.0.0", None, None), /// Allows using items which are missing stability attributes (removed, unmarked_api, "1.0.0", None, None), /// Allows unnamed fields of struct and union type - (removed, unnamed_fields, "1.83.0", Some(49804), Some("feature needs redesign")), + (removed, unnamed_fields, "1.83.0", Some(49804), Some("feature needs redesign"), 131045), (removed, unsafe_no_drop_flag, "1.0.0", None, None), (removed, unsized_tuple_coercion, "1.87.0", Some(42877), - Some("The feature restricts possible layouts for tuples, and this restriction is not worth it.")), + Some("The feature restricts possible layouts for tuples, and this restriction is not worth it."), 137728), /// Allows `union` fields that don't implement `Copy` as long as they don't have any drop glue. - (removed, untagged_unions, "1.13.0", Some(55149), - Some("unions with `Copy` and `ManuallyDrop` fields are stable; there is no intent to stabilize more")), + (removed, untagged_unions, "1.64.0", Some(55149), + Some("unions with `Copy` and `ManuallyDrop` fields are stable; there is no intent to stabilize more"), 97995), /// Allows `#[unwind(..)]`. /// /// Permits specifying whether a function should permit unwinding or abort on unwind. - (removed, unwind_attributes, "1.56.0", Some(58760), Some("use the C-unwind ABI instead")), + (removed, unwind_attributes, "1.56.0", Some(58760), Some("use the C-unwind ABI instead"), 86155), (removed, visible_private_types, "1.0.0", None, None), /// Allows `extern "wasm" fn` (removed, wasm_abi, "1.81.0", Some(83788), - Some("non-standard wasm ABI is no longer supported")), + Some("non-standard wasm ABI is no longer supported"), 127605), // !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! // Features are listed in alphabetical order. Tidy will fail if you don't keep it this way. // !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! !!!! diff --git a/compiler/rustc_feature/src/unstable.rs b/compiler/rustc_feature/src/unstable.rs index 9447deeecbbc..cfdca8c48b0d 100644 --- a/compiler/rustc_feature/src/unstable.rs +++ b/compiler/rustc_feature/src/unstable.rs @@ -353,6 +353,8 @@ declare_features! ( (unstable, abi_avr_interrupt, "1.45.0", Some(69664)), /// Allows `extern "C-cmse-nonsecure-call" fn()`. (unstable, abi_c_cmse_nonsecure_call, "1.51.0", Some(81391)), + /// Allows `extern "custom" fn()`. + (unstable, abi_custom, "CURRENT_RUSTC_VERSION", Some(140829)), /// Allows `extern "gpu-kernel" fn()`. (unstable, abi_gpu_kernel, "1.86.0", Some(135467)), /// Allows `extern "msp430-interrupt" fn()`. @@ -546,8 +548,6 @@ declare_features! ( (incomplete, inherent_associated_types, "1.52.0", Some(8995)), /// Allows using `pointer` and `reference` in intra-doc links (unstable, intra_doc_pointers, "1.51.0", Some(80896)), - // Allows using the `kl` and `widekl` target features and the associated intrinsics - (unstable, keylocker_x86, "1.86.0", Some(134813)), // Allows setting the threshold for the `large_assignments` lint. (unstable, large_assignments, "1.52.0", Some(83518)), /// Allow to have type alias types for inter-crate use. diff --git a/compiler/rustc_hir/src/hir.rs b/compiler/rustc_hir/src/hir.rs index 6f288bb39b95..336bf0d93fd0 100644 --- a/compiler/rustc_hir/src/hir.rs +++ b/compiler/rustc_hir/src/hir.rs @@ -34,6 +34,7 @@ use crate::def::{CtorKind, DefKind, PerNS, Res}; use crate::def_id::{DefId, LocalDefIdMap}; pub(crate) use crate::hir_id::{HirId, ItemLocalId, ItemLocalMap, OwnerId}; use crate::intravisit::{FnKind, VisitorExt}; +use crate::lints::DelayedLints; #[derive(Debug, Copy, Clone, PartialEq, Eq, HashStable_Generic)] pub enum AngleBrackets { @@ -1526,6 +1527,10 @@ pub struct OwnerInfo<'hir> { /// Map indicating what traits are in scope for places where this /// is relevant; generated by resolve. pub trait_map: ItemLocalMap>, + + /// Lints delayed during ast lowering to be emitted + /// after hir has completely built + pub delayed_lints: DelayedLints, } impl<'tcx> OwnerInfo<'tcx> { diff --git a/compiler/rustc_hir/src/lib.rs b/compiler/rustc_hir/src/lib.rs index c6fe475b4609..dafd31336fbb 100644 --- a/compiler/rustc_hir/src/lib.rs +++ b/compiler/rustc_hir/src/lib.rs @@ -27,6 +27,7 @@ mod hir; pub mod hir_id; pub mod intravisit; pub mod lang_items; +pub mod lints; pub mod pat_util; mod stable_hash_impls; mod target; diff --git a/compiler/rustc_hir/src/lints.rs b/compiler/rustc_hir/src/lints.rs new file mode 100644 index 000000000000..7be6c32e57ed --- /dev/null +++ b/compiler/rustc_hir/src/lints.rs @@ -0,0 +1,23 @@ +use rustc_attr_data_structures::lints::AttributeLint; +use rustc_data_structures::fingerprint::Fingerprint; +use rustc_macros::HashStable_Generic; + +use crate::HirId; + +/// During ast lowering, no lints can be emitted. +/// That is because lints attach to nodes either in the AST, or on the built HIR. +/// When attached to AST nodes, they're emitted just before building HIR, +/// and then there's a gap where no lints can be emitted until HIR is done. +/// The variants in this enum represent lints that are temporarily stashed during +/// AST lowering to be emitted once HIR is built. +#[derive(Clone, Debug, HashStable_Generic)] +pub enum DelayedLint { + AttributeParsing(AttributeLint), +} + +#[derive(Debug)] +pub struct DelayedLints { + pub lints: Box<[DelayedLint]>, + // Only present when the crate hash is needed. + pub opt_hash: Option, +} diff --git a/compiler/rustc_hir/src/stable_hash_impls.rs b/compiler/rustc_hir/src/stable_hash_impls.rs index 91ea88cae477..6acf1524b608 100644 --- a/compiler/rustc_hir/src/stable_hash_impls.rs +++ b/compiler/rustc_hir/src/stable_hash_impls.rs @@ -6,6 +6,7 @@ use crate::hir::{ AttributeMap, BodyId, Crate, ForeignItemId, ImplItemId, ItemId, OwnerNodes, TraitItemId, }; use crate::hir_id::{HirId, ItemLocalId}; +use crate::lints::DelayedLints; /// Requirements for a `StableHashingContext` to be used in this crate. /// This is a hack to allow using the `HashStable_Generic` derive macro @@ -102,6 +103,13 @@ impl<'tcx, HirCtx: crate::HashStableContext> HashStable for OwnerNodes<' } } +impl HashStable for DelayedLints { + fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) { + let DelayedLints { opt_hash, .. } = *self; + opt_hash.unwrap().hash_stable(hcx, hasher); + } +} + impl<'tcx, HirCtx: crate::HashStableContext> HashStable for AttributeMap<'tcx> { fn hash_stable(&self, hcx: &mut HirCtx, hasher: &mut StableHasher) { // We ignore the `map` since it refers to information included in `opt_hash` which is diff --git a/compiler/rustc_hir_analysis/Cargo.toml b/compiler/rustc_hir_analysis/Cargo.toml index 899370b34e49..5d6c49ee862f 100644 --- a/compiler/rustc_hir_analysis/Cargo.toml +++ b/compiler/rustc_hir_analysis/Cargo.toml @@ -14,6 +14,7 @@ rustc_abi = { path = "../rustc_abi" } rustc_arena = { path = "../rustc_arena" } rustc_ast = { path = "../rustc_ast" } rustc_attr_data_structures = { path = "../rustc_attr_data_structures" } +rustc_attr_parsing = { path = "../rustc_attr_parsing" } rustc_data_structures = { path = "../rustc_data_structures" } rustc_errors = { path = "../rustc_errors" } rustc_feature = { path = "../rustc_feature" } diff --git a/compiler/rustc_hir_analysis/messages.ftl b/compiler/rustc_hir_analysis/messages.ftl index 4fcd9f8a646e..3e98bd213d3b 100644 --- a/compiler/rustc_hir_analysis/messages.ftl +++ b/compiler/rustc_hir_analysis/messages.ftl @@ -1,3 +1,7 @@ +hir_analysis_abi_custom_clothed_function = + items with the `"custom"` ABI can only be declared externally or defined via naked functions + .suggestion = convert this to an `#[unsafe(naked)]` function + hir_analysis_ambiguous_assoc_item = ambiguous associated {$assoc_kind} `{$assoc_ident}` in bounds of `{$qself}` .label = ambiguous associated {$assoc_kind} `{$assoc_ident}` diff --git a/compiler/rustc_hir_analysis/src/autoderef.rs b/compiler/rustc_hir_analysis/src/autoderef.rs index 99e495d92669..c88c534e1354 100644 --- a/compiler/rustc_hir_analysis/src/autoderef.rs +++ b/compiler/rustc_hir_analysis/src/autoderef.rs @@ -160,7 +160,7 @@ impl<'a, 'tcx> Autoderef<'a, 'tcx> { self.param_env, ty::Binder::dummy(trait_ref), ); - if !self.infcx.predicate_may_hold(&obligation) { + if !self.infcx.next_trait_solver() && !self.infcx.predicate_may_hold(&obligation) { debug!("overloaded_deref_ty: cannot match obligation"); return None; } @@ -184,17 +184,17 @@ impl<'a, 'tcx> Autoderef<'a, 'tcx> { self.param_env, ty, ) else { - // We shouldn't have errors here, except for evaluate/fulfill mismatches, - // but that's not a reason for an ICE (`predicate_may_hold` is conservative - // by design). - // FIXME(-Znext-solver): This *actually* shouldn't happen then. + // We shouldn't have errors here in the old solver, except for + // evaluate/fulfill mismatches, but that's not a reason for an ICE. return None; }; let errors = ocx.select_where_possible(); if !errors.is_empty() { - // This shouldn't happen, except for evaluate/fulfill mismatches, - // but that's not a reason for an ICE (`predicate_may_hold` is conservative - // by design). + if self.infcx.next_trait_solver() { + unreachable!(); + } + // We shouldn't have errors here in the old solver, except for + // evaluate/fulfill mismatches, but that's not a reason for an ICE. debug!(?errors, "encountered errors while fulfilling"); return None; } diff --git a/compiler/rustc_hir_analysis/src/check/check.rs b/compiler/rustc_hir_analysis/src/check/check.rs index 064b42413f03..32fec0604c0f 100644 --- a/compiler/rustc_hir_analysis/src/check/check.rs +++ b/compiler/rustc_hir_analysis/src/check/check.rs @@ -21,7 +21,7 @@ use rustc_middle::ty::error::TypeErrorToStringExt; use rustc_middle::ty::layout::{LayoutError, MAX_SIMD_LANES}; use rustc_middle::ty::util::Discr; use rustc_middle::ty::{ - AdtDef, BottomUpFolder, GenericArgKind, RegionKind, TypeFoldable, TypeSuperVisitable, + AdtDef, BottomUpFolder, FnSig, GenericArgKind, RegionKind, TypeFoldable, TypeSuperVisitable, TypeVisitable, TypeVisitableExt, fold_regions, }; use rustc_session::lint::builtin::UNINHABITED_STATIC; @@ -37,22 +37,23 @@ use {rustc_attr_data_structures as attrs, rustc_hir as hir}; use super::compare_impl_item::check_type_bounds; use super::*; +fn add_abi_diag_help(abi: ExternAbi, diag: &mut Diag<'_, T>) { + if let ExternAbi::Cdecl { unwind } = abi { + let c_abi = ExternAbi::C { unwind }; + diag.help(format!("use `extern {c_abi}` instead",)); + } else if let ExternAbi::Stdcall { unwind } = abi { + let c_abi = ExternAbi::C { unwind }; + let system_abi = ExternAbi::System { unwind }; + diag.help(format!( + "if you need `extern {abi}` on win32 and `extern {c_abi}` everywhere else, \ + use `extern {system_abi}`" + )); + } +} + pub fn check_abi(tcx: TyCtxt<'_>, hir_id: hir::HirId, span: Span, abi: ExternAbi) { // FIXME: this should be checked earlier, e.g. in `rustc_ast_lowering`, to fix // things like #86232. - fn add_help(abi: ExternAbi, diag: &mut Diag<'_, T>) { - if let ExternAbi::Cdecl { unwind } = abi { - let c_abi = ExternAbi::C { unwind }; - diag.help(format!("use `extern {c_abi}` instead",)); - } else if let ExternAbi::Stdcall { unwind } = abi { - let c_abi = ExternAbi::C { unwind }; - let system_abi = ExternAbi::System { unwind }; - diag.help(format!( - "if you need `extern {abi}` on win32 and `extern {c_abi}` everywhere else, \ - use `extern {system_abi}`" - )); - } - } match AbiMap::from_target(&tcx.sess.target).canonize_abi(abi, false) { AbiMapping::Direct(..) => (), @@ -63,13 +64,13 @@ pub fn check_abi(tcx: TyCtxt<'_>, hir_id: hir::HirId, span: Span, abi: ExternAbi E0570, "`{abi}` is not a supported ABI for the current target", ); - add_help(abi, &mut err); + add_abi_diag_help(abi, &mut err); err.emit(); } AbiMapping::Deprecated(..) => { tcx.node_span_lint(UNSUPPORTED_CALLING_CONVENTIONS, hir_id, span, |lint| { lint.primary_message("use of calling convention not supported on this target"); - add_help(abi, lint); + add_abi_diag_help(abi, lint); }); } } @@ -80,7 +81,16 @@ pub fn check_abi_fn_ptr(tcx: TyCtxt<'_>, hir_id: hir::HirId, span: Span, abi: Ex // in `check_abi` above. match AbiMap::from_target(&tcx.sess.target).canonize_abi(abi, false) { AbiMapping::Direct(..) => (), - AbiMapping::Deprecated(..) | AbiMapping::Invalid => { + // This is not a redundant match arm: these ABIs started linting after introducing + // UNSUPPORTED_FN_PTR_CALLING_CONVENTIONS already existed and we want to + // avoid expanding the scope of that lint so it can move to a hard error sooner. + AbiMapping::Deprecated(..) => { + tcx.node_span_lint(UNSUPPORTED_CALLING_CONVENTIONS, hir_id, span, |lint| { + lint.primary_message("use of calling convention not supported on this target"); + add_abi_diag_help(abi, lint); + }); + } + AbiMapping::Invalid => { tcx.node_span_lint(UNSUPPORTED_FN_PTR_CALLING_CONVENTIONS, hir_id, span, |lint| { lint.primary_message(format!( "the calling convention {abi} is not supported on this target" @@ -90,6 +100,18 @@ pub fn check_abi_fn_ptr(tcx: TyCtxt<'_>, hir_id: hir::HirId, span: Span, abi: Ex } } +pub fn check_custom_abi(tcx: TyCtxt<'_>, def_id: LocalDefId, fn_sig: FnSig<'_>, fn_sig_span: Span) { + if fn_sig.abi == ExternAbi::Custom { + // Function definitions that use `extern "custom"` must be naked functions. + if !tcx.has_attr(def_id, sym::naked) { + tcx.dcx().emit_err(crate::errors::AbiCustomClothedFunction { + span: fn_sig_span, + naked_span: tcx.def_span(def_id).shrink_to_lo(), + }); + } + } +} + fn check_struct(tcx: TyCtxt<'_>, def_id: LocalDefId) { let def = tcx.adt_def(def_id); let span = tcx.def_span(def_id); diff --git a/compiler/rustc_hir_analysis/src/check/intrinsic.rs b/compiler/rustc_hir_analysis/src/check/intrinsic.rs index 481cdaa4c6ca..060fc51b7bda 100644 --- a/compiler/rustc_hir_analysis/src/check/intrinsic.rs +++ b/compiler/rustc_hir_analysis/src/check/intrinsic.rs @@ -71,7 +71,7 @@ fn intrinsic_operation_unsafety(tcx: TyCtxt<'_>, intrinsic_id: LocalDefId) -> hi | sym::box_new | sym::breakpoint | sym::size_of - | sym::min_align_of + | sym::align_of | sym::needs_drop | sym::caller_location | sym::add_with_overflow @@ -200,10 +200,8 @@ pub(crate) fn check_intrinsic_type( sym::abort => (0, 0, vec![], tcx.types.never), sym::unreachable => (0, 0, vec![], tcx.types.never), sym::breakpoint => (0, 0, vec![], tcx.types.unit), - sym::size_of | sym::pref_align_of | sym::min_align_of | sym::variant_count => { - (1, 0, vec![], tcx.types.usize) - } - sym::size_of_val | sym::min_align_of_val => { + sym::size_of | sym::align_of | sym::variant_count => (1, 0, vec![], tcx.types.usize), + sym::size_of_val | sym::align_of_val => { (1, 0, vec![Ty::new_imm_ptr(tcx, param(0))], tcx.types.usize) } sym::rustc_peek => (1, 0, vec![param(0)], param(0)), diff --git a/compiler/rustc_hir_analysis/src/check/mod.rs b/compiler/rustc_hir_analysis/src/check/mod.rs index fad8abf5fae8..c5c7e6b2aa72 100644 --- a/compiler/rustc_hir_analysis/src/check/mod.rs +++ b/compiler/rustc_hir_analysis/src/check/mod.rs @@ -72,7 +72,7 @@ pub mod wfcheck; use std::num::NonZero; -pub use check::{check_abi, check_abi_fn_ptr}; +pub use check::{check_abi, check_abi_fn_ptr, check_custom_abi}; use rustc_abi::{ExternAbi, VariantIdx}; use rustc_data_structures::fx::{FxHashSet, FxIndexMap}; use rustc_errors::{Diag, ErrorGuaranteed, pluralize, struct_span_code_err}; diff --git a/compiler/rustc_hir_analysis/src/collect.rs b/compiler/rustc_hir_analysis/src/collect.rs index e1df0d60452d..6e22ac5a28a8 100644 --- a/compiler/rustc_hir_analysis/src/collect.rs +++ b/compiler/rustc_hir_analysis/src/collect.rs @@ -494,7 +494,7 @@ impl<'tcx> HirTyLowerer<'tcx> for ItemCtxt<'tcx> { // Only visit the type looking for `_` if we didn't fix the type above visitor.visit_ty_unambig(a); - self.lowerer().lower_arg_ty(a, None) + self.lowerer().lower_ty(a) }) .collect(); diff --git a/compiler/rustc_hir_analysis/src/errors.rs b/compiler/rustc_hir_analysis/src/errors.rs index a27d1ed6c532..809cb311c1f5 100644 --- a/compiler/rustc_hir_analysis/src/errors.rs +++ b/compiler/rustc_hir_analysis/src/errors.rs @@ -1698,3 +1698,17 @@ pub(crate) struct SelfInTypeAlias { #[label] pub span: Span, } + +#[derive(Diagnostic)] +#[diag(hir_analysis_abi_custom_clothed_function)] +pub(crate) struct AbiCustomClothedFunction { + #[primary_span] + pub span: Span, + #[suggestion( + hir_analysis_suggestion, + applicability = "maybe-incorrect", + code = "#[unsafe(naked)]\n", + style = "short" + )] + pub naked_span: Span, +} diff --git a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs index 4c65d0d05102..bf407cbaccb5 100644 --- a/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs +++ b/compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs @@ -805,7 +805,11 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { ty::ClauseKind::Trait(ty::TraitPredicate { trait_ref, polarity }) }); let bound = (bound.upcast(tcx), span); - // FIXME(-Znext-solver): We can likely remove this hack once the new trait solver lands. + // FIXME(-Znext-solver): We can likely remove this hack once the + // new trait solver lands. This fixed an overflow in the old solver. + // This may have performance implications, so please check perf when + // removing it. + // This was added in . if tcx.is_lang_item(trait_def_id, rustc_hir::LangItem::Sized) { bounds.insert(0, bound); } else { @@ -2704,16 +2708,6 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ { } } - pub fn lower_arg_ty(&self, ty: &hir::Ty<'tcx>, expected_ty: Option>) -> Ty<'tcx> { - match ty.kind { - hir::TyKind::Infer(()) if let Some(expected_ty) = expected_ty => { - self.record_ty(ty.hir_id, expected_ty, ty.span); - expected_ty - } - _ => self.lower_ty(ty), - } - } - /// Lower a function type from the HIR to our internal notion of a function signature. #[instrument(level = "debug", skip(self, hir_id, safety, abi, decl, generics, hir_ty), ret)] pub fn lower_fn_ty( diff --git a/compiler/rustc_hir_analysis/src/lib.rs b/compiler/rustc_hir_analysis/src/lib.rs index a92ee89186cf..007f3a6abf6c 100644 --- a/compiler/rustc_hir_analysis/src/lib.rs +++ b/compiler/rustc_hir_analysis/src/lib.rs @@ -92,8 +92,9 @@ mod variance; pub use errors::NoVariantNamed; use rustc_abi::ExternAbi; -use rustc_hir as hir; use rustc_hir::def::DefKind; +use rustc_hir::lints::DelayedLint; +use rustc_hir::{self as hir}; use rustc_middle::middle; use rustc_middle::mir::interpret::GlobalId; use rustc_middle::query::Providers; @@ -174,6 +175,14 @@ pub fn provide(providers: &mut Providers) { }; } +fn emit_delayed_lint(lint: &DelayedLint, tcx: TyCtxt<'_>) { + match lint { + DelayedLint::AttributeParsing(attribute_lint) => { + rustc_attr_parsing::emit_attribute_lint(attribute_lint, tcx) + } + } +} + pub fn check_crate(tcx: TyCtxt<'_>) { let _prof_timer = tcx.sess.timer("type_check_crate"); @@ -192,6 +201,14 @@ pub fn check_crate(tcx: TyCtxt<'_>) { let _: R = tcx.ensure_ok().crate_inherent_impls_overlap_check(()); }); + for owner_id in tcx.hir_crate_items(()).owners() { + if let Some(delayed_lints) = tcx.opt_ast_lowering_delayed_lints(owner_id) { + for lint in &delayed_lints.lints { + emit_delayed_lint(lint, tcx); + } + } + } + tcx.par_hir_body_owners(|item_def_id| { let def_kind = tcx.def_kind(item_def_id); // Make sure we evaluate all static and (non-associated) const items, even if unused. diff --git a/compiler/rustc_hir_typeck/messages.ftl b/compiler/rustc_hir_typeck/messages.ftl index 6c33dfb4ec05..ac7ff65528d9 100644 --- a/compiler/rustc_hir_typeck/messages.ftl +++ b/compiler/rustc_hir_typeck/messages.ftl @@ -1,3 +1,7 @@ +hir_typeck_abi_custom_call = + functions with the `"custom"` ABI cannot be called + .note = an `extern "custom"` function can only be called from within inline assembly + hir_typeck_add_missing_parentheses_in_range = you must surround the range in parentheses to call its `{$func_name}` function hir_typeck_add_return_type_add = try adding a return type @@ -17,6 +21,24 @@ hir_typeck_base_expression_double_dot_enable_default_field_values = add `#![feature(default_field_values)]` to the crate attributes to enable default values on `struct` fields hir_typeck_base_expression_double_dot_remove = remove the `..` as all the fields are already present +hir_typeck_break_inside_closure = + `{$name}` inside of a closure + .label = cannot `{$name}` inside of a closure + .closure_label = enclosing closure + +hir_typeck_break_inside_coroutine = + `{$name}` inside `{$kind}` {$source} + .label = cannot `{$name}` inside `{$kind}` {$source} + .coroutine_label = enclosing `{$kind}` {$source} + +hir_typeck_break_non_loop = + `break` with value from a `{$kind}` loop + .label = can only break with a value inside `loop` or breakable block + .label2 = you can't `break` with a value in a `{$kind}` loop + .suggestion = use `break` on its own without a value inside this `{$kind}` loop + .break_expr_suggestion = alternatively, you might have meant to use the available loop label + + hir_typeck_candidate_trait_note = `{$trait_name}` defines an item `{$item_name}`{$action_or_ty -> [NONE] {""} [implement] , perhaps you need to implement it @@ -64,6 +86,12 @@ hir_typeck_const_select_must_be_fn = this argument must be a function item .note = expected a function item, found {$ty} .help = consult the documentation on `const_eval_select` for more information +hir_typeck_continue_labeled_block = + `continue` pointing to a labeled block + .label = labeled blocks cannot be `continue`'d + .block_label = labeled block the `continue` points to + + hir_typeck_convert_to_str = try converting the passed type into a `&str` hir_typeck_convert_using_method = try using `{$sugg}` to convert `{$found}` to `{$expected}` @@ -182,6 +210,19 @@ hir_typeck_option_result_asref = use `{$def_path}::as_ref` to convert `{$expecte hir_typeck_option_result_cloned = use `{$def_path}::cloned` to clone the value inside the `{$def_path}` hir_typeck_option_result_copied = use `{$def_path}::copied` to copy the value inside the `{$def_path}` +hir_typeck_outside_loop = + `{$name}` outside of a loop{$is_break -> + [true] {" or labeled block"} + *[false] {""} + } + .label = cannot `{$name}` outside of a loop{$is_break -> + [true] {" or labeled block"} + *[false] {""} + } + +hir_typeck_outside_loop_suggestion = consider labeling this block to be able to break within it + + hir_typeck_params_not_allowed = referencing function parameters is not allowed in naked functions .help = follow the calling convention in asm block to use parameters @@ -254,6 +295,13 @@ hir_typeck_union_pat_dotdot = `..` cannot be used in union patterns hir_typeck_union_pat_multiple_fields = union patterns should have exactly one field +hir_typeck_unlabeled_cf_in_while_condition = + `break` or `continue` with no label in the condition of a `while` loop + .label = unlabeled `{$cf_type}` in the condition of a `while` loop + +hir_typeck_unlabeled_in_labeled_block = + unlabeled `{$cf_type}` inside of a labeled block + .label = `{$cf_type}` statements that would diverge to or through a labeled block need to bear a label hir_typeck_use_is_empty = consider using the `is_empty` method on `{$expr_ty}` to determine if it contains anything diff --git a/compiler/rustc_hir_typeck/src/_match.rs b/compiler/rustc_hir_typeck/src/_match.rs index 61dd8c573073..4ac260cb15f4 100644 --- a/compiler/rustc_hir_typeck/src/_match.rs +++ b/compiler/rustc_hir_typeck/src/_match.rs @@ -600,7 +600,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { let (def_id, args) = match *expected_ty.kind() { // FIXME: Could also check that the RPIT is not defined ty::Alias(ty::Opaque, alias_ty) => (alias_ty.def_id.as_local()?, alias_ty.args), - // FIXME(-Znext-solver): Remove this branch once `replace_opaque_types_with_infer` is gone. + // FIXME(-Znext-solver=no): Remove this branch once `replace_opaque_types_with_infer` is gone. ty::Infer(ty::TyVar(_)) => self .inner .borrow_mut() diff --git a/compiler/rustc_hir_typeck/src/callee.rs b/compiler/rustc_hir_typeck/src/callee.rs index d173fe7c2c26..e915b4fc626f 100644 --- a/compiler/rustc_hir_typeck/src/callee.rs +++ b/compiler/rustc_hir_typeck/src/callee.rs @@ -1,5 +1,6 @@ use std::iter; +use rustc_abi::ExternAbi; use rustc_ast::util::parser::ExprPrecedence; use rustc_errors::{Applicability, Diag, ErrorGuaranteed, StashKey}; use rustc_hir::def::{self, CtorKind, Namespace, Res}; @@ -83,6 +84,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { while result.is_none() && autoderef.next().is_some() { result = self.try_overloaded_call_step(call_expr, callee_expr, arg_exprs, &autoderef); } + self.check_call_custom_abi(autoderef.final_ty(false), call_expr.span); self.register_predicates(autoderef.into_obligations()); let output = match result { @@ -135,6 +137,22 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { output } + /// Functions of type `extern "custom" fn(/* ... */)` cannot be called using `ExprKind::Call`. + /// + /// These functions have a calling convention that is unknown to rust, hence it cannot generate + /// code for the call. The only way to execute such a function is via inline assembly. + fn check_call_custom_abi(&self, callee_ty: Ty<'tcx>, span: Span) { + let abi = match callee_ty.kind() { + ty::FnDef(def_id, _) => self.tcx.fn_sig(def_id).skip_binder().skip_binder().abi, + ty::FnPtr(_, header) => header.abi, + _ => return, + }; + + if let ExternAbi::Custom = abi { + self.tcx.dcx().emit_err(errors::AbiCustomCall { span }); + } + } + #[instrument(level = "debug", skip(self, call_expr, callee_expr, arg_exprs, autoderef), ret)] fn try_overloaded_call_step( &self, diff --git a/compiler/rustc_hir_typeck/src/demand.rs b/compiler/rustc_hir_typeck/src/demand.rs index 152c88ad92a5..5b55fbe91500 100644 --- a/compiler/rustc_hir_typeck/src/demand.rs +++ b/compiler/rustc_hir_typeck/src/demand.rs @@ -260,7 +260,11 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { mut expected_ty_expr: Option<&'tcx hir::Expr<'tcx>>, allow_two_phase: AllowTwoPhase, ) -> Result, Diag<'a>> { - let expected = self.resolve_vars_with_obligations(expected); + let expected = if self.next_trait_solver() { + expected + } else { + self.resolve_vars_with_obligations(expected) + }; let e = match self.coerce(expr, checked_ty, expected, allow_two_phase, None) { Ok(ty) => return Ok(ty), diff --git a/compiler/rustc_hir_typeck/src/errors.rs b/compiler/rustc_hir_typeck/src/errors.rs index 97a90548fc54..abb8cdc1cdf3 100644 --- a/compiler/rustc_hir_typeck/src/errors.rs +++ b/compiler/rustc_hir_typeck/src/errors.rs @@ -2,11 +2,14 @@ use std::borrow::Cow; +use rustc_ast::Label; use rustc_errors::codes::*; use rustc_errors::{ Applicability, Diag, DiagArgValue, DiagCtxtHandle, DiagSymbolList, Diagnostic, EmissionGuarantee, IntoDiagArg, Level, MultiSpan, Subdiagnostic, }; +use rustc_hir as hir; +use rustc_hir::ExprKind; use rustc_macros::{Diagnostic, LintDiagnostic, Subdiagnostic}; use rustc_middle::ty::{self, Ty}; use rustc_span::edition::{Edition, LATEST_STABLE_EDITION}; @@ -721,6 +724,131 @@ pub(crate) struct TrivialCast<'tcx> { pub cast_ty: Ty<'tcx>, } +pub(crate) struct BreakNonLoop<'a> { + pub span: Span, + pub head: Option, + pub kind: &'a str, + pub suggestion: String, + pub loop_label: Option; types::type_(p); if p.eat(T![as]) { if is_use_path_start(p) { - types::path_type(p); + types::path_type_bounds(p, true); } else { p.error("expected a trait"); } } p.expect(T![>]); + m.complete(p, TYPE_ANCHOR); if !p.at(T![::]) { p.error("expected `::`"); } diff --git a/src/tools/rust-analyzer/crates/parser/src/grammar/types.rs b/src/tools/rust-analyzer/crates/parser/src/grammar/types.rs index 9d31e435cf98..908440b5d056 100644 --- a/src/tools/rust-analyzer/crates/parser/src/grammar/types.rs +++ b/src/tools/rust-analyzer/crates/parser/src/grammar/types.rs @@ -330,15 +330,6 @@ fn bare_dyn_trait_type(p: &mut Parser<'_>) { m.complete(p, DYN_TRAIT_TYPE); } -// test path_type -// type A = Foo; -// type B = ::Foo; -// type C = self::Foo; -// type D = super::Foo; -pub(super) fn path_type(p: &mut Parser<'_>) { - path_type_bounds(p, true); -} - // test macro_call_type // type A = foo!(); // type B = crate::foo!(); @@ -365,6 +356,11 @@ fn path_or_macro_type(p: &mut Parser<'_>, allow_bounds: bool) { } } +// test path_type +// type A = Foo; +// type B = ::Foo; +// type C = self::Foo; +// type D = super::Foo; pub(super) fn path_type_bounds(p: &mut Parser<'_>, allow_bounds: bool) { assert!(paths::is_path_start(p)); let m = p.start(); diff --git a/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs b/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs index b1727509b137..f534546ea07e 100644 --- a/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs +++ b/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs @@ -291,6 +291,7 @@ pub enum SyntaxKind { TUPLE_STRUCT_PAT, TUPLE_TYPE, TYPE_ALIAS, + TYPE_ANCHOR, TYPE_ARG, TYPE_BOUND, TYPE_BOUND_LIST, @@ -463,6 +464,7 @@ impl SyntaxKind { | TUPLE_STRUCT_PAT | TUPLE_TYPE | TYPE_ALIAS + | TYPE_ANCHOR | TYPE_ARG | TYPE_BOUND | TYPE_BOUND_LIST diff --git a/src/tools/rust-analyzer/crates/parser/test_data/generated/runner.rs b/src/tools/rust-analyzer/crates/parser/test_data/generated/runner.rs index 030d8e0f04dd..6ec4192830bc 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/generated/runner.rs +++ b/src/tools/rust-analyzer/crates/parser/test_data/generated/runner.rs @@ -83,6 +83,10 @@ mod ok { #[test] fn cast_expr() { run_and_expect_no_errors("test_data/parser/inline/ok/cast_expr.rs"); } #[test] + fn closure_binder() { + run_and_expect_no_errors("test_data/parser/inline/ok/closure_binder.rs"); + } + #[test] fn closure_body_underscore_assignment() { run_and_expect_no_errors( "test_data/parser/inline/ok/closure_body_underscore_assignment.rs", @@ -872,6 +876,10 @@ mod err { run_and_expect_errors("test_data/parser/inline/err/tuple_pat_leading_comma.rs"); } #[test] + fn type_bounds_macro_call_recovery() { + run_and_expect_errors("test_data/parser/inline/err/type_bounds_macro_call_recovery.rs"); + } + #[test] fn type_in_array_recover() { run_and_expect_errors("test_data/parser/inline/err/type_in_array_recover.rs"); } diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/err/0024_many_type_parens.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/err/0024_many_type_parens.rast index f0dbc9b1027f..025c12e4c2a0 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/err/0024_many_type_parens.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/err/0024_many_type_parens.rast @@ -186,13 +186,14 @@ SOURCE_FILE TUPLE_EXPR L_PAREN "(" CLOSURE_EXPR - FOR_KW "for" - GENERIC_PARAM_LIST - L_ANGLE "<" - LIFETIME_PARAM - LIFETIME - LIFETIME_IDENT "'a" - R_ANGLE ">" + CLOSURE_BINDER + FOR_KW "for" + GENERIC_PARAM_LIST + L_ANGLE "<" + LIFETIME_PARAM + LIFETIME + LIFETIME_IDENT "'a" + R_ANGLE ">" WHITESPACE " " BIN_EXPR BIN_EXPR diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/angled_path_without_qual.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/angled_path_without_qual.rast index 0529e9750e7f..53fbe0b615e0 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/angled_path_without_qual.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/angled_path_without_qual.rast @@ -10,11 +10,12 @@ SOURCE_FILE PATH_TYPE PATH PATH_SEGMENT - L_ANGLE "<" - TUPLE_TYPE - L_PAREN "(" - R_PAREN ")" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + TUPLE_TYPE + L_PAREN "(" + R_PAREN ")" + R_ANGLE ">" SEMICOLON ";" WHITESPACE "\n" TYPE_ALIAS @@ -28,21 +29,22 @@ SOURCE_FILE PATH_TYPE PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "A" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "B" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "A" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "B" + R_ANGLE ">" SEMICOLON ";" WHITESPACE "\n" error 13: expected `::` diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rast new file mode 100644 index 000000000000..4722beb61928 --- /dev/null +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rast @@ -0,0 +1,112 @@ +SOURCE_FILE + FN + FN_KW "fn" + WHITESPACE " " + NAME + IDENT "foo" + GENERIC_PARAM_LIST + L_ANGLE "<" + TYPE_PARAM + NAME + IDENT "T" + COLON ":" + WHITESPACE " " + TYPE_BOUND_LIST + TYPE_BOUND + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + ERROR + BANG "!" + TOKEN_TREE + L_BRACK "[" + R_BRACK "]" + COMMA "," + WHITESPACE " " + TYPE_PARAM + NAME + IDENT "T" + COLON ":" + WHITESPACE " " + TYPE_BOUND_LIST + TYPE_BOUND + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + ERROR + BANG "!" + COMMA "," + WHITESPACE " " + TYPE_PARAM + NAME + IDENT "T" + COLON ":" + WHITESPACE " " + TYPE_BOUND_LIST + TYPE_BOUND + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + ERROR + BANG "!" + TOKEN_TREE + L_CURLY "{" + R_CURLY "}" + R_ANGLE ">" + PARAM_LIST + L_PAREN "(" + R_PAREN ")" + WHITESPACE " " + RET_TYPE + THIN_ARROW "->" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Box" + GENERIC_ARG_LIST + L_ANGLE "<" + TYPE_ARG + DYN_TRAIT_TYPE + TYPE_BOUND_LIST + TYPE_BOUND + MACRO_TYPE + MACRO_CALL + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + BANG "!" + WHITESPACE " " + PLUS "+" + WHITESPACE " " + TYPE_BOUND + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + ERROR + BANG "!" + TOKEN_TREE + L_CURLY "{" + R_CURLY "}" + R_ANGLE ">" + WHITESPACE " " + BLOCK_EXPR + STMT_LIST + L_CURLY "{" + R_CURLY "}" + WHITESPACE "\n" +error 12: unexpected `!` in type path, macro calls are not allowed here +error 21: unexpected `!` in type path, macro calls are not allowed here +error 28: unexpected `!` in type path, macro calls are not allowed here +error 43: expected `{`, `[`, `(` +error 48: unexpected `!` in type path, macro calls are not allowed here diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rs b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rs new file mode 100644 index 000000000000..517404fdb0e5 --- /dev/null +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/err/type_bounds_macro_call_recovery.rs @@ -0,0 +1 @@ +fn foo() -> Box {} diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/call_expr.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/call_expr.rast index 19cc8d5ac7cf..7c1d894f7e4c 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/call_expr.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/call_expr.rast @@ -88,13 +88,14 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Foo" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Foo" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF @@ -119,21 +120,22 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Foo" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Trait" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Foo" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Trait" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rast new file mode 100644 index 000000000000..c04dbe1ea0a4 --- /dev/null +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rast @@ -0,0 +1,36 @@ +SOURCE_FILE + FN + FN_KW "fn" + WHITESPACE " " + NAME + IDENT "main" + PARAM_LIST + L_PAREN "(" + R_PAREN ")" + WHITESPACE " " + BLOCK_EXPR + STMT_LIST + L_CURLY "{" + WHITESPACE " " + EXPR_STMT + CLOSURE_EXPR + CLOSURE_BINDER + FOR_KW "for" + GENERIC_PARAM_LIST + L_ANGLE "<" + LIFETIME_PARAM + LIFETIME + LIFETIME_IDENT "'a" + R_ANGLE ">" + WHITESPACE " " + PARAM_LIST + PIPE "|" + PIPE "|" + WHITESPACE " " + TUPLE_EXPR + L_PAREN "(" + R_PAREN ")" + SEMICOLON ";" + WHITESPACE " " + R_CURLY "}" + WHITESPACE "\n" diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rs b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rs new file mode 100644 index 000000000000..a6d8aafb08a4 --- /dev/null +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/closure_binder.rs @@ -0,0 +1 @@ +fn main() { for<'a> || (); } diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/lambda_expr.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/lambda_expr.rast index c25ad8430d0d..ea401d224e69 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/lambda_expr.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/lambda_expr.rast @@ -202,13 +202,14 @@ SOURCE_FILE WHITESPACE "\n " EXPR_STMT CLOSURE_EXPR - FOR_KW "for" - GENERIC_PARAM_LIST - L_ANGLE "<" - LIFETIME_PARAM - LIFETIME - LIFETIME_IDENT "'a" - R_ANGLE ">" + CLOSURE_BINDER + FOR_KW "for" + GENERIC_PARAM_LIST + L_ANGLE "<" + LIFETIME_PARAM + LIFETIME + LIFETIME_IDENT "'a" + R_ANGLE ">" WHITESPACE " " PARAM_LIST PIPE "|" @@ -222,13 +223,14 @@ SOURCE_FILE WHITESPACE "\n " EXPR_STMT CLOSURE_EXPR - FOR_KW "for" - GENERIC_PARAM_LIST - L_ANGLE "<" - LIFETIME_PARAM - LIFETIME - LIFETIME_IDENT "'a" - R_ANGLE ">" + CLOSURE_BINDER + FOR_KW "for" + GENERIC_PARAM_LIST + L_ANGLE "<" + LIFETIME_PARAM + LIFETIME + LIFETIME_IDENT "'a" + R_ANGLE ">" WHITESPACE " " MOVE_KW "move" WHITESPACE " " diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/qual_paths.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/qual_paths.rast index 8c66cfe599f2..10f8a6a75165 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/qual_paths.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/qual_paths.rast @@ -11,21 +11,22 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "A" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "B" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "A" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "B" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF @@ -51,21 +52,22 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "usize" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Default" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "usize" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Default" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/type_path_in_pattern.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/type_path_in_pattern.rast index 297f7575ca6e..3d27afa5ecd7 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/type_path_in_pattern.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/type_path_in_pattern.rast @@ -19,10 +19,11 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - INFER_TYPE - UNDERSCORE "_" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + INFER_TYPE + UNDERSCORE "_" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/where_clause.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/where_clause.rast index a3cbe457e1ac..9adfe2caa732 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/where_clause.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/inline/ok/where_clause.rast @@ -84,21 +84,22 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "T" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Iterator" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Iterator" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0036_fully_qualified.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0036_fully_qualified.rast index 9382020e2f60..2fecb1cc47d8 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0036_fully_qualified.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0036_fully_qualified.rast @@ -45,21 +45,22 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "S" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Iterator" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "S" + WHITESPACE " " + AS_KW "as" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Iterator" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0042_ufcs_call_list.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0042_ufcs_call_list.rast index a536b0e881f0..d1d1ffacf0d3 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0042_ufcs_call_list.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0042_ufcs_call_list.rast @@ -107,13 +107,14 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Foo" - R_ANGLE ">" + TYPE_ANCHOR + L_ANGLE "<" + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "Foo" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0067_where_for_pred.rast b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0067_where_for_pred.rast index cd3b21ae94fd..8bf1090f9cfc 100644 --- a/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0067_where_for_pred.rast +++ b/src/tools/rust-analyzer/crates/parser/test_data/parser/ok/0067_where_for_pred.rast @@ -288,26 +288,27 @@ SOURCE_FILE PATH PATH PATH_SEGMENT - L_ANGLE "<" - REF_TYPE - AMP "&" - LIFETIME - LIFETIME_IDENT "'a" + TYPE_ANCHOR + L_ANGLE "<" + REF_TYPE + AMP "&" + LIFETIME + LIFETIME_IDENT "'a" + WHITESPACE " " + PATH_TYPE + PATH + PATH_SEGMENT + NAME_REF + IDENT "T" + WHITESPACE " " + AS_KW "as" WHITESPACE " " PATH_TYPE PATH PATH_SEGMENT NAME_REF - IDENT "T" - WHITESPACE " " - AS_KW "as" - WHITESPACE " " - PATH_TYPE - PATH - PATH_SEGMENT - NAME_REF - IDENT "Baz" - R_ANGLE ">" + IDENT "Baz" + R_ANGLE ">" COLON2 "::" PATH_SEGMENT NAME_REF diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl.rs index 11dbd9200915..ad2859903348 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl.rs @@ -10,6 +10,7 @@ use std::fmt; +use intern::Symbol; use proc_macro::bridge; mod token_stream; @@ -112,3 +113,135 @@ fn literal_kind_to_internal(kind: bridge::LitKind) -> tt::LitKind { bridge::LitKind::ErrWithGuar => tt::LitKind::Err(()), } } + +pub(super) fn literal_from_str( + s: &str, + span: Span, +) -> Result, ()> { + use proc_macro::bridge::LitKind; + use rustc_lexer::{LiteralKind, Token, TokenKind}; + + let mut tokens = rustc_lexer::tokenize(s); + let minus_or_lit = tokens.next().unwrap_or(Token { kind: TokenKind::Eof, len: 0 }); + + let lit = if minus_or_lit.kind == TokenKind::Minus { + let lit = tokens.next().ok_or(())?; + if !matches!( + lit.kind, + TokenKind::Literal { kind: LiteralKind::Int { .. } | LiteralKind::Float { .. }, .. } + ) { + return Err(()); + } + lit + } else { + minus_or_lit + }; + + if tokens.next().is_some() { + return Err(()); + } + + let TokenKind::Literal { kind, suffix_start } = lit.kind else { return Err(()) }; + let (kind, start_offset, end_offset) = match kind { + LiteralKind::Int { .. } => (LitKind::Integer, 0, 0), + LiteralKind::Float { .. } => (LitKind::Float, 0, 0), + LiteralKind::Char { terminated } => (LitKind::Char, 1, terminated as usize), + LiteralKind::Byte { terminated } => (LitKind::Byte, 2, terminated as usize), + LiteralKind::Str { terminated } => (LitKind::Str, 1, terminated as usize), + LiteralKind::ByteStr { terminated } => (LitKind::ByteStr, 2, terminated as usize), + LiteralKind::CStr { terminated } => (LitKind::CStr, 2, terminated as usize), + LiteralKind::RawStr { n_hashes } => ( + LitKind::StrRaw(n_hashes.unwrap_or_default()), + 2 + n_hashes.unwrap_or_default() as usize, + 1 + n_hashes.unwrap_or_default() as usize, + ), + LiteralKind::RawByteStr { n_hashes } => ( + LitKind::ByteStrRaw(n_hashes.unwrap_or_default()), + 3 + n_hashes.unwrap_or_default() as usize, + 1 + n_hashes.unwrap_or_default() as usize, + ), + LiteralKind::RawCStr { n_hashes } => ( + LitKind::CStrRaw(n_hashes.unwrap_or_default()), + 3 + n_hashes.unwrap_or_default() as usize, + 1 + n_hashes.unwrap_or_default() as usize, + ), + }; + + let (lit, suffix) = s.split_at(suffix_start as usize); + let lit = &lit[start_offset..lit.len() - end_offset]; + let suffix = match suffix { + "" | "_" => None, + suffix => Some(Symbol::intern(suffix)), + }; + + Ok(bridge::Literal { kind, symbol: Symbol::intern(lit), suffix, span }) +} + +pub(super) fn from_token_tree( + tree: bridge::TokenTree, Span, Symbol>, +) -> TokenStream { + match tree { + bridge::TokenTree::Group(group) => { + let group = TopSubtree::from_bridge(group); + TokenStream { token_trees: group.0 } + } + + bridge::TokenTree::Ident(ident) => { + let text = ident.sym; + let ident: tt::Ident = tt::Ident { + sym: text, + span: ident.span, + is_raw: if ident.is_raw { tt::IdentIsRaw::Yes } else { tt::IdentIsRaw::No }, + }; + let leaf = tt::Leaf::from(ident); + let tree = tt::TokenTree::from(leaf); + TokenStream { token_trees: vec![tree] } + } + + bridge::TokenTree::Literal(literal) => { + let token_trees = + if let Some((_minus, symbol)) = literal.symbol.as_str().split_once('-') { + let punct = tt::Punct { + spacing: tt::Spacing::Alone, + span: literal.span, + char: '-' as char, + }; + let leaf: tt::Leaf = tt::Leaf::from(punct); + let minus_tree = tt::TokenTree::from(leaf); + + let literal = tt::Literal { + symbol: Symbol::intern(symbol), + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![minus_tree, tree] + } else { + let literal = tt::Literal { + symbol: literal.symbol, + suffix: literal.suffix, + span: literal.span, + kind: literal_kind_to_internal(literal.kind), + }; + + let leaf: tt::Leaf = tt::Leaf::from(literal); + let tree = tt::TokenTree::from(leaf); + vec![tree] + }; + TokenStream { token_trees } + } + + bridge::TokenTree::Punct(p) => { + let punct = tt::Punct { + char: p.ch as char, + spacing: if p.joint { tt::Spacing::Joint } else { tt::Spacing::Alone }, + span: p.span, + }; + let leaf = tt::Leaf::from(punct); + let tree = tt::TokenTree::from(leaf); + TokenStream { token_trees: vec![tree] } + } + } +} diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs index e0c6e68f8037..5d1271ba81e1 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/rust_analyzer_span.rs @@ -14,16 +14,7 @@ use proc_macro::bridge::{self, server}; use span::{FIXUP_ERASED_FILE_AST_ID_MARKER, Span}; use tt::{TextRange, TextSize}; -use crate::server_impl::{TopSubtree, literal_kind_to_internal, token_stream::TokenStreamBuilder}; -mod tt { - pub use tt::*; - - pub type TokenTree = ::tt::TokenTree; - pub type Leaf = ::tt::Leaf; - pub type Literal = ::tt::Literal; - pub type Punct = ::tt::Punct; - pub type Ident = ::tt::Ident; -} +use crate::server_impl::{from_token_tree, literal_from_str, token_stream::TokenStreamBuilder}; type TokenStream = crate::server_impl::TokenStream; @@ -62,66 +53,7 @@ impl server::FreeFunctions for RaSpanServer { &mut self, s: &str, ) -> Result, ()> { - use proc_macro::bridge::LitKind; - use rustc_lexer::{LiteralKind, Token, TokenKind}; - - let mut tokens = rustc_lexer::tokenize(s); - let minus_or_lit = tokens.next().unwrap_or(Token { kind: TokenKind::Eof, len: 0 }); - - let lit = if minus_or_lit.kind == TokenKind::Minus { - let lit = tokens.next().ok_or(())?; - if !matches!( - lit.kind, - TokenKind::Literal { - kind: LiteralKind::Int { .. } | LiteralKind::Float { .. }, - .. - } - ) { - return Err(()); - } - lit - } else { - minus_or_lit - }; - - if tokens.next().is_some() { - return Err(()); - } - - let TokenKind::Literal { kind, suffix_start } = lit.kind else { return Err(()) }; - let (kind, start_offset, end_offset) = match kind { - LiteralKind::Int { .. } => (LitKind::Integer, 0, 0), - LiteralKind::Float { .. } => (LitKind::Float, 0, 0), - LiteralKind::Char { terminated } => (LitKind::Char, 1, terminated as usize), - LiteralKind::Byte { terminated } => (LitKind::Byte, 2, terminated as usize), - LiteralKind::Str { terminated } => (LitKind::Str, 1, terminated as usize), - LiteralKind::ByteStr { terminated } => (LitKind::ByteStr, 2, terminated as usize), - LiteralKind::CStr { terminated } => (LitKind::CStr, 2, terminated as usize), - LiteralKind::RawStr { n_hashes } => ( - LitKind::StrRaw(n_hashes.unwrap_or_default()), - 2 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - LiteralKind::RawByteStr { n_hashes } => ( - LitKind::ByteStrRaw(n_hashes.unwrap_or_default()), - 3 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - LiteralKind::RawCStr { n_hashes } => ( - LitKind::CStrRaw(n_hashes.unwrap_or_default()), - 3 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - }; - - let (lit, suffix) = s.split_at(suffix_start as usize); - let lit = &lit[start_offset..lit.len() - end_offset]; - let suffix = match suffix { - "" | "_" => None, - suffix => Some(Symbol::intern(suffix)), - }; - - Ok(bridge::Literal { kind, symbol: Symbol::intern(lit), suffix, span: self.call_site }) + literal_from_str(s, self.call_site) } fn emit_diagnostic(&mut self, _: bridge::Diagnostic) { @@ -149,70 +81,7 @@ impl server::TokenStream for RaSpanServer { &mut self, tree: bridge::TokenTree, ) -> Self::TokenStream { - match tree { - bridge::TokenTree::Group(group) => { - let group = TopSubtree::from_bridge(group); - TokenStream { token_trees: group.0 } - } - - bridge::TokenTree::Ident(ident) => { - let text = ident.sym; - let ident: tt::Ident = tt::Ident { - sym: text, - span: ident.span, - is_raw: if ident.is_raw { tt::IdentIsRaw::Yes } else { tt::IdentIsRaw::No }, - }; - let leaf = tt::Leaf::from(ident); - let tree = tt::TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } - } - - bridge::TokenTree::Literal(literal) => { - let token_trees = - if let Some((_minus, symbol)) = literal.symbol.as_str().split_once('-') { - let punct = tt::Punct { - spacing: tt::Spacing::Alone, - span: literal.span, - char: '-' as char, - }; - let leaf: tt::Leaf = tt::Leaf::from(punct); - let minus_tree = tt::TokenTree::from(leaf); - - let literal = tt::Literal { - symbol: Symbol::intern(symbol), - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - let leaf: tt::Leaf = tt::Leaf::from(literal); - let tree = tt::TokenTree::from(leaf); - vec![minus_tree, tree] - } else { - let literal = tt::Literal { - symbol: literal.symbol, - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - - let leaf: tt::Leaf = tt::Leaf::from(literal); - let tree = tt::TokenTree::from(leaf); - vec![tree] - }; - TokenStream { token_trees } - } - - bridge::TokenTree::Punct(p) => { - let punct = tt::Punct { - char: p.ch as char, - spacing: if p.joint { tt::Spacing::Joint } else { tt::Spacing::Alone }, - span: p.span, - }; - let leaf = tt::Leaf::from(punct); - let tree = tt::TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } - } - } + from_token_tree(tree) } fn expand_expr(&mut self, self_: &Self::TokenStream) -> Result { diff --git a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs index d55b269f868d..b493b325e830 100644 --- a/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs +++ b/src/tools/rust-analyzer/crates/proc-macro-srv/src/server_impl/token_id.rs @@ -5,23 +5,9 @@ use std::ops::{Bound, Range}; use intern::Symbol; use proc_macro::bridge::{self, server}; -use crate::server_impl::{TopSubtree, literal_kind_to_internal, token_stream::TokenStreamBuilder}; -mod tt { - pub use span::TokenId; +use crate::server_impl::{from_token_tree, literal_from_str, token_stream::TokenStreamBuilder}; - pub use tt::*; - - pub type TokenTree = ::tt::TokenTree; - pub type Leaf = ::tt::Leaf; - pub type Literal = ::tt::Literal; - pub type Punct = ::tt::Punct; - pub type Ident = ::tt::Ident; -} -type TokenTree = tt::TokenTree; -type Punct = tt::Punct; -type Spacing = tt::Spacing; -type Literal = tt::Literal; -type Span = tt::TokenId; +type Span = span::TokenId; type TokenStream = crate::server_impl::TokenStream; pub struct FreeFunctions; @@ -49,67 +35,7 @@ impl server::FreeFunctions for TokenIdServer { &mut self, s: &str, ) -> Result, ()> { - use proc_macro::bridge::LitKind; - use rustc_lexer::{LiteralKind, Token, TokenKind}; - - let mut tokens = rustc_lexer::tokenize(s); - let minus_or_lit = tokens.next().unwrap_or(Token { kind: TokenKind::Eof, len: 0 }); - - let lit = if minus_or_lit.kind == TokenKind::Minus { - let lit = tokens.next().ok_or(())?; - if !matches!( - lit.kind, - TokenKind::Literal { - kind: LiteralKind::Int { .. } | LiteralKind::Float { .. }, - .. - } - ) { - return Err(()); - } - lit - } else { - minus_or_lit - }; - - if tokens.next().is_some() { - return Err(()); - } - - let TokenKind::Literal { kind, suffix_start } = lit.kind else { return Err(()) }; - - let (kind, start_offset, end_offset) = match kind { - LiteralKind::Int { .. } => (LitKind::Integer, 0, 0), - LiteralKind::Float { .. } => (LitKind::Float, 0, 0), - LiteralKind::Char { terminated } => (LitKind::Char, 1, terminated as usize), - LiteralKind::Byte { terminated } => (LitKind::Byte, 2, terminated as usize), - LiteralKind::Str { terminated } => (LitKind::Str, 1, terminated as usize), - LiteralKind::ByteStr { terminated } => (LitKind::ByteStr, 2, terminated as usize), - LiteralKind::CStr { terminated } => (LitKind::CStr, 2, terminated as usize), - LiteralKind::RawStr { n_hashes } => ( - LitKind::StrRaw(n_hashes.unwrap_or_default()), - 2 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - LiteralKind::RawByteStr { n_hashes } => ( - LitKind::ByteStrRaw(n_hashes.unwrap_or_default()), - 3 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - LiteralKind::RawCStr { n_hashes } => ( - LitKind::CStrRaw(n_hashes.unwrap_or_default()), - 3 + n_hashes.unwrap_or_default() as usize, - 1 + n_hashes.unwrap_or_default() as usize, - ), - }; - - let (lit, suffix) = s.split_at(suffix_start as usize); - let lit = &lit[start_offset..lit.len() - end_offset]; - let suffix = match suffix { - "" | "_" => None, - suffix => Some(Symbol::intern(suffix)), - }; - - Ok(bridge::Literal { kind, symbol: Symbol::intern(lit), suffix, span: self.call_site }) + literal_from_str(s, self.call_site) } fn emit_diagnostic(&mut self, _: bridge::Diagnostic) {} @@ -135,69 +61,7 @@ impl server::TokenStream for TokenIdServer { &mut self, tree: bridge::TokenTree, ) -> Self::TokenStream { - match tree { - bridge::TokenTree::Group(group) => { - let group = TopSubtree::from_bridge(group); - TokenStream { token_trees: group.0 } - } - - bridge::TokenTree::Ident(ident) => { - let ident: tt::Ident = tt::Ident { - sym: ident.sym, - span: ident.span, - is_raw: if ident.is_raw { tt::IdentIsRaw::Yes } else { tt::IdentIsRaw::No }, - }; - let leaf = tt::Leaf::from(ident); - let tree = TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } - } - - bridge::TokenTree::Literal(literal) => { - let token_trees = - if let Some((_minus, symbol)) = literal.symbol.as_str().split_once('-') { - let punct = tt::Punct { - spacing: tt::Spacing::Alone, - span: literal.span, - char: '-' as char, - }; - let leaf: tt::Leaf = tt::Leaf::from(punct); - let minus_tree = tt::TokenTree::from(leaf); - - let literal = Literal { - symbol: Symbol::intern(symbol), - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - let leaf: tt::Leaf = tt::Leaf::from(literal); - let tree = tt::TokenTree::from(leaf); - vec![minus_tree, tree] - } else { - let literal = Literal { - symbol: literal.symbol, - suffix: literal.suffix, - span: literal.span, - kind: literal_kind_to_internal(literal.kind), - }; - - let leaf: tt::Leaf = tt::Leaf::from(literal); - let tree = tt::TokenTree::from(leaf); - vec![tree] - }; - TokenStream { token_trees } - } - - bridge::TokenTree::Punct(p) => { - let punct = Punct { - char: p.ch as char, - spacing: if p.joint { Spacing::Joint } else { Spacing::Alone }, - span: p.span, - }; - let leaf = tt::Leaf::from(punct); - let tree = TokenTree::from(leaf); - TokenStream { token_trees: vec![tree] } - } - } + from_token_tree(tree) } fn expand_expr(&mut self, self_: &Self::TokenStream) -> Result { @@ -337,6 +201,8 @@ impl server::Server for TokenIdServer { #[cfg(test)] mod tests { + use span::TokenId; + use super::*; #[test] @@ -345,18 +211,18 @@ mod tests { token_trees: vec![ tt::TokenTree::Leaf(tt::Leaf::Ident(tt::Ident { sym: Symbol::intern("struct"), - span: tt::TokenId(0), + span: TokenId(0), is_raw: tt::IdentIsRaw::No, })), tt::TokenTree::Leaf(tt::Leaf::Ident(tt::Ident { sym: Symbol::intern("T"), - span: tt::TokenId(0), + span: TokenId(0), is_raw: tt::IdentIsRaw::No, })), tt::TokenTree::Subtree(tt::Subtree { delimiter: tt::Delimiter { - open: tt::TokenId(0), - close: tt::TokenId(0), + open: TokenId(0), + close: TokenId(0), kind: tt::DelimiterKind::Brace, }, len: 0, @@ -372,8 +238,8 @@ mod tests { let subtree_paren_a = vec![ tt::TokenTree::Subtree(tt::Subtree { delimiter: tt::Delimiter { - open: tt::TokenId(0), - close: tt::TokenId(0), + open: TokenId(0), + close: TokenId(0), kind: tt::DelimiterKind::Parenthesis, }, len: 1, @@ -381,24 +247,24 @@ mod tests { tt::TokenTree::Leaf(tt::Leaf::Ident(tt::Ident { is_raw: tt::IdentIsRaw::No, sym: Symbol::intern("a"), - span: tt::TokenId(0), + span: TokenId(0), })), ]; - let t1 = TokenStream::from_str("(a)", tt::TokenId(0)).unwrap(); + let t1 = TokenStream::from_str("(a)", TokenId(0)).unwrap(); assert_eq!(t1.token_trees.len(), 2); assert!(t1.token_trees[0..2] == subtree_paren_a); - let t2 = TokenStream::from_str("(a);", tt::TokenId(0)).unwrap(); + let t2 = TokenStream::from_str("(a);", TokenId(0)).unwrap(); assert_eq!(t2.token_trees.len(), 3); assert!(t2.token_trees[0..2] == subtree_paren_a); - let underscore = TokenStream::from_str("_", tt::TokenId(0)).unwrap(); + let underscore = TokenStream::from_str("_", TokenId(0)).unwrap(); assert!( underscore.token_trees[0] == tt::TokenTree::Leaf(tt::Leaf::Ident(tt::Ident { sym: Symbol::intern("_"), - span: tt::TokenId(0), + span: TokenId(0), is_raw: tt::IdentIsRaw::No, })) ); diff --git a/src/tools/rust-analyzer/crates/project-model/src/cargo_workspace.rs b/src/tools/rust-analyzer/crates/project-model/src/cargo_workspace.rs index 6e730b1aea26..bb02284a5130 100644 --- a/src/tools/rust-analyzer/crates/project-model/src/cargo_workspace.rs +++ b/src/tools/rust-analyzer/crates/project-model/src/cargo_workspace.rs @@ -431,12 +431,6 @@ impl CargoWorkspace { .ok_or(cargo_metadata::Error::NoJson)?; Ok((cargo_metadata::MetadataCommand::parse(stdout)?, None)) })() - .map(|(metadata, error)| { - ( - metadata, - error.map(|e| e.context(format!("Failed to run `{:?}`", meta.cargo_command()))), - ) - }) .with_context(|| format!("Failed to run `{:?}`", meta.cargo_command())) } diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/src/config.rs b/src/tools/rust-analyzer/crates/rust-analyzer/src/config.rs index d1ca8c1a91a3..5cbea9c2b3d9 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/src/config.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/src/config.rs @@ -1192,7 +1192,7 @@ impl ConfigChange { #[derive(Debug, Clone, Eq, PartialEq)] pub enum LinkedProject { ProjectManifest(ProjectManifest), - InlineJsonProject(ProjectJson), + InlineProjectJson(ProjectJson), } impl From for LinkedProject { @@ -1203,7 +1203,7 @@ impl From for LinkedProject { impl From for LinkedProject { fn from(v: ProjectJson) -> Self { - LinkedProject::InlineJsonProject(v) + LinkedProject::InlineProjectJson(v) } } @@ -1597,6 +1597,16 @@ impl Config { term_search_borrowck: self.assist_termSearch_borrowcheck(source_root).to_owned(), } } + + pub fn diagnostic_fixes(&self, source_root: Option) -> DiagnosticsConfig { + // We always want to show quickfixes for diagnostics, even when diagnostics/experimental diagnostics are disabled. + DiagnosticsConfig { + enabled: true, + disable_experimental: false, + ..self.diagnostics(source_root) + } + } + pub fn expand_proc_attr_macros(&self) -> bool { self.procMacro_enable().to_owned() && self.procMacro_attributes_enable().to_owned() } diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/src/handlers/request.rs b/src/tools/rust-analyzer/crates/rust-analyzer/src/handlers/request.rs index 69983a676261..6d46ce68ed47 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/src/handlers/request.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/src/handlers/request.rs @@ -1439,7 +1439,7 @@ pub(crate) fn handle_code_action( }; let assists = snap.analysis.assists_with_fixes( &assists_config, - &snap.config.diagnostics(Some(source_root)), + &snap.config.diagnostic_fixes(Some(source_root)), resolve, frange, )?; @@ -1530,7 +1530,7 @@ pub(crate) fn handle_code_action_resolve( let assists = snap.analysis.assists_with_fixes( &assists_config, - &snap.config.diagnostics(Some(source_root)), + &snap.config.diagnostic_fixes(Some(source_root)), AssistResolveStrategy::Single(assist_resolve), frange, )?; diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/src/lsp/utils.rs b/src/tools/rust-analyzer/crates/rust-analyzer/src/lsp/utils.rs index 673eaa5952f0..5bea7084fdb5 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/src/lsp/utils.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/src/lsp/utils.rs @@ -108,8 +108,7 @@ impl GlobalState { /// edge users from being upset! pub(crate) fn poke_rust_analyzer_developer(&mut self, message: String) { let from_source_build = option_env!("POKE_RA_DEVS").is_some(); - let profiling_enabled = std::env::var("RA_PROFILE").is_ok(); - if from_source_build || profiling_enabled { + if from_source_build { self.show_and_log_error(message, None); } } diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/src/reload.rs b/src/tools/rust-analyzer/crates/rust-analyzer/src/reload.rs index ae9e3e998746..4677880daaf9 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/src/reload.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/src/reload.rs @@ -292,7 +292,7 @@ impl GlobalState { if let (Some(_command), Some(path)) = (&discover_command, &path) { let build = linked_projects.iter().find_map(|project| match project { - LinkedProject::InlineJsonProject(it) => it.crate_by_buildfile(path), + LinkedProject::InlineProjectJson(it) => it.crate_by_buildfile(path), _ => None, }); @@ -318,7 +318,7 @@ impl GlobalState { &progress, ) } - LinkedProject::InlineJsonProject(it) => { + LinkedProject::InlineProjectJson(it) => { let workspace = project_model::ProjectWorkspace::load_inline( it.clone(), &cargo_config, diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/main.rs b/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/main.rs index f6bcb5642c3b..59073af983b7 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/main.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/main.rs @@ -975,10 +975,6 @@ version = \"0.0.0\" } fn out_dirs_check_impl(root_contains_symlink: bool) { - if skip_slow_tests() { - return; - } - let mut server = Project::with_fixture( r###" //- /Cargo.toml @@ -1130,12 +1126,18 @@ fn main() { #[test] fn out_dirs_check() { + if skip_slow_tests() { + return; + } out_dirs_check_impl(false); } #[test] #[cfg(not(windows))] // windows requires elevated permissions to create symlinks fn root_contains_symlink_out_dirs_check() { + if skip_slow_tests() { + return; + } out_dirs_check_impl(true); } diff --git a/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/ratoml.rs b/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/ratoml.rs index 485f32281dde..cac7efd84aaf 100644 --- a/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/ratoml.rs +++ b/src/tools/rust-analyzer/crates/rust-analyzer/tests/slow-tests/ratoml.rs @@ -439,6 +439,7 @@ assist.emitMustUse = true"#, } #[test] +#[ignore = "flaky test that tends to hang"] fn ratoml_inherit_config_from_ws_root() { if skip_slow_tests() { return; diff --git a/src/tools/rust-analyzer/crates/syntax/rust.ungram b/src/tools/rust-analyzer/crates/syntax/rust.ungram index 10abca7d35d9..c81da06682ee 100644 --- a/src/tools/rust-analyzer/crates/syntax/rust.ungram +++ b/src/tools/rust-analyzer/crates/syntax/rust.ungram @@ -39,7 +39,10 @@ PathSegment = | NameRef GenericArgList? | NameRef ParenthesizedArgList RetType? | NameRef ReturnTypeSyntax -| '<' Type ('as' PathType)? '>' +| TypeAnchor + +TypeAnchor = + '<' Type ('as' PathType)? '>' ReturnTypeSyntax = '(' '..' ')' @@ -98,7 +101,7 @@ WhereClause = 'where' predicates:(WherePred (',' WherePred)* ','?) WherePred = - ('for' GenericParamList)? (Lifetime | Type) ':' TypeBoundList? + ('for' GenericParamList)? (Lifetime | Type) ':' TypeBoundList? //*************************// diff --git a/src/tools/rust-analyzer/crates/syntax/src/ast/generated/nodes.rs b/src/tools/rust-analyzer/crates/syntax/src/ast/generated/nodes.rs index cd9f4dba8908..04c7e8a578c5 100644 --- a/src/tools/rust-analyzer/crates/syntax/src/ast/generated/nodes.rs +++ b/src/tools/rust-analyzer/crates/syntax/src/ast/generated/nodes.rs @@ -1232,21 +1232,13 @@ impl PathSegment { support::child(&self.syntax) } #[inline] - pub fn path_type(&self) -> Option { support::child(&self.syntax) } - #[inline] pub fn ret_type(&self) -> Option { support::child(&self.syntax) } #[inline] pub fn return_type_syntax(&self) -> Option { support::child(&self.syntax) } #[inline] - pub fn ty(&self) -> Option { support::child(&self.syntax) } + pub fn type_anchor(&self) -> Option { support::child(&self.syntax) } #[inline] pub fn coloncolon_token(&self) -> Option { support::token(&self.syntax, T![::]) } - #[inline] - pub fn l_angle_token(&self) -> Option { support::token(&self.syntax, T![<]) } - #[inline] - pub fn r_angle_token(&self) -> Option { support::token(&self.syntax, T![>]) } - #[inline] - pub fn as_token(&self) -> Option { support::token(&self.syntax, T![as]) } } pub struct PathType { pub(crate) syntax: SyntaxNode, @@ -1739,6 +1731,21 @@ impl TypeAlias { #[inline] pub fn type_token(&self) -> Option { support::token(&self.syntax, T![type]) } } +pub struct TypeAnchor { + pub(crate) syntax: SyntaxNode, +} +impl TypeAnchor { + #[inline] + pub fn path_type(&self) -> Option { support::child(&self.syntax) } + #[inline] + pub fn ty(&self) -> Option { support::child(&self.syntax) } + #[inline] + pub fn l_angle_token(&self) -> Option { support::token(&self.syntax, T![<]) } + #[inline] + pub fn r_angle_token(&self) -> Option { support::token(&self.syntax, T![>]) } + #[inline] + pub fn as_token(&self) -> Option { support::token(&self.syntax, T![as]) } +} pub struct TypeArg { pub(crate) syntax: SyntaxNode, } @@ -7108,6 +7115,42 @@ impl fmt::Debug for TypeAlias { f.debug_struct("TypeAlias").field("syntax", &self.syntax).finish() } } +impl AstNode for TypeAnchor { + #[inline] + fn kind() -> SyntaxKind + where + Self: Sized, + { + TYPE_ANCHOR + } + #[inline] + fn can_cast(kind: SyntaxKind) -> bool { kind == TYPE_ANCHOR } + #[inline] + fn cast(syntax: SyntaxNode) -> Option { + if Self::can_cast(syntax.kind()) { + Some(Self { syntax }) + } else { + None + } + } + #[inline] + fn syntax(&self) -> &SyntaxNode { &self.syntax } +} +impl hash::Hash for TypeAnchor { + fn hash(&self, state: &mut H) { self.syntax.hash(state); } +} +impl Eq for TypeAnchor {} +impl PartialEq for TypeAnchor { + fn eq(&self, other: &Self) -> bool { self.syntax == other.syntax } +} +impl Clone for TypeAnchor { + fn clone(&self) -> Self { Self { syntax: self.syntax.clone() } } +} +impl fmt::Debug for TypeAnchor { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("TypeAnchor").field("syntax", &self.syntax).finish() + } +} impl AstNode for TypeArg { #[inline] fn kind() -> SyntaxKind @@ -10624,6 +10667,11 @@ impl std::fmt::Display for TypeAlias { std::fmt::Display::fmt(self.syntax(), f) } } +impl std::fmt::Display for TypeAnchor { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + std::fmt::Display::fmt(self.syntax(), f) + } +} impl std::fmt::Display for TypeArg { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { std::fmt::Display::fmt(self.syntax(), f) diff --git a/src/tools/rust-analyzer/crates/syntax/src/ast/node_ext.rs b/src/tools/rust-analyzer/crates/syntax/src/ast/node_ext.rs index b9ccd34cff06..dcf853427e53 100644 --- a/src/tools/rust-analyzer/crates/syntax/src/ast/node_ext.rs +++ b/src/tools/rust-analyzer/crates/syntax/src/ast/node_ext.rs @@ -276,18 +276,15 @@ impl ast::PathSegment { _ => PathSegmentKind::Name(name_ref), } } else { - match self.syntax().first_child_or_token()?.kind() { - T![<] => { - // or - // T is any TypeRef, Trait has to be a PathType - let mut type_refs = - self.syntax().children().filter(|node| ast::Type::can_cast(node.kind())); - let type_ref = type_refs.next().and_then(ast::Type::cast); - let trait_ref = type_refs.next().and_then(ast::PathType::cast); - PathSegmentKind::Type { type_ref, trait_ref } - } - _ => return None, - } + let anchor = self.type_anchor()?; + // FIXME: Move this over to `ast::TypeAnchor` + // or + // T is any TypeRef, Trait has to be a PathType + let mut type_refs = + anchor.syntax().children().filter(|node| ast::Type::can_cast(node.kind())); + let type_ref = type_refs.next().and_then(ast::Type::cast); + let trait_ref = type_refs.next().and_then(ast::PathType::cast); + PathSegmentKind::Type { type_ref, trait_ref } }; Some(res) } @@ -473,7 +470,7 @@ impl ast::Impl { // [#15778](https://github.com/rust-lang/rust-analyzer/issues/15778) impl ast::PathSegment { pub fn qualifying_trait(&self) -> Option { - let mut path_types = support::children(self.syntax()); + let mut path_types = support::children(self.type_anchor()?.syntax()); let first = path_types.next()?; path_types.next().or(Some(first)) } diff --git a/src/tools/rust-analyzer/crates/test-fixture/src/lib.rs b/src/tools/rust-analyzer/crates/test-fixture/src/lib.rs index 96e1301f227e..8eb48f8d93e7 100644 --- a/src/tools/rust-analyzer/crates/test-fixture/src/lib.rs +++ b/src/tools/rust-analyzer/crates/test-fixture/src/lib.rs @@ -538,6 +538,21 @@ pub fn disallow_cfg(_attr: TokenStream, input: TokenStream) -> TokenStream { disabled: false, }, ), + ( + r#" +#[proc_macro_attribute] +pub fn generate_suffixed_type(_attr: TokenStream, input: TokenStream) -> TokenStream { + input +} +"# + .into(), + ProcMacro { + name: Symbol::intern("generate_suffixed_type"), + kind: ProcMacroKind::Attr, + expander: sync::Arc::new(GenerateSuffixedTypeProcMacroExpander), + disabled: false, + }, + ), ]) } @@ -919,3 +934,57 @@ impl ProcMacroExpander for DisallowCfgProcMacroExpander { Ok(subtree.clone()) } } + +// Generates a new type by adding a suffix to the original name +#[derive(Debug)] +struct GenerateSuffixedTypeProcMacroExpander; +impl ProcMacroExpander for GenerateSuffixedTypeProcMacroExpander { + fn expand( + &self, + subtree: &TopSubtree, + _attrs: Option<&TopSubtree>, + _env: &Env, + _def_site: Span, + call_site: Span, + _mixed_site: Span, + _current_dir: String, + ) -> Result { + let TokenTree::Leaf(Leaf::Ident(ident)) = &subtree.0[1] else { + return Err(ProcMacroExpansionError::Panic("incorrect Input".into())); + }; + + let ident = match ident.sym.as_str() { + "struct" => { + let TokenTree::Leaf(Leaf::Ident(ident)) = &subtree.0[2] else { + return Err(ProcMacroExpansionError::Panic("incorrect Input".into())); + }; + ident + } + + "enum" => { + let TokenTree::Leaf(Leaf::Ident(ident)) = &subtree.0[4] else { + return Err(ProcMacroExpansionError::Panic("incorrect Input".into())); + }; + ident + } + + _ => { + return Err(ProcMacroExpansionError::Panic("incorrect Input".into())); + } + }; + + let generated_ident = tt::Ident { + sym: Symbol::intern(&format!("{}Suffix", ident.sym)), + span: ident.span, + is_raw: tt::IdentIsRaw::No, + }; + + let ret = quote! { call_site => + #subtree + + struct #generated_ident; + }; + + Ok(ret) + } +} diff --git a/src/tools/rust-analyzer/docs/book/src/non_cargo_based_projects.md b/src/tools/rust-analyzer/docs/book/src/non_cargo_based_projects.md index 151f8758a176..bbdb48bbbc9e 100644 --- a/src/tools/rust-analyzer/docs/book/src/non_cargo_based_projects.md +++ b/src/tools/rust-analyzer/docs/book/src/non_cargo_based_projects.md @@ -5,7 +5,7 @@ build system, you’ll have to describe the structure of your project for rust-analyzer in the `rust-project.json` format: ```typescript -interface JsonProject { +interface ProjectJson { /// Path to the sysroot directory. /// /// The sysroot is where rustc looks for the diff --git a/src/tools/rust-analyzer/editors/code/package-lock.json b/src/tools/rust-analyzer/editors/code/package-lock.json index 18fb097aad7f..ab431140c10d 100644 --- a/src/tools/rust-analyzer/editors/code/package-lock.json +++ b/src/tools/rust-analyzer/editors/code/package-lock.json @@ -5500,9 +5500,9 @@ } }, "node_modules/tar-fs": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.2.tgz", - "integrity": "sha512-EsaAXwxmx8UB7FRKqeozqEPop69DXcmYwTQwXvyAPF352HJsPdkVhvTaDPYqfNgruveJIJy3TA2l+2zj8LJIJA==", + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/tar-fs/-/tar-fs-2.1.3.tgz", + "integrity": "sha512-090nwYJDmlhwFwEW3QQl+vaNnxsO2yVsd45eTKRBzSzu+hlb1w2K9inVq5b0ngXuLVqQ4ApvsUHHnu/zQNkWAg==", "dev": true, "license": "MIT", "optional": true, diff --git a/src/tools/rust-analyzer/rust-version b/src/tools/rust-analyzer/rust-version index 5b47d1bbaed7..af0dd5c9acda 100644 --- a/src/tools/rust-analyzer/rust-version +++ b/src/tools/rust-analyzer/rust-version @@ -1 +1 @@ -a8e4c68dcb4dc1e48a0db294c5323cab0227fcb9 +7c10378e1fee5ddc6573b916aeb884ab10e0de17 diff --git a/src/tools/rustbook/Cargo.lock b/src/tools/rustbook/Cargo.lock index 8893846b5fa5..ed67fa7d1a9e 100644 --- a/src/tools/rustbook/Cargo.lock +++ b/src/tools/rustbook/Cargo.lock @@ -47,9 +47,9 @@ dependencies = [ [[package]] name = "anstream" -version = "0.6.18" +version = "0.6.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8acc5369981196006228e28809f761875c0327210a891e941f4c683b3a99529b" +checksum = "301af1932e46185686725e0fad2f8f2aa7da69dd70bf6ecc44d6b703844a3933" dependencies = [ "anstyle", "anstyle-parse", @@ -62,36 +62,36 @@ dependencies = [ [[package]] name = "anstyle" -version = "1.0.10" +version = "1.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "55cc3b69f167a1ef2e161439aa98aed94e6028e5f9a59be9a6ffb47aef1651f9" +checksum = "862ed96ca487e809f1c8e5a8447f6ee2cf102f846893800b20cebdf541fc6bbd" [[package]] name = "anstyle-parse" -version = "0.2.6" +version = "0.2.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b2d16507662817a6a20a9ea92df6652ee4f94f914589377d69f3b21bc5798a9" +checksum = "4e7644824f0aa2c7b9384579234ef10eb7efb6a0deb83f9630a49594dd9c15c2" dependencies = [ "utf8parse", ] [[package]] name = "anstyle-query" -version = "1.1.2" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "79947af37f4177cfead1110013d678905c37501914fba0efea834c3fe9a8d60c" +checksum = "6c8bdeb6047d8983be085bab0ba1472e6dc604e7041dbf6fcd5e71523014fae9" dependencies = [ "windows-sys", ] [[package]] name = "anstyle-wincon" -version = "3.0.7" +version = "3.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca3534e77181a9cc07539ad51f2141fe32f6c3ffd4df76db8ad92346b003ae4e" +checksum = "403f75924867bb1033c59fbf0797484329750cfbe3c4325cd33127941fabc882" dependencies = [ "anstyle", - "once_cell", + "once_cell_polyfill", "windows-sys", ] @@ -124,9 +124,9 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" [[package]] name = "bitflags" -version = "2.9.0" +version = "2.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c8214115b7bf84099f1309324e63141d4c5d7cc26862f97a0a857dbefe165bd" +checksum = "1b8e56985ec62d17e9c1001dc89c88ecd7dc08e47eba5ec7c29c7b5eeecde967" [[package]] name = "block-buffer" @@ -150,15 +150,15 @@ dependencies = [ [[package]] name = "bumpalo" -version = "3.17.0" +version = "3.18.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1628fb46dfa0b37568d12e5edd512553eccf6a22a78e8bde00bb4aed84d5bdbf" +checksum = "793db76d6187cd04dff33004d8e6c9cc4e05cd330500379d2394209271b4aeee" [[package]] name = "cc" -version = "1.2.22" +version = "1.2.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "32db95edf998450acc7881c932f94cd9b05c87b4b2599e8bab064753da4acfd1" +checksum = "956a5e21988b87f372569b66183b78babf23ebc2e744b733e4350a752c4dafac" dependencies = [ "shlex", ] @@ -185,9 +185,9 @@ dependencies = [ [[package]] name = "clap" -version = "4.5.38" +version = "4.5.39" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed93b9805f8ba930df42c2590f05453d5ec36cbb85d018868a5b24d31f6ac000" +checksum = "fd60e63e9be68e5fb56422e397cf9baddded06dae1d2e523401542383bc72a9f" dependencies = [ "clap_builder", "clap_derive", @@ -195,9 +195,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.5.38" +version = "4.5.39" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "379026ff283facf611b0ea629334361c4211d1b12ee01024eec1591133b04120" +checksum = "89cc6392a1f72bbeb820d71f32108f61fdaf18bc526e1d23954168a67759ef51" dependencies = [ "anstream", "anstyle", @@ -208,9 +208,9 @@ dependencies = [ [[package]] name = "clap_complete" -version = "4.5.50" +version = "4.5.52" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c91d3baa3bcd889d60e6ef28874126a0b384fd225ab83aa6d8a801c519194ce1" +checksum = "1a554639e42d0c838336fc4fbedb9e2df3ad1fa4acda149f9126b4ccfcd7900f" dependencies = [ "clap", ] @@ -235,9 +235,9 @@ checksum = "f46ad14479a25103f283c0f10005961cf086d8dc42205bb44c46ac563475dca6" [[package]] name = "colorchoice" -version = "1.0.3" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b63caa9aa9397e2d9480a9b13673856c78d8ac123288526c37d7839f2a86990" +checksum = "b05b61dc5112cbb17e4b6cd61790d9845d13888356391624cbe7e41efeac1e75" [[package]] name = "core-foundation-sys" @@ -459,9 +459,9 @@ checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f" [[package]] name = "errno" -version = "0.3.11" +version = "0.3.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "976dd42dc7e85965fe702eb8164f21f450704bdde31faefd6471dba214cb594e" +checksum = "cea14ef9355e3beab063703aa9dab15afd25f0667c341310c1e5274bb1d0da18" dependencies = [ "libc", "windows-sys", @@ -482,9 +482,9 @@ checksum = "37909eebbb50d72f9059c3b6d82c0463f2ff062c9e95845c43a6c9c0355411be" [[package]] name = "flate2" -version = "1.1.1" +version = "1.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ced92e76e966ca2fd84c8f7aa01a4aea65b0eb6648d72f7c8f3e2764a67fece" +checksum = "4a3d7db9596fecd151c5f638c0ee5d5bd487b6e0ea232e5dc96d5250f6f94b1d" dependencies = [ "crc32fast", "miniz_oxide", @@ -531,7 +531,7 @@ version = "0.2.21" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "14dbbfd5c71d70241ecf9e6f13737f7b5ce823821063188d7e46c41d371eebd5" dependencies = [ - "unicode-width", + "unicode-width 0.1.14", ] [[package]] @@ -564,9 +564,9 @@ dependencies = [ [[package]] name = "hashbrown" -version = "0.15.3" +version = "0.15.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "84b26c544d002229e640969970a2e74021aadf6e2f96372b9c58eff97de08eb3" +checksum = "5971ac85611da7067dbfcabef3c70ebb5606018acd9e2a3903a0da507521e0d5" [[package]] name = "heck" @@ -680,9 +680,9 @@ checksum = "00210d6893afc98edb752b664b8890f0ef174c8adbb8d0be9710fa66fbbf72d3" [[package]] name = "icu_properties" -version = "2.0.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2549ca8c7241c82f59c80ba2a6f415d931c5b58d24fb8412caa1a1f02c49139a" +checksum = "016c619c1eeb94efb86809b015c58f479963de65bdb6253345c1a1276f22e32b" dependencies = [ "displaydoc", "icu_collections", @@ -696,9 +696,9 @@ dependencies = [ [[package]] name = "icu_properties_data" -version = "2.0.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8197e866e47b68f8f7d95249e172903bec06004b18b2937f1095d40a0c57de04" +checksum = "298459143998310acd25ffe6810ed544932242d3f07083eee1084d83a71bd632" [[package]] name = "icu_provider" @@ -768,9 +768,9 @@ checksum = "4a5f13b858c8d314ee3e8f639011f7ccefe71f97f96e50151fb991f267928e2c" [[package]] name = "jiff" -version = "0.2.13" +version = "0.2.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f02000660d30638906021176af16b17498bd0d12813dbfe7b276d8bc7f3c0806" +checksum = "a194df1107f33c79f4f93d02c80798520551949d59dfad22b6157048a88cca93" dependencies = [ "jiff-static", "log", @@ -781,9 +781,9 @@ dependencies = [ [[package]] name = "jiff-static" -version = "0.2.13" +version = "0.2.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3c30758ddd7188629c6713fc45d1188af4f44c90582311d0c8d8c9907f60c48" +checksum = "6c6e1db7ed32c6c71b759497fae34bf7933636f75a251b9e736555da426f6442" dependencies = [ "proc-macro2", "quote", @@ -835,9 +835,9 @@ checksum = "241eaef5fd12c88705a01fc1066c48c4b36e0dd4377dcdc7ec3942cea7a69956" [[package]] name = "lock_api" -version = "0.4.12" +version = "0.4.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17" +checksum = "96936507f153605bddfcda068dd804796c84324ed2510809e5b2a624c81da765" dependencies = [ "autocfg", "scopeguard", @@ -961,7 +961,7 @@ dependencies = [ "pulldown-cmark-to-cmark 19.0.1", "serde_json", "thiserror 1.0.69", - "toml 0.8.22", + "toml 0.8.23", ] [[package]] @@ -1024,13 +1024,19 @@ version = "1.21.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "42f5e15c9953c5e4ccceeb2e7382a716482c34515315f7b03532b8b4e8393d2d" +[[package]] +name = "once_cell_polyfill" +version = "1.70.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4895175b425cb1f87721b59f0f286c2092bd4af812243672510e1ac53e2e0ad" + [[package]] name = "onig" version = "6.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "336b9c63443aceef14bea841b899035ae3abe89b7c486aaf4c5bd8aafedac3f0" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "libc", "once_cell", "onig_sys", @@ -1048,9 +1054,9 @@ dependencies = [ [[package]] name = "opener" -version = "0.8.1" +version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "de96cad6ee771be7f68df884d3767460b4684012308d8342ed5623fe62b2628c" +checksum = "771b9704f8cd8b424ec747a320b30b47517a6966ba2c7da90047c16f4a962223" dependencies = [ "bstr", "normpath", @@ -1059,9 +1065,9 @@ dependencies = [ [[package]] name = "parking_lot" -version = "0.12.3" +version = "0.12.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27" +checksum = "70d58bf43669b5795d1576d0641cfb6fbb2057bf629506267a92807158584a13" dependencies = [ "lock_api", "parking_lot_core", @@ -1069,9 +1075,9 @@ dependencies = [ [[package]] name = "parking_lot_core" -version = "0.9.10" +version = "0.9.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8" +checksum = "bc838d2a56b5b1a6c25f55575dfc605fabb63bb2365f6c2353ef9159aa69e4a5" dependencies = [ "cfg-if", "libc", @@ -1206,9 +1212,9 @@ dependencies = [ [[package]] name = "portable-atomic" -version = "1.11.0" +version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "350e9b48cbc6b0e028b0473b114454c6316e57336ee184ceab6e53f72c178b3e" +checksum = "f84267b20a16ea918e43c6a88433c2d54fa145c92a811b5b047ccbe153674483" [[package]] name = "portable-atomic-util" @@ -1249,7 +1255,7 @@ version = "0.10.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76979bea66e7875e7509c4ec5300112b316af87fa7a252ca91c448b32dfe3993" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "memchr", "pulldown-cmark-escape 0.10.1", "unicase", @@ -1261,7 +1267,7 @@ version = "0.12.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f86ba2052aebccc42cbbb3ed234b8b13ce76f75c3551a303cb2bcffcff12bb14" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "getopts", "memchr", "pulldown-cmark-escape 0.11.0", @@ -1315,11 +1321,11 @@ checksum = "74765f6d916ee2faa39bc8e68e4f3ed8949b48cccdac59983d287a7cb71ce9c5" [[package]] name = "railroad" -version = "0.3.2" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0ecedffc46c1b2cb04f4b80e094eae6b3f3f470a9635f1f396dd5206428f6b58" +checksum = "e6d5b8e8a7c20c600f9b98cbf46b64e63d5c9e69deb98cee1ff264de9f1dda5d" dependencies = [ - "unicode-width", + "unicode-width 0.2.0", ] [[package]] @@ -1343,7 +1349,7 @@ version = "0.5.12" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "928fca9cf2aa042393a8325b9ead81d2f0df4cb12e1e24cef072922ccd99c5af" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", ] [[package]] @@ -1393,7 +1399,7 @@ version = "1.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c71e83d6afe7ff64890ec6b71d6a69bb8a610ab78ce364b3352876bb4c801266" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", "errno", "libc", "linux-raw-sys", @@ -1402,9 +1408,9 @@ dependencies = [ [[package]] name = "rustversion" -version = "1.0.20" +version = "1.0.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eded382c5f5f786b989652c49544c4877d9f015cc22e145a5ea8ea66c2921cd2" +checksum = "8a0d197bd2c9dc6e53b84da9556a69ba4cdfab8619eb41a8bd1cc2027a0f6b1d" [[package]] name = "ryu" @@ -1467,9 +1473,9 @@ dependencies = [ [[package]] name = "serde_spanned" -version = "0.6.8" +version = "0.6.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "87607cb1398ed59d48732e575a4c28a7a8ebf2454b964fe3f224f2afc07909e1" +checksum = "bf41e0cfaf7226dca15e8197172c295a782857fcb97fad1808a166870dee75a3" dependencies = [ "serde", ] @@ -1499,9 +1505,9 @@ checksum = "56199f7ddabf13fe5074ce809e7d3f42b42ae711800501b5b16ea82ad029c39d" [[package]] name = "smallvec" -version = "1.15.0" +version = "1.15.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8917285742e9f3e1683f0a9c4e6b57960b7314d0b08d30d1ecd426713ee2eee9" +checksum = "67b1b7a3b5fe4f1376887184045fcf45c69e92af734b7aaddc05fb777b6fbd03" [[package]] name = "stable_deref_trait" @@ -1584,9 +1590,9 @@ dependencies = [ [[package]] name = "tempfile" -version = "3.19.1" +version = "3.20.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7437ac7763b9b123ccf33c338a5cc1bac6f69b45a136c19bdd8a65e3916435bf" +checksum = "e8a64e3985349f2441a1a9ef0b853f869006c3855f2cda6862a94d26ebb9d6a1" dependencies = [ "fastrand", "getrandom", @@ -1683,9 +1689,9 @@ dependencies = [ [[package]] name = "toml" -version = "0.8.22" +version = "0.8.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "05ae329d1f08c4d17a59bed7ff5b5a769d062e64a62d34a3261b219e62cd5aae" +checksum = "dc1beb996b9d83529a9e75c17a1686767d148d70663143c7854d8b4a09ced362" dependencies = [ "serde", "serde_spanned", @@ -1695,18 +1701,18 @@ dependencies = [ [[package]] name = "toml_datetime" -version = "0.6.9" +version = "0.6.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3da5db5a963e24bc68be8b17b6fa82814bb22ee8660f192bb182771d498f09a3" +checksum = "22cddaf88f4fbc13c51aebbf5f8eceb5c7c5a9da2ac40a13519eb5b0a0e8f11c" dependencies = [ "serde", ] [[package]] name = "toml_edit" -version = "0.22.26" +version = "0.22.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "310068873db2c5b3e7659d2cc35d21855dbafa50d1ce336397c666e3cb08137e" +checksum = "41fe8c660ae4257887cf66394862d21dbca4a6ddd26f04a3560410406a2f819a" dependencies = [ "indexmap", "serde", @@ -1718,9 +1724,9 @@ dependencies = [ [[package]] name = "toml_write" -version = "0.1.1" +version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfb942dfe1d8e29a7ee7fcbde5bd2b9a25fb89aa70caea2eba3bee836ff41076" +checksum = "5d99f8c9a7727884afe522e9bd5edbfc91a3312b36a77b5fb8926e4c31a41801" [[package]] name = "topological-sort" @@ -1758,6 +1764,12 @@ version = "0.1.14" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7dd6e30e90baa6f72411720665d41d89b9a3d039dc45b8faea1ddd07f617f6af" +[[package]] +name = "unicode-width" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1fc81956842c57dac11422a97c3b8195a1ff727f06e85c84ed2e8aa277c9a0fd" + [[package]] name = "url" version = "2.5.4" @@ -1872,9 +1884,9 @@ dependencies = [ [[package]] name = "web_atoms" -version = "0.1.2" +version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b9c5f0bc545ea3b20b423e33b9b457764de0b3730cd957f6c6aa6c301785f6e" +checksum = "57ffde1dc01240bdf9992e3205668b235e59421fd085e8a317ed98da0178d414" dependencies = [ "phf", "phf_codegen", @@ -1893,9 +1905,9 @@ dependencies = [ [[package]] name = "windows-core" -version = "0.61.0" +version = "0.61.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4763c1de310c86d75a878046489e2e5ba02c649d185f21c67d4cf8a56d098980" +checksum = "c0fdd3ddb90610c7638aa2b3a3ab2904fb9e5cdbecc643ddb3647212781c4ae3" dependencies = [ "windows-implement", "windows-interface", @@ -1934,18 +1946,18 @@ checksum = "76840935b766e1b0a05c0066835fb9ec80071d4c09a16f6bd5f7e655e3c14c38" [[package]] name = "windows-result" -version = "0.3.2" +version = "0.3.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c64fd11a4fd95df68efcfee5f44a294fe71b8bc6a91993e2791938abcc712252" +checksum = "56f42bd332cc6c8eac5af113fc0c1fd6a8fd2aa08a0119358686e5160d0586c6" dependencies = [ "windows-link", ] [[package]] name = "windows-strings" -version = "0.4.0" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a2ba9642430ee452d5a7aa78d72907ebe8cfda358e8cb7918a2050581322f97" +checksum = "56e6c93f3a0c3b36176cb1327a4958a0353d5d166c2a35cb268ace15e91d3b57" dependencies = [ "windows-link", ] @@ -2038,7 +2050,7 @@ version = "0.39.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1" dependencies = [ - "bitflags 2.9.0", + "bitflags 2.9.1", ] [[package]] diff --git a/src/tools/tidy/src/deps.rs b/src/tools/tidy/src/deps.rs index fdca7a7a40e2..170dcd626a28 100644 --- a/src/tools/tidy/src/deps.rs +++ b/src/tools/tidy/src/deps.rs @@ -441,6 +441,7 @@ const PERMITTED_RUSTC_DEPENDENCIES: &[&str] = &[ "windows-strings", "windows-sys", "windows-targets", + "windows-threading", "windows_aarch64_gnullvm", "windows_aarch64_msvc", "windows_i686_gnu", diff --git a/tests/codegen/autovec/dont-shuffle-bswaps-opt2.rs b/tests/codegen/autovec/dont-shuffle-bswaps-opt2.rs new file mode 100644 index 000000000000..c354228acc50 --- /dev/null +++ b/tests/codegen/autovec/dont-shuffle-bswaps-opt2.rs @@ -0,0 +1,31 @@ +//@ compile-flags: -Copt-level=2 + +#![crate_type = "lib"] +#![no_std] + +// This test is paired with the arch-specific -opt3.rs test. + +// The code is from https://github.com/rust-lang/rust/issues/122805. +// Ensure we do not generate the shufflevector instruction +// to avoid complicating the code. + +// CHECK-LABEL: define{{.*}}void @convert( +// CHECK-NOT: shufflevector +#[no_mangle] +pub fn convert(value: [u16; 8]) -> [u8; 16] { + #[cfg(target_endian = "little")] + let bswap = u16::to_be; + #[cfg(target_endian = "big")] + let bswap = u16::to_le; + let addr16 = [ + bswap(value[0]), + bswap(value[1]), + bswap(value[2]), + bswap(value[3]), + bswap(value[4]), + bswap(value[5]), + bswap(value[6]), + bswap(value[7]), + ]; + unsafe { core::mem::transmute::<_, [u8; 16]>(addr16) } +} diff --git a/tests/codegen/dont-shuffle-bswaps.rs b/tests/codegen/autovec/dont-shuffle-bswaps-opt3.rs similarity index 58% rename from tests/codegen/dont-shuffle-bswaps.rs rename to tests/codegen/autovec/dont-shuffle-bswaps-opt3.rs index c1dab2bc2953..203d12005de2 100644 --- a/tests/codegen/dont-shuffle-bswaps.rs +++ b/tests/codegen/autovec/dont-shuffle-bswaps-opt3.rs @@ -1,29 +1,27 @@ -//@ revisions: OPT2 OPT3 OPT3_S390X -//@[OPT2] compile-flags: -Copt-level=2 -//@[OPT3] compile-flags: -C opt-level=3 -// some targets don't do the opt we are looking for -//@[OPT3] only-64bit -//@[OPT3] ignore-s390x -//@[OPT3_S390X] compile-flags: -C opt-level=3 -C target-cpu=z13 -//@[OPT3_S390X] only-s390x +//@ revisions: AARCH64 X86_64 Z13 +//@ compile-flags: -Copt-level=3 +//@[AARCH64] only-aarch64 +//@[X86_64] only-x86_64 +//@[Z13] only-s390x +//@[Z13] compile-flags: -Ctarget-cpu=z13 #![crate_type = "lib"] #![no_std] +// This test is paired with the arch-neutral -opt2.rs test + // The code is from https://github.com/rust-lang/rust/issues/122805. // Ensure we do not generate the shufflevector instruction // to avoid complicating the code. + // CHECK-LABEL: define{{.*}}void @convert( // CHECK-NOT: shufflevector + // On higher opt levels, this should just be a bswap: -// OPT3: load <8 x i16> -// OPT3-NEXT: call <8 x i16> @llvm.bswap -// OPT3-NEXT: store <8 x i16> -// OPT3-NEXT: ret void -// OPT3_S390X: load <8 x i16> -// OPT3_S390X-NEXT: call <8 x i16> @llvm.bswap -// OPT3_S390X-NEXT: store <8 x i16> -// OPT3_S390X-NEXT: ret void +// CHECK: load <8 x i16> +// CHECK-NEXT: call <8 x i16> @llvm.bswap +// CHECK-NEXT: store <8 x i16> +// CHECK-NEXT: ret void #[no_mangle] pub fn convert(value: [u16; 8]) -> [u8; 16] { #[cfg(target_endian = "little")] diff --git a/tests/codegen/retpoline.rs b/tests/codegen/retpoline.rs new file mode 100644 index 000000000000..30fdd9c2db2c --- /dev/null +++ b/tests/codegen/retpoline.rs @@ -0,0 +1,29 @@ +// ignore-tidy-linelength +// Test that the +// `retpoline-external-thunk`, `retpoline-indirect-branches`, `retpoline-indirect-calls` +// target features are (not) emitted when the `retpoline/retpoline-external-thunk` flag is (not) set. + +//@ revisions: disabled enabled_retpoline enabled_retpoline_external_thunk +//@ needs-llvm-components: x86 +//@ compile-flags: --target x86_64-unknown-linux-gnu +//@ [enabled_retpoline] compile-flags: -Zretpoline +//@ [enabled_retpoline_external_thunk] compile-flags: -Zretpoline-external-thunk + +#![crate_type = "lib"] +#![feature(no_core, lang_items)] +#![no_core] + +#[lang = "sized"] +trait Sized {} + +#[no_mangle] +pub fn foo() { + // CHECK: @foo() unnamed_addr #0 + + // disabled-NOT: attributes #0 = { {{.*}}"target-features"="{{[^"]*}}+retpoline-external-thunk{{.*}} } + // disabled-NOT: attributes #0 = { {{.*}}"target-features"="{{[^"]*}}+retpoline-indirect-branches{{.*}} } + // disabled-NOT: attributes #0 = { {{.*}}"target-features"="{{[^"]*}}+retpoline-indirect-calls{{.*}} } + + // enabled_retpoline: attributes #0 = { {{.*}}"target-features"="{{[^"]*}}+retpoline-indirect-branches,+retpoline-indirect-calls{{.*}} } + // enabled_retpoline_external_thunk: attributes #0 = { {{.*}}"target-features"="{{[^"]*}}+retpoline-external-thunk,+retpoline-indirect-branches,+retpoline-indirect-calls{{.*}} } +} diff --git a/tests/crashes/139825.rs b/tests/crashes/139825.rs deleted file mode 100644 index 8c5b6b80f0ba..000000000000 --- a/tests/crashes/139825.rs +++ /dev/null @@ -1,5 +0,0 @@ -//@ known-bug: #139825 -//@compile-flags: --check-cfg=cfg(docsrs,test) --crate-type lib -struct a -where - for<#[cfg(b)] c> u8:; diff --git a/tests/debuginfo/type-names.rs b/tests/debuginfo/type-names.rs index 3c7eab7e8d71..ac61fef48fe1 100644 --- a/tests/debuginfo/type-names.rs +++ b/tests/debuginfo/type-names.rs @@ -19,7 +19,7 @@ // gdb-check:type = type_names::GenericStruct // gdb-command:whatis generic_struct2 -// gdb-check:type = type_names::GenericStruct usize> +// gdb-check:type = type_names::GenericStruct usize> // gdb-command:whatis mod_struct // gdb-check:type = type_names::mod1::Struct2 @@ -379,7 +379,7 @@ fn main() { let simple_struct = Struct1; let generic_struct1: GenericStruct = GenericStruct(PhantomData); - let generic_struct2: GenericStruct usize> = + let generic_struct2: GenericStruct usize> = GenericStruct(PhantomData); let mod_struct = mod1::Struct2; diff --git a/tests/incremental/hashes/trait_defs.rs b/tests/incremental/hashes/trait_defs.rs index cb8716d90b07..7141ddb0d7ed 100644 --- a/tests/incremental/hashes/trait_defs.rs +++ b/tests/incremental/hashes/trait_defs.rs @@ -440,7 +440,7 @@ trait TraitAddExternModifier { // Change extern "C" to extern "stdcall" #[cfg(any(cfail1,cfail4))] -trait TraitChangeExternCToRustIntrinsic { +trait TraitChangeExternCToExternSystem { // -------------------------------------------------------------- // ------------------------- // -------------------------------------------------------------- @@ -458,7 +458,7 @@ trait TraitChangeExternCToRustIntrinsic { #[rustc_clean(cfg="cfail3")] #[rustc_clean(except="opt_hir_owner_nodes,fn_sig", cfg="cfail5")] #[rustc_clean(cfg="cfail6")] - extern "stdcall" fn method(); + extern "system" fn method(); } diff --git a/tests/mir-opt/early_otherwise_branch.opt3.EarlyOtherwiseBranch.diff b/tests/mir-opt/early_otherwise_branch.opt3.EarlyOtherwiseBranch.diff index 7b94a4c2bf73..22ebe2f3f297 100644 --- a/tests/mir-opt/early_otherwise_branch.opt3.EarlyOtherwiseBranch.diff +++ b/tests/mir-opt/early_otherwise_branch.opt3.EarlyOtherwiseBranch.diff @@ -32,16 +32,12 @@ StorageDead(_4); _9 = discriminant((_3.0: Option2)); - switchInt(move _9) -> [0: bb2, 1: bb3, 2: bb4, otherwise: bb9]; -+ StorageLive(_12); + _12 = discriminant((_3.1: Option2)); -+ StorageLive(_13); + _13 = Ne(copy _9, move _12); -+ StorageDead(_12); + switchInt(move _13) -> [0: bb7, otherwise: bb1]; } bb1: { -+ StorageDead(_13); _0 = const 1_u32; - goto -> bb8; + goto -> bb5; @@ -100,7 +96,6 @@ + } + + bb7: { -+ StorageDead(_13); + switchInt(copy _9) -> [0: bb4, 1: bb3, 2: bb2, otherwise: bb6]; } } diff --git a/tests/mir-opt/early_otherwise_branch.opt4.EarlyOtherwiseBranch.diff b/tests/mir-opt/early_otherwise_branch.opt4.EarlyOtherwiseBranch.diff index f52795baef81..0da0eb3c53cb 100644 --- a/tests/mir-opt/early_otherwise_branch.opt4.EarlyOtherwiseBranch.diff +++ b/tests/mir-opt/early_otherwise_branch.opt4.EarlyOtherwiseBranch.diff @@ -32,16 +32,12 @@ StorageDead(_4); _9 = discriminant((_3.0: Option2)); - switchInt(move _9) -> [0: bb2, 1: bb3, 2: bb4, otherwise: bb9]; -+ StorageLive(_12); + _12 = discriminant((_3.1: Option2)); -+ StorageLive(_13); + _13 = Ne(copy _9, move _12); -+ StorageDead(_12); + switchInt(move _13) -> [0: bb7, otherwise: bb1]; } bb1: { -+ StorageDead(_13); _0 = const 1_u32; - goto -> bb8; + goto -> bb5; @@ -100,7 +96,6 @@ + } + + bb7: { -+ StorageDead(_13); + switchInt(copy _9) -> [0: bb4, 1: bb3, 2: bb2, otherwise: bb6]; } } diff --git a/tests/mir-opt/early_otherwise_branch.opt5.EarlyOtherwiseBranch.diff b/tests/mir-opt/early_otherwise_branch.opt5.EarlyOtherwiseBranch.diff index b7447ef0c469..b13d21e2d7ab 100644 --- a/tests/mir-opt/early_otherwise_branch.opt5.EarlyOtherwiseBranch.diff +++ b/tests/mir-opt/early_otherwise_branch.opt5.EarlyOtherwiseBranch.diff @@ -20,13 +20,11 @@ StorageDead(_5); StorageDead(_4); - switchInt(copy (_3.0: u32)) -> [1: bb2, 2: bb3, 3: bb4, otherwise: bb1]; -+ StorageLive(_6); + _6 = Ne(copy (_3.0: u32), copy (_3.1: u32)); + switchInt(move _6) -> [0: bb6, otherwise: bb1]; } bb1: { -+ StorageDead(_6); _0 = const 0_u32; - goto -> bb8; + goto -> bb5; @@ -70,7 +68,6 @@ - bb8: { - StorageDead(_3); - return; -+ StorageDead(_6); + switchInt(copy (_3.0: u32)) -> [1: bb4, 2: bb3, 3: bb2, otherwise: bb1]; } } diff --git a/tests/mir-opt/early_otherwise_branch.rs b/tests/mir-opt/early_otherwise_branch.rs index 382c38ceb3ab..19a5d25de2df 100644 --- a/tests/mir-opt/early_otherwise_branch.rs +++ b/tests/mir-opt/early_otherwise_branch.rs @@ -1,6 +1,10 @@ //@ test-mir-pass: EarlyOtherwiseBranch //@ compile-flags: -Zmir-enable-passes=+UnreachableEnumBranching +#![feature(custom_mir, core_intrinsics)] + +use std::intrinsics::mir::*; + enum Option2 { Some(T), None, @@ -124,6 +128,34 @@ fn opt5_failed_type(x: u32, y: u64) -> u32 { } } +// EMIT_MIR early_otherwise_branch.target_self.EarlyOtherwiseBranch.diff +#[custom_mir(dialect = "runtime")] +fn target_self(val: i32) { + // CHECK-LABEL: fn target_self( + // CHECK: Ne( + // CHECK-NEXT: switchInt + mir! { + { + Goto(bb1) + } + bb1 = { + match val { + 0 => bb2, + _ => bb1, + } + } + bb2 = { + match val { + 0 => bb3, + _ => bb1, + } + } + bb3 = { + Return() + } + } +} + fn main() { opt1(None, Some(0)); opt2(None, Some(0)); @@ -131,4 +163,5 @@ fn main() { opt4(Option2::None, Option2::Some(0)); opt5(0, 0); opt5_failed(0, 0); + target_self(1); } diff --git a/tests/mir-opt/early_otherwise_branch.target_self.EarlyOtherwiseBranch.diff b/tests/mir-opt/early_otherwise_branch.target_self.EarlyOtherwiseBranch.diff new file mode 100644 index 000000000000..4f70847bcdf8 --- /dev/null +++ b/tests/mir-opt/early_otherwise_branch.target_self.EarlyOtherwiseBranch.diff @@ -0,0 +1,28 @@ +- // MIR for `target_self` before EarlyOtherwiseBranch ++ // MIR for `target_self` after EarlyOtherwiseBranch + + fn target_self(_1: i32) -> () { + let mut _0: (); ++ let mut _2: bool; + + bb0: { + goto -> bb1; + } + + bb1: { +- switchInt(copy _1) -> [0: bb2, otherwise: bb1]; ++ _2 = Ne(copy _1, copy _1); ++ switchInt(move _2) -> [0: bb3, otherwise: bb1]; + } + + bb2: { +- switchInt(copy _1) -> [0: bb3, otherwise: bb1]; ++ return; + } + + bb3: { +- return; ++ switchInt(copy _1) -> [0: bb2, otherwise: bb1]; + } + } + diff --git a/tests/mir-opt/early_otherwise_branch_3_element_tuple.opt2.EarlyOtherwiseBranch.diff b/tests/mir-opt/early_otherwise_branch_3_element_tuple.opt2.EarlyOtherwiseBranch.diff index 831d8cbb4d60..e0878167e441 100644 --- a/tests/mir-opt/early_otherwise_branch_3_element_tuple.opt2.EarlyOtherwiseBranch.diff +++ b/tests/mir-opt/early_otherwise_branch_3_element_tuple.opt2.EarlyOtherwiseBranch.diff @@ -42,16 +42,12 @@ StorageDead(_5); _14 = discriminant((_4.0: Option2)); - switchInt(move _14) -> [0: bb2, 1: bb4, 2: bb6, otherwise: bb12]; -+ StorageLive(_18); + _18 = discriminant((_4.1: Option2)); -+ StorageLive(_19); + _19 = Ne(copy _14, move _18); -+ StorageDead(_18); + switchInt(move _19) -> [0: bb10, otherwise: bb1]; } bb1: { -+ StorageDead(_19); _0 = const 1_u32; - goto -> bb11; + goto -> bb8; @@ -134,7 +130,6 @@ + } + + bb10: { -+ StorageDead(_19); + switchInt(copy _14) -> [0: bb2, 1: bb3, 2: bb4, otherwise: bb9]; } } diff --git a/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-abort.diff b/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-abort.diff index 8ebd07b9c9c1..e61a3e8d7383 100644 --- a/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-abort.diff +++ b/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-abort.diff @@ -5,7 +5,7 @@ let mut _0: usize; bb0: { -- _0 = std::intrinsics::min_align_of::() -> [return: bb1, unwind unreachable]; +- _0 = std::intrinsics::align_of::() -> [return: bb1, unwind unreachable]; + _0 = AlignOf(T); + goto -> bb1; } diff --git a/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-unwind.diff b/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-unwind.diff index 8ebd07b9c9c1..e61a3e8d7383 100644 --- a/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-unwind.diff +++ b/tests/mir-opt/lower_intrinsics.align_of.LowerIntrinsics.panic-unwind.diff @@ -5,7 +5,7 @@ let mut _0: usize; bb0: { -- _0 = std::intrinsics::min_align_of::() -> [return: bb1, unwind unreachable]; +- _0 = std::intrinsics::align_of::() -> [return: bb1, unwind unreachable]; + _0 = AlignOf(T); + goto -> bb1; } diff --git a/tests/mir-opt/lower_intrinsics.rs b/tests/mir-opt/lower_intrinsics.rs index 1e4f20241947..7729e502ad6b 100644 --- a/tests/mir-opt/lower_intrinsics.rs +++ b/tests/mir-opt/lower_intrinsics.rs @@ -51,7 +51,7 @@ pub fn size_of() -> usize { pub fn align_of() -> usize { // CHECK-LABEL: fn align_of( // CHECK: {{_.*}} = AlignOf(T); - core::intrinsics::min_align_of::() + core::intrinsics::align_of::() } // EMIT_MIR lower_intrinsics.forget.LowerIntrinsics.diff diff --git a/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-abort.mir index 30eafe8594b3..2eee8a97db0d 100644 --- a/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-abort.mir +++ b/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-abort.mir @@ -39,7 +39,7 @@ fn vec_deref_to_slice(_1: &Vec) -> &[u8] { } scope 15 (inlined std::mem::size_of::) { } - scope 16 (inlined align_of::) { + scope 16 (inlined std::mem::align_of::) { } scope 17 (inlined slice_from_raw_parts::) { debug data => _3; diff --git a/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-unwind.mir index 30eafe8594b3..2eee8a97db0d 100644 --- a/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-unwind.mir +++ b/tests/mir-opt/pre-codegen/vec_deref.vec_deref_to_slice.PreCodegen.after.panic-unwind.mir @@ -39,7 +39,7 @@ fn vec_deref_to_slice(_1: &Vec) -> &[u8] { } scope 15 (inlined std::mem::size_of::) { } - scope 16 (inlined align_of::) { + scope 16 (inlined std::mem::align_of::) { } scope 17 (inlined slice_from_raw_parts::) { debug data => _3; diff --git a/tests/pretty/postfix-match/precedence.pp b/tests/pretty/postfix-match/precedence.pp index 967aa7bc39ef..2052b445a2b3 100644 --- a/tests/pretty/postfix-match/precedence.pp +++ b/tests/pretty/postfix-match/precedence.pp @@ -26,7 +26,7 @@ pub fn main() { _ => {} }; (4 as usize).match { _ => {} }; - (return).match { _ => {} }; + return.match { _ => {} }; (a = 42).match { _ => {} }; (|| {}).match { _ => {} }; (42..101).match { _ => {} }; diff --git a/tests/run-make/cpp-global-destructors/rmake.rs b/tests/run-make/cpp-global-destructors/rmake.rs index 9bc5c84e10db..92aeb67c2785 100644 --- a/tests/run-make/cpp-global-destructors/rmake.rs +++ b/tests/run-make/cpp-global-destructors/rmake.rs @@ -6,15 +6,11 @@ //@ ignore-cross-compile // Reason: the compiled binary is executed -//@ ignore-none -// Reason: no-std is not supported. //@ ignore-wasm32 //@ ignore-wasm64 // Reason: compiling C++ to WASM may cause problems. -// Neither of these are tested in full CI. -//@ ignore-nvptx64-nvidia-cuda -// Reason: can't find crate "std" +// Not exercised in full CI, but sgx technically supports std. //@ ignore-sgx use run_make_support::{build_native_static_lib_cxx, run, rustc}; diff --git a/tests/run-make/export-executable-symbols/rmake.rs b/tests/run-make/export-executable-symbols/rmake.rs index 77f968189b65..dc8c59b9c742 100644 --- a/tests/run-make/export-executable-symbols/rmake.rs +++ b/tests/run-make/export-executable-symbols/rmake.rs @@ -10,8 +10,7 @@ // (See #85673) //@ ignore-wasm32 //@ ignore-wasm64 -//@ ignore-none -// Reason: no-std is not supported +//@ needs-target-std use run_make_support::{bin_name, llvm_readobj, rustc}; diff --git a/tests/run-make/incr-foreign-head-span/rmake.rs b/tests/run-make/incr-foreign-head-span/rmake.rs index 92e2ed5f8793..d9841b314641 100644 --- a/tests/run-make/incr-foreign-head-span/rmake.rs +++ b/tests/run-make/incr-foreign-head-span/rmake.rs @@ -5,10 +5,7 @@ // source file from disk during compilation of a downstream crate. // See https://github.com/rust-lang/rust/issues/86480 -//@ ignore-none -// Reason: no-std is not supported -//@ ignore-nvptx64-nvidia-cuda -// Reason: can't find crate for 'std' +//@ needs-target-std use run_make_support::{rfs, rust_lib_name, rustc}; diff --git a/tests/run-make/incr-prev-body-beyond-eof/rmake.rs b/tests/run-make/incr-prev-body-beyond-eof/rmake.rs index 47dce85248ab..cfa8d5b46cd9 100644 --- a/tests/run-make/incr-prev-body-beyond-eof/rmake.rs +++ b/tests/run-make/incr-prev-body-beyond-eof/rmake.rs @@ -7,11 +7,7 @@ // was hashed by rustc in addition to the span length, and the fix still // works. -//@ ignore-none -// reason: no-std is not supported - -//@ ignore-nvptx64-nvidia-cuda -// FIXME: can't find crate for `std` +//@ needs-target-std use run_make_support::{rfs, rustc}; diff --git a/tests/run-make/incr-test-moved-file/rmake.rs b/tests/run-make/incr-test-moved-file/rmake.rs index 0ba1b0d58fee..dfba95d3fedb 100644 --- a/tests/run-make/incr-test-moved-file/rmake.rs +++ b/tests/run-make/incr-test-moved-file/rmake.rs @@ -9,10 +9,7 @@ // for successful compilation. // See https://github.com/rust-lang/rust/issues/83112 -//@ ignore-none -// Reason: no-std is not supported -//@ ignore-nvptx64-nvidia-cuda -// FIXME: can't find crate for 'std' +//@ needs-target-std use run_make_support::{rfs, rustc}; diff --git a/tests/run-make/moved-src-dir-fingerprint-ice/rmake.rs b/tests/run-make/moved-src-dir-fingerprint-ice/rmake.rs index f63146e692ac..0d96b40e8a43 100644 --- a/tests/run-make/moved-src-dir-fingerprint-ice/rmake.rs +++ b/tests/run-make/moved-src-dir-fingerprint-ice/rmake.rs @@ -12,10 +12,7 @@ // sessions. // See https://github.com/rust-lang/rust/issues/85019 -//@ ignore-none -// Reason: no-std is not supported -//@ ignore-nvptx64-nvidia-cuda -// FIXME: can't find crate for 'std' +//@ needs-target-std use run_make_support::{rfs, rust_lib_name, rustc}; diff --git a/tests/rustdoc-json/fn_pointer/abi.rs b/tests/rustdoc-json/fn_pointer/abi.rs index 34150c0fe89e..ec76e0f66362 100644 --- a/tests/rustdoc-json/fn_pointer/abi.rs +++ b/tests/rustdoc-json/fn_pointer/abi.rs @@ -1,4 +1,4 @@ -#![feature(abi_vectorcall)] +#![feature(rust_cold_cc)] //@ is "$.index[?(@.name=='AbiRust')].inner.type_alias.type.function_pointer.header.abi" \"Rust\" pub type AbiRust = fn(); @@ -15,8 +15,5 @@ pub type AbiCUnwind = extern "C-unwind" fn(); //@ is "$.index[?(@.name=='AbiSystemUnwind')].inner.type_alias.type.function_pointer.header.abi" '{"System": {"unwind": true}}' pub type AbiSystemUnwind = extern "system-unwind" fn(); -//@ is "$.index[?(@.name=='AbiVecorcall')].inner.type_alias.type.function_pointer.header.abi.Other" '"\"vectorcall\""' -pub type AbiVecorcall = extern "vectorcall" fn(); - -//@ is "$.index[?(@.name=='AbiVecorcallUnwind')].inner.type_alias.type.function_pointer.header.abi.Other" '"\"vectorcall-unwind\""' -pub type AbiVecorcallUnwind = extern "vectorcall-unwind" fn(); +//@ is "$.index[?(@.name=='AbiRustCold')].inner.type_alias.type.function_pointer.header.abi.Other" '"\"rust-cold\""' +pub type AbiRustCold = extern "rust-cold" fn(); diff --git a/tests/rustdoc-json/fns/abi.rs b/tests/rustdoc-json/fns/abi.rs index 7277bb1f59a4..3373d135c89d 100644 --- a/tests/rustdoc-json/fns/abi.rs +++ b/tests/rustdoc-json/fns/abi.rs @@ -1,4 +1,4 @@ -#![feature(abi_vectorcall)] +#![feature(rust_cold_cc)] //@ is "$.index[?(@.name=='abi_rust')].inner.function.header.abi" \"Rust\" pub fn abi_rust() {} @@ -15,8 +15,5 @@ pub extern "C-unwind" fn abi_c_unwind() {} //@ is "$.index[?(@.name=='abi_system_unwind')].inner.function.header.abi" '{"System": {"unwind": true}}' pub extern "system-unwind" fn abi_system_unwind() {} -//@ is "$.index[?(@.name=='abi_vectorcall')].inner.function.header.abi.Other" '"\"vectorcall\""' -pub extern "vectorcall" fn abi_vectorcall() {} - -//@ is "$.index[?(@.name=='abi_vectorcall_unwind')].inner.function.header.abi.Other" '"\"vectorcall-unwind\""' -pub extern "vectorcall-unwind" fn abi_vectorcall_unwind() {} +//@ is "$.index[?(@.name=='abi_rust_cold')].inner.function.header.abi.Other" '"\"rust-cold\""' +pub extern "rust-cold" fn abi_rust_cold() {} diff --git a/tests/rustdoc-json/methods/abi.rs b/tests/rustdoc-json/methods/abi.rs index fa2387ddf67a..be6a11784f55 100644 --- a/tests/rustdoc-json/methods/abi.rs +++ b/tests/rustdoc-json/methods/abi.rs @@ -1,5 +1,4 @@ -#![feature(abi_vectorcall)] - +#![feature(rust_cold_cc)] //@ has "$.index[?(@.name=='Foo')]" pub struct Foo; @@ -19,11 +18,8 @@ impl Foo { //@ is "$.index[?(@.name=='abi_system_unwind')].inner.function.header.abi" '{"System": {"unwind": true}}' pub extern "system-unwind" fn abi_system_unwind() {} - //@ is "$.index[?(@.name=='abi_vectorcall')].inner.function.header.abi.Other" '"\"vectorcall\""' - pub extern "vectorcall" fn abi_vectorcall() {} - - //@ is "$.index[?(@.name=='abi_vectorcall_unwind')].inner.function.header.abi.Other" '"\"vectorcall-unwind\""' - pub extern "vectorcall-unwind" fn abi_vectorcall_unwind() {} + //@ is "$.index[?(@.name=='abi_rust_cold')].inner.function.header.abi.Other" '"\"rust-cold\""' + pub extern "rust-cold" fn abi_rust_cold() {} } pub trait Bar { @@ -42,9 +38,6 @@ pub trait Bar { //@ is "$.index[?(@.name=='trait_abi_system_unwind')].inner.function.header.abi" '{"System": {"unwind": true}}' extern "system-unwind" fn trait_abi_system_unwind() {} - //@ is "$.index[?(@.name=='trait_abi_vectorcall')].inner.function.header.abi.Other" '"\"vectorcall\""' - extern "vectorcall" fn trait_abi_vectorcall() {} - - //@ is "$.index[?(@.name=='trait_abi_vectorcall_unwind')].inner.function.header.abi.Other" '"\"vectorcall-unwind\""' - extern "vectorcall-unwind" fn trait_abi_vectorcall_unwind() {} + //@ is "$.index[?(@.name=='trait_abi_rust_cold')].inner.function.header.abi.Other" '"\"rust-cold\""' + extern "rust-cold" fn trait_abi_rust_cold() {} } diff --git a/tests/rustdoc-json/vectorcall.rs b/tests/rustdoc-json/vectorcall.rs new file mode 100644 index 000000000000..19cac244f422 --- /dev/null +++ b/tests/rustdoc-json/vectorcall.rs @@ -0,0 +1,27 @@ +#![feature(abi_vectorcall)] +//@ only-x86_64 + +//@ is "$.index[?(@.name=='AbiVectorcall')].inner.type_alias.type.function_pointer.header.abi.Other" '"\"vectorcall\""' +pub type AbiVectorcall = extern "vectorcall" fn(); + +//@ is "$.index[?(@.name=='AbiVectorcallUnwind')].inner.type_alias.type.function_pointer.header.abi.Other" '"\"vectorcall-unwind\""' +pub type AbiVectorcallUnwind = extern "vectorcall-unwind" fn(); + +//@ has "$.index[?(@.name=='Foo')]" +pub struct Foo; + +impl Foo { + //@ is "$.index[?(@.name=='abi_vectorcall')].inner.function.header.abi.Other" '"\"vectorcall\""' + pub extern "vectorcall" fn abi_vectorcall() {} + + //@ is "$.index[?(@.name=='abi_vectorcall_unwind')].inner.function.header.abi.Other" '"\"vectorcall-unwind\""' + pub extern "vectorcall-unwind" fn abi_vectorcall_unwind() {} +} + +pub trait Bar { + //@ is "$.index[?(@.name=='trait_abi_vectorcall')].inner.function.header.abi.Other" '"\"vectorcall\""' + extern "vectorcall" fn trait_abi_vectorcall() {} + + //@ is "$.index[?(@.name=='trait_abi_vectorcall_unwind')].inner.function.header.abi.Other" '"\"vectorcall-unwind\""' + extern "vectorcall-unwind" fn trait_abi_vectorcall_unwind() {} +} diff --git a/tests/rustdoc/cfg-bool.rs b/tests/rustdoc/cfg-bool.rs index 34fdfbe930e1..0aaa132e0b54 100644 --- a/tests/rustdoc/cfg-bool.rs +++ b/tests/rustdoc/cfg-bool.rs @@ -3,11 +3,15 @@ // regression test for https://github.com/rust-lang/rust/issues/138112 -//@ has 'foo/fn.foo.html' '//div[@class="stab portability"]' 'Available nowhere' +//@ has 'foo/index.html' +//@ has - '//*[@class="stab portability"]/@title' 'Available nowhere' + +//@ count 'foo/fn.foo.html' '//*[@class="stab portability"]' 1 +//@ has 'foo/fn.foo.html' '//*[@class="stab portability"]' 'Available nowhere' #[doc(cfg(false))] pub fn foo() {} -// a cfg(true) will simply be ommited, as it is the same as no cfg. -//@ !has 'foo/fn.bar.html' '//div[@class="stab portability"]' '' +// a cfg(true) will simply be omitted, as it is the same as no cfg. +//@ count 'foo/fn.bar.html' '//*[@class="stab portability"]' 0 #[doc(cfg(true))] pub fn bar() {} diff --git a/tests/rustdoc/macro/macro-generated-macro.macro_morestuff_pre.html b/tests/rustdoc/macro/macro-generated-macro.macro_morestuff_pre.html index 28f15522a82f..4dcc8111c6ff 100644 --- a/tests/rustdoc/macro/macro-generated-macro.macro_morestuff_pre.html +++ b/tests/rustdoc/macro/macro-generated-macro.macro_morestuff_pre.html @@ -1,7 +1,7 @@ macro_rules! morestuff { ( - <= "space between most kinds of tokens" : 1 $x + @ :: >>= 'static - "no space inside paren or bracket" : (2 a) [2 a] $(2 $a:tt)* + <= "space between most kinds of tokens" : 1 $x:ident + @ :: >>= + 'static "no space inside paren or bracket" : (2 a) [2 a] $(2 $a:tt)* "space inside curly brace" : { 2 a } "no space inside empty delimiters" : () [] {} "no space before comma or semicolon" : a, (a), { a }, a; [T; 0]; diff --git a/tests/rustdoc/macro/macro-generated-macro.rs b/tests/rustdoc/macro/macro-generated-macro.rs index e77d0cf89e74..dfb152bafb62 100644 --- a/tests/rustdoc/macro/macro-generated-macro.rs +++ b/tests/rustdoc/macro/macro-generated-macro.rs @@ -25,7 +25,7 @@ make_macro!(linebreak 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 //@ snapshot macro_morestuff_pre macro_generated_macro/macro.morestuff.html //pre/text() make_macro!(morestuff - "space between most kinds of tokens": 1 $x + @ :: >>= 'static + "space between most kinds of tokens": 1 $x:ident + @ :: >>= 'static "no space inside paren or bracket": (2 a) [2 a] $(2 $a:tt)* "space inside curly brace": { 2 a } "no space inside empty delimiters": () [] {} diff --git a/tests/ui-fulldeps/pprust-parenthesis-insertion.rs b/tests/ui-fulldeps/pprust-parenthesis-insertion.rs index c566ac459e0d..36916e978562 100644 --- a/tests/ui-fulldeps/pprust-parenthesis-insertion.rs +++ b/tests/ui-fulldeps/pprust-parenthesis-insertion.rs @@ -63,8 +63,8 @@ static EXPRS: &[&str] = &[ "(2 += 2) += 2", // Return has lower precedence than a binary operator. "(return 2) + 2", - "2 + (return 2)", // FIXME: no parenthesis needed. - "(return) + 2", // FIXME: no parenthesis needed. + "2 + return 2", + "return + 2", // These mean different things. "return - 2", "(return) - 2", diff --git a/tests/ui-fulldeps/session-diagnostic/diagnostic-derive.stderr b/tests/ui-fulldeps/session-diagnostic/diagnostic-derive.stderr index 03fca17aa55d..001699b2bc72 100644 --- a/tests/ui-fulldeps/session-diagnostic/diagnostic-derive.stderr +++ b/tests/ui-fulldeps/session-diagnostic/diagnostic-derive.stderr @@ -583,18 +583,32 @@ error: cannot find attribute `multipart_suggestion` in this scope | LL | #[multipart_suggestion(no_crate_suggestion)] | ^^^^^^^^^^^^^^^^^^^^ + | +help: `multipart_suggestion` is an attribute that can be used by the derive macro `Subdiagnostic`, you might be missing a `derive` attribute + | +LL + #[derive(Subdiagnostic)] +LL | struct MultipartSuggestion { + | error: cannot find attribute `multipart_suggestion` in this scope --> $DIR/diagnostic-derive.rs:647:3 | LL | #[multipart_suggestion()] | ^^^^^^^^^^^^^^^^^^^^ + | +help: `multipart_suggestion` is an attribute that can be used by the derive macro `Subdiagnostic`, you might be missing a `derive` attribute + | +LL + #[derive(Subdiagnostic)] +LL | struct MultipartSuggestion { + | error: cannot find attribute `multipart_suggestion` in this scope --> $DIR/diagnostic-derive.rs:651:7 | LL | #[multipart_suggestion(no_crate_suggestion)] | ^^^^^^^^^^^^^^^^^^^^ + | + = note: `multipart_suggestion` is an attribute that can be used by the derive macro `Subdiagnostic`, you might be missing a `derive` attribute error[E0425]: cannot find value `nonsense` in module `crate::fluent_generated` --> $DIR/diagnostic-derive.rs:75:8 diff --git a/tests/ui-fulldeps/stable-mir/check_abi.rs b/tests/ui-fulldeps/stable-mir/check_abi.rs index 71edf813a7be..15ef583709b0 100644 --- a/tests/ui-fulldeps/stable-mir/check_abi.rs +++ b/tests/ui-fulldeps/stable-mir/check_abi.rs @@ -21,10 +21,13 @@ use stable_mir::abi::{ ArgAbi, CallConvention, FieldsShape, IntegerLength, PassMode, Primitive, Scalar, ValueAbi, VariantsShape, }; +use stable_mir::mir::MirVisitor; use stable_mir::mir::mono::Instance; use stable_mir::target::MachineInfo; +use stable_mir::ty::{AdtDef, RigidTy, Ty, TyKind}; use stable_mir::{CrateDef, CrateItem, CrateItems, ItemKind}; use std::assert_matches::assert_matches; +use std::collections::HashSet; use std::convert::TryFrom; use std::io::Write; use std::ops::ControlFlow; @@ -67,6 +70,17 @@ fn test_stable_mir() -> ControlFlow<()> { assert!(ptr_variadic_fn_abi.c_variadic); assert_eq!(ptr_variadic_fn_abi.args.len(), 1); + let entry = stable_mir::entry_fn().unwrap(); + let main_fn = Instance::try_from(entry).unwrap(); + let mut visitor = AdtDefVisitor::default(); + visitor.visit_body(&main_fn.body().unwrap()); + let AdtDefVisitor { adt_defs } = visitor; + assert_eq!(adt_defs.len(), 1); + + // Test ADT representation options + let repr_c_struct = adt_defs.iter().find(|def| def.trimmed_name() == "ReprCStruct").unwrap(); + assert!(repr_c_struct.repr().flags.is_c); + ControlFlow::Continue(()) } @@ -138,6 +152,20 @@ fn get_item<'a>( items.iter().find(|crate_item| (item.0 == crate_item.kind()) && crate_item.name() == item.1) } +#[derive(Default)] +struct AdtDefVisitor { + adt_defs: HashSet, +} + +impl MirVisitor for AdtDefVisitor { + fn visit_ty(&mut self, ty: &Ty, _location: stable_mir::mir::visit::Location) { + if let TyKind::RigidTy(RigidTy::Adt(adt, _)) = ty.kind() { + self.adt_defs.insert(adt); + } + self.super_ty(ty) + } +} + /// This test will generate and analyze a dummy crate using the stable mir. /// For that, it will first write the dummy crate into a file. /// Then it will create a `StableMir` using custom arguments and then @@ -147,7 +175,7 @@ fn main() { generate_input(&path).unwrap(); let args = &[ "rustc".to_string(), - "--crate-type=lib".to_string(), + "-Cpanic=abort".to_string(), "--crate-name".to_string(), CRATE_NAME.to_string(), path.to_string(), @@ -185,6 +213,13 @@ fn generate_input(path: &str) -> std::io::Result<()> { // We only care about the signature. todo!() }} + + fn main() {{ + #[repr(C)] + struct ReprCStruct; + + let _s = ReprCStruct; + }} "# )?; Ok(()) diff --git a/tests/ui-fulldeps/stable-mir/closure-generic-body.rs b/tests/ui-fulldeps/stable-mir/closure-generic-body.rs new file mode 100644 index 000000000000..2a23345a9d31 --- /dev/null +++ b/tests/ui-fulldeps/stable-mir/closure-generic-body.rs @@ -0,0 +1,90 @@ +//@ run-pass +//! Tests stable mir API for retrieving the body of a closure. + +//@ ignore-stage1 +//@ ignore-cross-compile +//@ ignore-remote +//@ edition: 2021 + +#![feature(rustc_private)] +#![feature(assert_matches)] + +extern crate rustc_middle; +#[macro_use] +extern crate rustc_smir; +extern crate rustc_driver; +extern crate rustc_interface; +extern crate stable_mir; + +use std::io::Write; +use std::ops::ControlFlow; + +use stable_mir::mir::{Body, ConstOperand, Operand, TerminatorKind}; +use stable_mir::ty::{FnDef, RigidTy, TyKind}; + +const CRATE_NAME: &str = "crate_closure_body"; + +fn test_closure_body() -> ControlFlow<()> { + let crate_items = stable_mir::all_local_items(); + for item in crate_items { + let item_ty = item.ty(); + match &item_ty.kind() { + TyKind::RigidTy(RigidTy::Closure(closure_def, _)) => { + let closure_body = closure_def.body().unwrap(); + check_incr_closure_body(closure_body); + } + _ => {} + } + } + + ControlFlow::Continue(()) +} + +fn check_incr_closure_body(body: Body) { + let first_block = &body.blocks[0]; + let TerminatorKind::Call { func: Operand::Constant(ConstOperand { const_, .. }), .. } = + &first_block.terminator.kind + else { + panic!("expected Call Terminator, got: "); + }; + + let TyKind::RigidTy(RigidTy::FnDef(FnDef(def_id), ..), ..) = const_.ty().kind() else { + panic!("expected FnDef"); + }; + + assert_eq!(def_id.name(), "id"); +} + +fn main() { + let path = "closure_body.rs"; + generate_input(&path).unwrap(); + let args = &[ + "rustc".to_string(), + "-Cpanic=abort".to_string(), + "--crate-name".to_string(), + CRATE_NAME.to_string(), + path.to_string(), + ]; + run!(args, test_closure_body).unwrap(); +} + +fn generate_input(path: &str) -> std::io::Result<()> { + let mut file = std::fs::File::create(path)?; + write!( + file, + r#" + fn id(y: T) -> T {{ + y + }} + + fn main() {{ + let cl_id= |x| {{ + id(x) + }}; + + let _= cl_id(5); + }} + "# + )?; + Ok(()) +} diff --git a/tests/ui-fulldeps/stable-mir/closure_body.rs b/tests/ui-fulldeps/stable-mir/closure_body.rs new file mode 100644 index 000000000000..7ed0dabd2c3e --- /dev/null +++ b/tests/ui-fulldeps/stable-mir/closure_body.rs @@ -0,0 +1,90 @@ +//@ run-pass +//! Tests stable mir API for retrieving the body of a closure. + +//@ ignore-stage1 +//@ ignore-cross-compile +//@ ignore-remote +//@ edition: 2021 + +#![feature(rustc_private)] +#![feature(assert_matches)] + +extern crate rustc_middle; +#[macro_use] +extern crate rustc_smir; +extern crate rustc_driver; +extern crate rustc_interface; +extern crate stable_mir; + +use std::io::Write; +use std::ops::ControlFlow; + +use stable_mir::mir::{Body, ConstOperand, Operand, TerminatorKind}; +use stable_mir::ty::{FnDef, RigidTy, TyKind}; + +const CRATE_NAME: &str = "crate_closure_body"; + +fn test_closure_body() -> ControlFlow<()> { + let crate_items = stable_mir::all_local_items(); + for item in crate_items { + let item_ty = item.ty(); + match &item_ty.kind() { + TyKind::RigidTy(RigidTy::Closure(closure_def, _)) => { + let closure_body = closure_def.body().unwrap(); + check_incr_closure_body(closure_body); + } + _ => {} + } + } + + ControlFlow::Continue(()) +} + +fn check_incr_closure_body(body: Body) { + let first_block = &body.blocks[0]; + let TerminatorKind::Call { func: Operand::Constant(ConstOperand { const_, .. }), .. } = + &first_block.terminator.kind + else { + panic!("expected Call Terminator, got: "); + }; + + let TyKind::RigidTy(RigidTy::FnDef(FnDef(def_id), ..), ..) = const_.ty().kind() else { + panic!("expected FnDef"); + }; + + assert_eq!(def_id.name(), "incr"); +} + +fn main() { + let path = "closure_body.rs"; + generate_input(&path).unwrap(); + let args = &[ + "rustc".to_string(), + "-Cpanic=abort".to_string(), + "--crate-name".to_string(), + CRATE_NAME.to_string(), + path.to_string(), + ]; + run!(args, test_closure_body).unwrap(); +} + +fn generate_input(path: &str) -> std::io::Result<()> { + let mut file = std::fs::File::create(path)?; + write!( + file, + r#" + fn incr(y: i32) -> i32 {{ + y + 1 + }} + + fn main() {{ + let cl_incr = |x: i32| {{ + incr(x) + }}; + + let _= cl_incr(5); + }} + "# + )?; + Ok(()) +} diff --git a/tests/ui/abi/bad-custom.rs b/tests/ui/abi/bad-custom.rs new file mode 100644 index 000000000000..e792f0955b91 --- /dev/null +++ b/tests/ui/abi/bad-custom.rs @@ -0,0 +1,121 @@ +//@ edition: 2021 +//@ check-fail +//@ needs-asm-support +#![feature(abi_custom)] + +#[unsafe(naked)] +extern "custom" fn must_be_unsafe(a: i64) -> i64 { + //~^ ERROR functions with the `"custom"` ABI must be unsafe + //~| ERROR invalid signature for `extern "custom"` function + std::arch::naked_asm!("") +} + +#[unsafe(naked)] +unsafe extern "custom" fn no_parameters(a: i64) { + //~^ ERROR invalid signature for `extern "custom"` function + std::arch::naked_asm!("") +} + +#[unsafe(naked)] +unsafe extern "custom" fn no_return_type() -> i64 { + //~^ ERROR invalid signature for `extern "custom"` function + std::arch::naked_asm!("") +} + +unsafe extern "custom" fn double(a: i64) -> i64 { + //~^ ERROR items with the `"custom"` ABI can only be declared externally or defined via naked functions + //~| ERROR invalid signature for `extern "custom"` function + unimplemented!() +} + +struct Thing(i64); + +impl Thing { + unsafe extern "custom" fn is_even(self) -> bool { + //~^ ERROR items with the `"custom"` ABI can only be declared externally or defined via naked functions + //~| ERROR invalid signature for `extern "custom"` function + unimplemented!() + } +} + +trait BitwiseNot { + unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { + //~^ ERROR items with the `"custom"` ABI can only be declared externally or defined via naked functions + //~| ERROR invalid signature for `extern "custom"` function + unimplemented!() + } +} + +impl BitwiseNot for Thing {} + +trait Negate { + extern "custom" fn negate(a: i64) -> i64; + //~^ ERROR functions with the `"custom"` ABI must be unsafe + //~| ERROR invalid signature for `extern "custom"` function +} + +impl Negate for Thing { + extern "custom" fn negate(a: i64) -> i64 { + //~^ ERROR items with the `"custom"` ABI can only be declared externally or defined via naked functions + //~| ERROR functions with the `"custom"` ABI must be unsafe + //~| ERROR invalid signature for `extern "custom"` function + -a + } +} + +unsafe extern "custom" { + fn increment(a: i64) -> i64; + //~^ ERROR invalid signature for `extern "custom"` function + + safe fn extern_cannot_be_safe(); + //~^ ERROR foreign functions with the `"custom"` ABI cannot be safe +} + +fn caller(f: unsafe extern "custom" fn(i64) -> i64, mut x: i64) -> i64 { + unsafe { f(x) } + //~^ ERROR functions with the `"custom"` ABI cannot be called +} + +fn caller_by_ref(f: &unsafe extern "custom" fn(i64) -> i64, mut x: i64) -> i64 { + unsafe { f(x) } + //~^ ERROR functions with the `"custom"` ABI cannot be called +} + +type Custom = unsafe extern "custom" fn(i64) -> i64; + +fn caller_alias(f: Custom, mut x: i64) -> i64 { + unsafe { f(x) } + //~^ ERROR functions with the `"custom"` ABI cannot be called +} + +#[unsafe(naked)] +const unsafe extern "custom" fn no_const_fn() { + std::arch::naked_asm!("") + //~^ ERROR inline assembly is not allowed in constant functions +} + +async unsafe extern "custom" fn no_async_fn() { + //~^ ERROR items with the `"custom"` ABI can only be declared externally or defined via naked functions + //~| ERROR functions with the `"custom"` ABI cannot be `async` +} + +fn no_promotion_to_fn_trait(f: unsafe extern "custom" fn()) -> impl Fn() { + //~^ ERROR expected a `Fn()` closure, found `unsafe extern "custom" fn()` + f +} + +pub fn main() { + unsafe { + assert_eq!(double(21), 42); + //~^ ERROR functions with the `"custom"` ABI cannot be called + + assert_eq!(unsafe { increment(41) }, 42); + //~^ ERROR functions with the `"custom"` ABI cannot be called + + assert!(Thing(41).is_even()); + //~^ ERROR functions with the `"custom"` ABI cannot be called + + assert_eq!(Thing::bitwise_not(42), !42); + //~^ ERROR functions with the `"custom"` ABI cannot be called + } +} diff --git a/tests/ui/abi/bad-custom.stderr b/tests/ui/abi/bad-custom.stderr new file mode 100644 index 000000000000..ec0f11af8980 --- /dev/null +++ b/tests/ui/abi/bad-custom.stderr @@ -0,0 +1,299 @@ +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/bad-custom.rs:7:1 + | +LL | extern "custom" fn must_be_unsafe(a: i64) -> i64 { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn must_be_unsafe(a: i64) -> i64 { + | ++++++ + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:7:35 + | +LL | extern "custom" fn must_be_unsafe(a: i64) -> i64 { + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - extern "custom" fn must_be_unsafe(a: i64) -> i64 { +LL + extern "custom" fn must_be_unsafe() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:14:41 + | +LL | unsafe extern "custom" fn no_parameters(a: i64) { + | ^^^^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - unsafe extern "custom" fn no_parameters(a: i64) { +LL + unsafe extern "custom" fn no_parameters() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:20:47 + | +LL | unsafe extern "custom" fn no_return_type() -> i64 { + | ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - unsafe extern "custom" fn no_return_type() -> i64 { +LL + unsafe extern "custom" fn no_return_type() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:25:34 + | +LL | unsafe extern "custom" fn double(a: i64) -> i64 { + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - unsafe extern "custom" fn double(a: i64) -> i64 { +LL + unsafe extern "custom" fn double() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:34:39 + | +LL | unsafe extern "custom" fn is_even(self) -> bool { + | ^^^^ ^^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - unsafe extern "custom" fn is_even(self) -> bool { +LL + unsafe extern "custom" fn is_even() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:42:43 + | +LL | unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { +LL + unsafe extern "custom" fn bitwise_not() { + | + +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/bad-custom.rs:52:5 + | +LL | extern "custom" fn negate(a: i64) -> i64; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn negate(a: i64) -> i64; + | ++++++ + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:52:31 + | +LL | extern "custom" fn negate(a: i64) -> i64; + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - extern "custom" fn negate(a: i64) -> i64; +LL + extern "custom" fn negate(); + | + +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/bad-custom.rs:58:5 + | +LL | extern "custom" fn negate(a: i64) -> i64 { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn negate(a: i64) -> i64 { + | ++++++ + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:58:31 + | +LL | extern "custom" fn negate(a: i64) -> i64 { + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - extern "custom" fn negate(a: i64) -> i64 { +LL + extern "custom" fn negate() { + | + +error: invalid signature for `extern "custom"` function + --> $DIR/bad-custom.rs:67:18 + | +LL | fn increment(a: i64) -> i64; + | ^^^^^^ ^^^ + | + = note: functions with the `"custom"` ABI cannot have any parameters or return type +help: remove the parameters and return type + | +LL - fn increment(a: i64) -> i64; +LL + fn increment(); + | + +error: foreign functions with the `"custom"` ABI cannot be safe + --> $DIR/bad-custom.rs:70:5 + | +LL | safe fn extern_cannot_be_safe(); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: remove the `safe` keyword from this definition + | +LL - safe fn extern_cannot_be_safe(); +LL + fn extern_cannot_be_safe(); + | + +error: functions with the `"custom"` ABI cannot be `async` + --> $DIR/bad-custom.rs:97:1 + | +LL | async unsafe extern "custom" fn no_async_fn() { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: remove the `async` keyword from this definiton + | +LL - async unsafe extern "custom" fn no_async_fn() { +LL + unsafe extern "custom" fn no_async_fn() { + | + +error: items with the `"custom"` ABI can only be declared externally or defined via naked functions + --> $DIR/bad-custom.rs:97:1 + | +LL | async unsafe extern "custom" fn no_async_fn() { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: convert this to an `#[unsafe(naked)]` function + | +LL + #[unsafe(naked)] +LL | async unsafe extern "custom" fn no_async_fn() { + | + +error[E0277]: expected a `Fn()` closure, found `unsafe extern "custom" fn()` + --> $DIR/bad-custom.rs:102:64 + | +LL | fn no_promotion_to_fn_trait(f: unsafe extern "custom" fn()) -> impl Fn() { + | ^^^^^^^^^ call the function in a closure: `|| unsafe { /* code */ }` +LL | +LL | f + | - return type was inferred to be `unsafe extern "custom" fn()` here + | + = help: the trait `Fn()` is not implemented for `unsafe extern "custom" fn()` + = note: unsafe function cannot be called generically without an unsafe block + = note: wrap the `unsafe extern "custom" fn()` in a closure with no arguments: `|| { /* code */ }` + +error: items with the `"custom"` ABI can only be declared externally or defined via naked functions + --> $DIR/bad-custom.rs:25:1 + | +LL | unsafe extern "custom" fn double(a: i64) -> i64 { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: convert this to an `#[unsafe(naked)]` function + | +LL + #[unsafe(naked)] +LL | unsafe extern "custom" fn double(a: i64) -> i64 { + | + +error: items with the `"custom"` ABI can only be declared externally or defined via naked functions + --> $DIR/bad-custom.rs:34:5 + | +LL | unsafe extern "custom" fn is_even(self) -> bool { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: convert this to an `#[unsafe(naked)]` function + | +LL + #[unsafe(naked)] +LL | unsafe extern "custom" fn is_even(self) -> bool { + | + +error: items with the `"custom"` ABI can only be declared externally or defined via naked functions + --> $DIR/bad-custom.rs:42:5 + | +LL | unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: convert this to an `#[unsafe(naked)]` function + | +LL + #[unsafe(naked)] +LL | unsafe extern "custom" fn bitwise_not(a: i64) -> i64 { + | + +error: items with the `"custom"` ABI can only be declared externally or defined via naked functions + --> $DIR/bad-custom.rs:58:5 + | +LL | extern "custom" fn negate(a: i64) -> i64 { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: convert this to an `#[unsafe(naked)]` function + | +LL + #[unsafe(naked)] +LL | extern "custom" fn negate(a: i64) -> i64 { + | + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:75:14 + | +LL | unsafe { f(x) } + | ^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:80:14 + | +LL | unsafe { f(x) } + | ^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:87:14 + | +LL | unsafe { f(x) } + | ^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:109:20 + | +LL | assert_eq!(double(21), 42); + | ^^^^^^^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:112:29 + | +LL | assert_eq!(unsafe { increment(41) }, 42); + | ^^^^^^^^^^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:115:17 + | +LL | assert!(Thing(41).is_even()); + | ^^^^^^^^^^^^^^^^^^^ + +error: functions with the `"custom"` ABI cannot be called + --> $DIR/bad-custom.rs:118:20 + | +LL | assert_eq!(Thing::bitwise_not(42), !42); + | ^^^^^^^^^^^^^^^^^^^^^^ + +error[E0015]: inline assembly is not allowed in constant functions + --> $DIR/bad-custom.rs:93:5 + | +LL | std::arch::naked_asm!("") + | ^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to 28 previous errors + +Some errors have detailed explanations: E0015, E0277. +For more information about an error, try `rustc --explain E0015`. diff --git a/tests/ui/abi/custom.rs b/tests/ui/abi/custom.rs new file mode 100644 index 000000000000..0f6ff77f5808 --- /dev/null +++ b/tests/ui/abi/custom.rs @@ -0,0 +1,88 @@ +// Test that `extern "custom"` functions can be called from assembly, and defined using a naked +// function, and `global_asm!` with an `extern "custom"` block. +// +//@ run-pass +//@ only-x86_64 +#![feature(abi_custom)] + +use std::arch::{asm, global_asm, naked_asm}; + +#[unsafe(naked)] +unsafe extern "custom" fn double() { + naked_asm!("add rax, rax", "ret"); +} + +global_asm!( + // work around macOS prefixing symbols with _ + " .globl {0}", + "{0}:", + " add rax, 1", + " ret", + sym increment, +); + +unsafe extern "custom" { + fn increment(); +} + +#[repr(transparent)] +struct Thing(u64); + +impl Thing { + #[unsafe(naked)] + unsafe extern "custom" fn is_even() { + naked_asm!("test al, 1", "sete al", "ret"); + } +} + +trait BitwiseNot { + #[unsafe(naked)] + unsafe extern "custom" fn bitwise_not() { + naked_asm!("not rax", "ret"); + } +} + +impl BitwiseNot for Thing {} + +#[unsafe(naked)] +unsafe extern "C" fn const_generic() { + naked_asm!( + "mov rax, {}", + "ret", + const N, + ); +} + +pub fn main() { + let mut x: u64 = 21; + unsafe { asm!("call {}", sym double, inout("rax") x) }; + assert_eq!(x, 42); + + let mut x: u64 = 41; + unsafe { asm!("call {}", sym increment, inout("rax") x) }; + assert_eq!(x, 42); + + let mut x: u8; + unsafe { asm!("call {}", sym Thing::is_even, inout("al") 42u8 => x) }; + assert!(x != 0); + + let mut x: u64 = 42; + unsafe { asm!("call {}", sym Thing::bitwise_not, inout("rax") x) }; + assert_eq!(x, !42); + + // Create and call in `asm!` an `extern "custom"` function pointer. + fn caller(f: unsafe extern "custom" fn(), mut x: u64) -> u64 { + unsafe { asm!("call {}", in(reg) f, inout("rax") x) }; + x + } + + assert_eq!(caller(double, 2), 4); + + let x: u64; + unsafe { asm!("call {}", sym const_generic::<42>, out("rax") x) }; + assert_eq!(x, 42); + + let x: u64; + unsafe { asm!("call {}", sym const_generic::<84>, out("rax") x) }; + assert_eq!(x, 84); +} diff --git a/tests/ui/abi/unsupported.aarch64.stderr b/tests/ui/abi/unsupported.aarch64.stderr index ea645780b0d7..4721c26026d1 100644 --- a/tests/ui/abi/unsupported.aarch64.stderr +++ b/tests/ui/abi/unsupported.aarch64.stderr @@ -114,7 +114,7 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"stdcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:117:1 + --> $DIR/unsupported.rs:119:1 | LL | extern "stdcall" {} | ^^^^^^^^^^^^^^^^^^^ @@ -122,35 +122,36 @@ LL | extern "stdcall" {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` error[E0570]: `"stdcall-unwind"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: use `extern "C"` instead = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:136:1 + | +LL | extern "cdecl" {} + | ^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: use `extern "C"` instead + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -160,7 +161,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -169,13 +170,13 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:148:1 + --> $DIR/unsupported.rs:150:1 | LL | extern "vectorcall" {} | ^^^^^^^^^^^^^^^^^^^^^^ warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -184,7 +185,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -193,7 +194,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -255,7 +256,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -265,13 +266,13 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:1 + --> $DIR/unsupported.rs:143:1 | LL | extern "vectorcall" fn vectorcall() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -367,44 +368,9 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -415,7 +381,7 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -426,7 +392,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -435,15 +401,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/abi/unsupported.arm.stderr b/tests/ui/abi/unsupported.arm.stderr index 2c82e2951e22..ed9cd2ab2c5d 100644 --- a/tests/ui/abi/unsupported.arm.stderr +++ b/tests/ui/abi/unsupported.arm.stderr @@ -99,7 +99,7 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"stdcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:117:1 + --> $DIR/unsupported.rs:119:1 | LL | extern "stdcall" {} | ^^^^^^^^^^^^^^^^^^^ @@ -107,35 +107,36 @@ LL | extern "stdcall" {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` error[E0570]: `"stdcall-unwind"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: use `extern "C"` instead = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:136:1 + | +LL | extern "cdecl" {} + | ^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: use `extern "C"` instead + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -145,7 +146,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -154,13 +155,13 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:148:1 + --> $DIR/unsupported.rs:150:1 | LL | extern "vectorcall" {} | ^^^^^^^^^^^^^^^^^^^^^^ warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -169,7 +170,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -178,7 +179,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -234,7 +235,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -244,13 +245,13 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:1 + --> $DIR/unsupported.rs:143:1 | LL | extern "vectorcall" fn vectorcall() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -335,44 +336,9 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -383,7 +349,7 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -394,7 +360,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -403,15 +369,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/abi/unsupported.i686.stderr b/tests/ui/abi/unsupported.i686.stderr index d552f9a132cf..4d903b435d87 100644 --- a/tests/ui/abi/unsupported.i686.stderr +++ b/tests/ui/abi/unsupported.i686.stderr @@ -75,7 +75,7 @@ LL | extern "riscv-interrupt-m" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -84,7 +84,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -93,7 +93,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -135,7 +135,7 @@ LL | extern "riscv-interrupt-m" fn riscv() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -200,7 +200,7 @@ LL | fn riscv_ptr(f: extern "riscv-interrupt-m" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -211,7 +211,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/tests/ui/abi/unsupported.riscv32.stderr b/tests/ui/abi/unsupported.riscv32.stderr index a0e2901c759f..9e75dfafca0f 100644 --- a/tests/ui/abi/unsupported.riscv32.stderr +++ b/tests/ui/abi/unsupported.riscv32.stderr @@ -99,7 +99,7 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"stdcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:117:1 + --> $DIR/unsupported.rs:119:1 | LL | extern "stdcall" {} | ^^^^^^^^^^^^^^^^^^^ @@ -107,35 +107,36 @@ LL | extern "stdcall" {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` error[E0570]: `"stdcall-unwind"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: use `extern "C"` instead = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:136:1 + | +LL | extern "cdecl" {} + | ^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: use `extern "C"` instead + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -145,7 +146,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -154,13 +155,13 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:148:1 + --> $DIR/unsupported.rs:150:1 | LL | extern "vectorcall" {} | ^^^^^^^^^^^^^^^^^^^^^^ warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -169,7 +170,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -178,7 +179,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -234,7 +235,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -244,13 +245,13 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:1 + --> $DIR/unsupported.rs:143:1 | LL | extern "vectorcall" fn vectorcall() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -335,44 +336,9 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -383,7 +349,7 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -394,7 +360,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -403,15 +369,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/abi/unsupported.riscv64.stderr b/tests/ui/abi/unsupported.riscv64.stderr index a0e2901c759f..9e75dfafca0f 100644 --- a/tests/ui/abi/unsupported.riscv64.stderr +++ b/tests/ui/abi/unsupported.riscv64.stderr @@ -99,7 +99,7 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"stdcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:117:1 + --> $DIR/unsupported.rs:119:1 | LL | extern "stdcall" {} | ^^^^^^^^^^^^^^^^^^^ @@ -107,35 +107,36 @@ LL | extern "stdcall" {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` error[E0570]: `"stdcall-unwind"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: use `extern "C"` instead = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:136:1 + | +LL | extern "cdecl" {} + | ^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: use `extern "C"` instead + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -145,7 +146,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -154,13 +155,13 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:148:1 + --> $DIR/unsupported.rs:150:1 | LL | extern "vectorcall" {} | ^^^^^^^^^^^^^^^^^^^^^^ warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -169,7 +170,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -178,7 +179,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -234,7 +235,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -244,13 +245,13 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"vectorcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:141:1 + --> $DIR/unsupported.rs:143:1 | LL | extern "vectorcall" fn vectorcall() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -335,44 +336,9 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "vectorcall" is not supported on this target - --> $DIR/unsupported.rs:143:22 + --> $DIR/unsupported.rs:145:22 | LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -383,7 +349,7 @@ LL | fn vectorcall_ptr(f: extern "vectorcall" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -394,7 +360,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -403,15 +369,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/abi/unsupported.rs b/tests/ui/abi/unsupported.rs index 9ea22ca516b4..43bdfe3ea240 100644 --- a/tests/ui/abi/unsupported.rs +++ b/tests/ui/abi/unsupported.rs @@ -110,8 +110,10 @@ extern "stdcall" fn stdcall() {} //[x64_win]~^^ WARN unsupported_calling_conventions //[x64_win]~^^^ WARN this was previously accepted fn stdcall_ptr(f: extern "stdcall" fn()) { - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ WARN unsupported_fn_ptr_calling_conventions - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^^ WARN this was previously accepted + //[x64_win]~^ WARN unsupported_calling_conventions + //[x64_win]~| WARN this was previously accepted + //[x64,arm,aarch64,riscv32,riscv64]~^^^ WARN unsupported_fn_ptr_calling_conventions + //[x64,arm,aarch64,riscv32,riscv64]~| WARN this was previously accepted f() } extern "stdcall" {} @@ -127,7 +129,7 @@ extern "cdecl" fn cdecl() {} //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ WARN unsupported_calling_conventions //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^^ WARN this was previously accepted fn cdecl_ptr(f: extern "cdecl" fn()) { - //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ WARN unsupported_fn_ptr_calling_conventions + //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^ WARN unsupported_calling_conventions //[x64,x64_win,arm,aarch64,riscv32,riscv64]~^^ WARN this was previously accepted f() } diff --git a/tests/ui/abi/unsupported.x64.stderr b/tests/ui/abi/unsupported.x64.stderr index 732a5f84f50e..5b55e5707fad 100644 --- a/tests/ui/abi/unsupported.x64.stderr +++ b/tests/ui/abi/unsupported.x64.stderr @@ -99,7 +99,7 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 error[E0570]: `"stdcall"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:117:1 + --> $DIR/unsupported.rs:119:1 | LL | extern "stdcall" {} | ^^^^^^^^^^^^^^^^^^^ @@ -107,35 +107,36 @@ LL | extern "stdcall" {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` error[E0570]: `"stdcall-unwind"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: use `extern "C"` instead = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:136:1 + | +LL | extern "cdecl" {} + | ^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: use `extern "C"` instead + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -145,7 +146,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -154,7 +155,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -163,7 +164,7 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -219,7 +220,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -229,7 +230,7 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -314,44 +315,9 @@ LL | fn stdcall_ptr(f: extern "stdcall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -362,7 +328,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -371,15 +337,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/abi/unsupported.x64_win.stderr b/tests/ui/abi/unsupported.x64_win.stderr index 5597440d5d91..93b5a272e926 100644 --- a/tests/ui/abi/unsupported.x64_win.stderr +++ b/tests/ui/abi/unsupported.x64_win.stderr @@ -89,28 +89,29 @@ error[E0570]: `"thiscall"` is not a supported ABI for the current target LL | extern "thiscall" {} | ^^^^^^^^^^^^^^^^^^^^ -warning: the calling convention "stdcall" is not supported on this target +warning: use of calling convention not supported on this target --> $DIR/unsupported.rs:112:19 | LL | fn stdcall_ptr(f: extern "stdcall" fn()) { | ^^^^^^^^^^^^^^^^^^^^^ | = 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 #130260 - -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:117:1 - | -LL | extern "stdcall" {} - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` = note: `#[warn(unsupported_calling_conventions)]` on by default warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:121:1 + --> $DIR/unsupported.rs:119:1 + | +LL | extern "stdcall" {} + | ^^^^^^^^^^^^^^^^^^^ + | + = 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 #137018 + = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` + +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:123:1 | LL | extern "stdcall-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -119,17 +120,18 @@ LL | extern "stdcall-unwind" {} = note: for more information, see issue #137018 = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 +warning: use of calling convention not supported on this target + --> $DIR/unsupported.rs:131:17 | LL | fn cdecl_ptr(f: extern "cdecl" fn()) { | ^^^^^^^^^^^^^^^^^^^ | = 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 #130260 + = note: for more information, see issue #137018 + = help: use `extern "C"` instead warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 + --> $DIR/unsupported.rs:136:1 | LL | extern "cdecl" {} | ^^^^^^^^^^^^^^^^^ @@ -139,7 +141,7 @@ LL | extern "cdecl" {} = help: use `extern "C"` instead warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 + --> $DIR/unsupported.rs:139:1 | LL | extern "cdecl-unwind" {} | ^^^^^^^^^^^^^^^^^^^^^^^^ @@ -149,7 +151,7 @@ LL | extern "cdecl-unwind" {} = help: use `extern "C-unwind"` instead warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -158,7 +160,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { = note: for more information, see issue #130260 warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -167,13 +169,13 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:164:1 + --> $DIR/unsupported.rs:166:1 | LL | extern "C-cmse-nonsecure-entry" {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:169:1 + --> $DIR/unsupported.rs:171:1 | LL | extern "cdecl" {} | ^^^^^^^^^^^^^^^^^ @@ -235,7 +237,7 @@ LL | extern "stdcall" fn stdcall() {} = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 + --> $DIR/unsupported.rs:128:1 | LL | extern "cdecl" fn cdecl() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -245,7 +247,7 @@ LL | extern "cdecl" fn cdecl() {} = help: use `extern "C"` instead error[E0570]: `"C-cmse-nonsecure-entry"` is not a supported ABI for the current target - --> $DIR/unsupported.rs:157:1 + --> $DIR/unsupported.rs:159:1 | LL | extern "C-cmse-nonsecure-entry" fn cmse_entry() {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -319,79 +321,9 @@ LL | fn thiscall_ptr(f: extern "thiscall" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: the calling convention "stdcall" is not supported on this target - --> $DIR/unsupported.rs:112:19 - | -LL | fn stdcall_ptr(f: extern "stdcall" fn()) { - | ^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:117:1 - | -LL | extern "stdcall" {} - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:121:1 - | -LL | extern "stdcall-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: if you need `extern "stdcall-unwind"` on win32 and `extern "C-unwind"` everywhere else, use `extern "system-unwind"` - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: the calling convention "cdecl" is not supported on this target - --> $DIR/unsupported.rs:129:17 - | -LL | fn cdecl_ptr(f: extern "cdecl" fn()) { - | ^^^^^^^^^^^^^^^^^^^ - | - = 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 #130260 - = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:134:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:137:1 - | -LL | extern "cdecl-unwind" {} - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C-unwind"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-call" is not supported on this target - --> $DIR/unsupported.rs:151:21 + --> $DIR/unsupported.rs:153:21 | LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -402,7 +334,7 @@ LL | fn cmse_call_ptr(f: extern "C-cmse-nonsecure-call" fn()) { Future breakage diagnostic: warning: the calling convention "C-cmse-nonsecure-entry" is not supported on this target - --> $DIR/unsupported.rs:159:22 + --> $DIR/unsupported.rs:161:22 | LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -411,39 +343,3 @@ LL | fn cmse_entry_ptr(f: extern "C-cmse-nonsecure-entry" fn()) { = note: for more information, see issue #130260 = note: `#[warn(unsupported_fn_ptr_calling_conventions)]` on by default -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:169:1 - | -LL | extern "cdecl" {} - | ^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:108:1 - | -LL | extern "stdcall" fn stdcall() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` - = note: `#[warn(unsupported_calling_conventions)]` on by default - -Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported.rs:126:1 - | -LL | extern "cdecl" fn cdecl() {} - | ^^^^^^^^^^^^^^^^^^^^^^^^^ - | - = 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 #137018 - = help: use `extern "C"` instead - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/async-await/async-block-control-flow-static-semantics.stderr b/tests/ui/async-await/async-block-control-flow-static-semantics.stderr index 4ed15a942c67..b64690bae6cd 100644 --- a/tests/ui/async-await/async-block-control-flow-static-semantics.stderr +++ b/tests/ui/async-await/async-block-control-flow-static-semantics.stderr @@ -1,19 +1,3 @@ -error[E0267]: `break` inside `async` block - --> $DIR/async-block-control-flow-static-semantics.rs:32:9 - | -LL | async { - | ----- enclosing `async` block -LL | break 0u8; - | ^^^^^^^^^ cannot `break` inside `async` block - -error[E0267]: `break` inside `async` block - --> $DIR/async-block-control-flow-static-semantics.rs:39:13 - | -LL | async { - | ----- enclosing `async` block -LL | break 0u8; - | ^^^^^^^^^ cannot `break` inside `async` block - error[E0308]: mismatched types --> $DIR/async-block-control-flow-static-semantics.rs:21:58 | @@ -50,6 +34,22 @@ LL | let _: &dyn Future = █ | = note: required for the cast from `&{async block@$DIR/async-block-control-flow-static-semantics.rs:14:17: 14:22}` to `&dyn Future` +error[E0267]: `break` inside `async` block + --> $DIR/async-block-control-flow-static-semantics.rs:32:9 + | +LL | async { + | ----- enclosing `async` block +LL | break 0u8; + | ^^^^^^^^^ cannot `break` inside `async` block + +error[E0267]: `break` inside `async` block + --> $DIR/async-block-control-flow-static-semantics.rs:39:13 + | +LL | async { + | ----- enclosing `async` block +LL | break 0u8; + | ^^^^^^^^^ cannot `break` inside `async` block + error[E0308]: mismatched types --> $DIR/async-block-control-flow-static-semantics.rs:49:44 | diff --git a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr index 329cec6dad3a..b7259074bf64 100644 --- a/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr +++ b/tests/ui/async-await/async-closures/without-precise-captures-we-are-powerless.stderr @@ -106,11 +106,13 @@ LL | } error[E0621]: explicit lifetime required in the type of `x` --> $DIR/without-precise-captures-we-are-powerless.rs:38:5 | -LL | fn through_field_and_ref<'a>(x: &S<'a>) { - | ------ help: add explicit lifetime `'a` to the type of `x`: `&'a S<'a>` -... LL | outlives::<'a>(call_once(c)); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn through_field_and_ref<'a>(x: &'a S<'a>) { + | ++ error[E0597]: `c` does not live long enough --> $DIR/without-precise-captures-we-are-powerless.rs:43:20 @@ -131,11 +133,13 @@ LL | } error[E0621]: explicit lifetime required in the type of `x` --> $DIR/without-precise-captures-we-are-powerless.rs:44:5 | -LL | fn through_field_and_ref_move<'a>(x: &S<'a>) { - | ------ help: add explicit lifetime `'a` to the type of `x`: `&'a S<'a>` -... LL | outlives::<'a>(call_once(c)); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn through_field_and_ref_move<'a>(x: &'a S<'a>) { + | ++ error: aborting due to 10 previous errors diff --git a/tests/ui/async-await/issues/issue-63388-1.stderr b/tests/ui/async-await/issues/issue-63388-1.stderr index 277f7fa6f63e..a59fe7dbc20e 100644 --- a/tests/ui/async-await/issues/issue-63388-1.stderr +++ b/tests/ui/async-await/issues/issue-63388-1.stderr @@ -1,11 +1,14 @@ error[E0621]: explicit lifetime required in the type of `foo` --> $DIR/issue-63388-1.rs:14:9 | -LL | &'a self, foo: &dyn Foo - | -------- help: add explicit lifetime `'a` to the type of `foo`: `&'a (dyn Foo + 'a)` -... LL | foo | ^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `foo` + | +LL - &'a self, foo: &dyn Foo +LL + &'a self, foo: &'a (dyn Foo + 'a) + | error: aborting due to 1 previous error diff --git a/tests/ui/auxiliary/typeid-intrinsic-aux1.rs b/tests/ui/auxiliary/typeid-intrinsic-aux1.rs index 281c079682fd..a028008c6ae4 100644 --- a/tests/ui/auxiliary/typeid-intrinsic-aux1.rs +++ b/tests/ui/auxiliary/typeid-intrinsic-aux1.rs @@ -9,9 +9,9 @@ pub struct E(Result<&'static str, isize>); pub type F = Option; pub type G = usize; pub type H = &'static str; -pub type I = Box; -pub type I32Iterator = Iterator; -pub type U32Iterator = Iterator; +pub type I = Box; +pub type I32Iterator = dyn Iterator; +pub type U32Iterator = dyn Iterator; pub fn id_A() -> TypeId { TypeId::of::() } pub fn id_B() -> TypeId { TypeId::of::() } diff --git a/tests/ui/auxiliary/typeid-intrinsic-aux2.rs b/tests/ui/auxiliary/typeid-intrinsic-aux2.rs index 281c079682fd..a028008c6ae4 100644 --- a/tests/ui/auxiliary/typeid-intrinsic-aux2.rs +++ b/tests/ui/auxiliary/typeid-intrinsic-aux2.rs @@ -9,9 +9,9 @@ pub struct E(Result<&'static str, isize>); pub type F = Option; pub type G = usize; pub type H = &'static str; -pub type I = Box; -pub type I32Iterator = Iterator; -pub type U32Iterator = Iterator; +pub type I = Box; +pub type I32Iterator = dyn Iterator; +pub type U32Iterator = dyn Iterator; pub fn id_A() -> TypeId { TypeId::of::() } pub fn id_B() -> TypeId { TypeId::of::() } diff --git a/tests/ui/box/empty-alloc-deref-rvalue.rs b/tests/ui/box/empty-alloc-deref-rvalue.rs new file mode 100644 index 000000000000..507a753467ac --- /dev/null +++ b/tests/ui/box/empty-alloc-deref-rvalue.rs @@ -0,0 +1,10 @@ +//! Smoke test: dereferencing boxed zero-sized types (ZSTs) should not crash. +//! +//! Originally a regression test of github.com/rust-lang/rust/issues/13360 +//! but repurposed for a smoke test. + +//@ run-pass + +pub fn main() { + let _: () = *Box::new(()); +} diff --git a/tests/ui/filter-block-view-items.rs b/tests/ui/cfg/cfg-false-use-item.rs similarity index 72% rename from tests/ui/filter-block-view-items.rs rename to tests/ui/cfg/cfg-false-use-item.rs index cb599c272647..d37b48cdedb7 100644 --- a/tests/ui/filter-block-view-items.rs +++ b/tests/ui/cfg/cfg-false-use-item.rs @@ -1,3 +1,5 @@ +//! Test that use items with cfg(false) are properly filtered out + //@ run-pass pub fn main() { diff --git a/tests/ui/check-cfg/hrtb-crash.rs b/tests/ui/check-cfg/hrtb-crash.rs new file mode 100644 index 000000000000..f2bce33f9f9a --- /dev/null +++ b/tests/ui/check-cfg/hrtb-crash.rs @@ -0,0 +1,7 @@ +// https://github.com/rust-lang/rust/issues/139825 +//@ compile-flags: --check-cfg=cfg(docsrs,test) --crate-type lib +//@ check-pass +struct A +where + for<#[cfg(b)] c> u8:; +//~^ WARN: unexpected `cfg` condition name diff --git a/tests/ui/check-cfg/hrtb-crash.stderr b/tests/ui/check-cfg/hrtb-crash.stderr new file mode 100644 index 000000000000..431cf9cf53e2 --- /dev/null +++ b/tests/ui/check-cfg/hrtb-crash.stderr @@ -0,0 +1,13 @@ +warning: unexpected `cfg` condition name: `b` + --> $DIR/hrtb-crash.rs:6:15 + | +LL | for<#[cfg(b)] c> u8:; + | ^ help: found config with similar value: `target_feature = "b"` + | + = help: expected names are: `FALSE`, `docsrs`, and `test` and 31 more + = help: to expect this configuration use `--check-cfg=cfg(b)` + = note: see for more information about checking conditional configuration + = note: `#[warn(unexpected_cfgs)]` on by default + +warning: 1 warning emitted + diff --git a/tests/ui/check-cfg/target_feature.stderr b/tests/ui/check-cfg/target_feature.stderr index ec81ba2e3d89..f29a41d6a8e2 100644 --- a/tests/ui/check-cfg/target_feature.stderr +++ b/tests/ui/check-cfg/target_feature.stderr @@ -212,6 +212,9 @@ LL | cfg!(target_feature = "_UNEXPECTED_VALUE"); `relax` `relaxed-simd` `reserve-x18` +`retpoline-external-thunk` +`retpoline-indirect-branches` +`retpoline-indirect-calls` `rtm` `sb` `scq` diff --git a/tests/ui/const-generics/const-arg-in-const-arg.min.stderr b/tests/ui/const-generics/const-arg-in-const-arg.min.stderr index 16512cb69e23..ebb3e821e07b 100644 --- a/tests/ui/const-generics/const-arg-in-const-arg.min.stderr +++ b/tests/ui/const-generics/const-arg-in-const-arg.min.stderr @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | let _: [u8; bar::()]; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -58,7 +58,7 @@ error: generic parameters may not be used in const operations LL | let _ = [0; bar::()]; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -112,7 +112,7 @@ error: generic parameters may not be used in const operations LL | let _: Foo<{ bar::() }>; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -166,7 +166,7 @@ error: generic parameters may not be used in const operations LL | let _ = Foo::<{ bar::() }>; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations diff --git a/tests/ui/const-generics/defaults/complex-generic-default-expr.min.stderr b/tests/ui/const-generics/defaults/complex-generic-default-expr.min.stderr index 199546c0883f..e41e488371a8 100644 --- a/tests/ui/const-generics/defaults/complex-generic-default-expr.min.stderr +++ b/tests/ui/const-generics/defaults/complex-generic-default-expr.min.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | struct Foo; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations diff --git a/tests/ui/const-generics/early/const_arg_trivial_macro_expansion-4.stderr b/tests/ui/const-generics/early/const_arg_trivial_macro_expansion-4.stderr index 4722968b2034..a1aee041b1fc 100644 --- a/tests/ui/const-generics/early/const_arg_trivial_macro_expansion-4.stderr +++ b/tests/ui/const-generics/early/const_arg_trivial_macro_expansion-4.stderr @@ -7,7 +7,7 @@ LL | N LL | fn foo() -> Foo<{ arg!{} arg!{} }> { loop {} } | ------ in this macro invocation | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions = note: this error originates in the macro `arg` (in Nightly builds, run with -Z macro-backtrace for more info) @@ -20,7 +20,7 @@ LL | N LL | fn foo() -> Foo<{ arg!{} arg!{} }> { loop {} } | ------ in this macro invocation | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions = note: this error originates in the macro `arg` (in Nightly builds, run with -Z macro-backtrace for more info) @@ -30,7 +30,7 @@ error: generic parameters may not be used in const operations LL | fn bar() -> [(); { empty!{}; N }] { loop {} } | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 3 previous errors diff --git a/tests/ui/const-generics/early/macro_rules-braces.stderr b/tests/ui/const-generics/early/macro_rules-braces.stderr index 326950668010..30efa18982be 100644 --- a/tests/ui/const-generics/early/macro_rules-braces.stderr +++ b/tests/ui/const-generics/early/macro_rules-braces.stderr @@ -26,7 +26,7 @@ error: generic parameters may not be used in const operations LL | let _: foo!({{ N }}); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -35,7 +35,7 @@ error: generic parameters may not be used in const operations LL | let _: bar!({ N }); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -44,7 +44,7 @@ error: generic parameters may not be used in const operations LL | let _: baz!({{ N }}); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -53,7 +53,7 @@ error: generic parameters may not be used in const operations LL | let _: biz!({ N }); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 6 previous errors diff --git a/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces-2.stderr b/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces-2.stderr index e40d05924b11..d68715b4d8b7 100644 --- a/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces-2.stderr +++ b/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces-2.stderr @@ -7,7 +7,7 @@ LL | N LL | fn foo() -> A<{{ y!() }}> { | ---- in this macro invocation | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions = note: this error originates in the macro `y` (in Nightly builds, run with -Z macro-backtrace for more info) diff --git a/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces.stderr b/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces.stderr index b91d6c7a024a..1171b359f170 100644 --- a/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces.stderr +++ b/tests/ui/const-generics/early/trivial-const-arg-macro-nested-braces.stderr @@ -7,7 +7,7 @@ LL | { N } LL | fn foo() -> A<{ y!() }> { | ---- in this macro invocation | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions = note: this error originates in the macro `y` (in Nightly builds, run with -Z macro-backtrace for more info) diff --git a/tests/ui/const-generics/early/trivial-const-arg-nested-braces.stderr b/tests/ui/const-generics/early/trivial-const-arg-nested-braces.stderr index d60516ba4bcd..b812e3333d9c 100644 --- a/tests/ui/const-generics/early/trivial-const-arg-nested-braces.stderr +++ b/tests/ui/const-generics/early/trivial-const-arg-nested-braces.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | fn foo() -> A<{ { N } }> { | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 1 previous error diff --git a/tests/ui/const-generics/generic_const_exprs/array-size-in-generic-struct-param.min.stderr b/tests/ui/const-generics/generic_const_exprs/array-size-in-generic-struct-param.min.stderr index a8b6f06ab1c2..1f93c4f89098 100644 --- a/tests/ui/const-generics/generic_const_exprs/array-size-in-generic-struct-param.min.stderr +++ b/tests/ui/const-generics/generic_const_exprs/array-size-in-generic-struct-param.min.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | struct ArithArrayLen([u32; 0 + N]); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | arr: [u8; CFG.arr_size], | ^^^ cannot perform const operation using `CFG` | - = help: const parameters may only be used as standalone arguments, i.e. `CFG` + = help: const parameters may only be used as standalone arguments here, i.e. `CFG` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: `Config` is forbidden as the type of a const generic parameter diff --git a/tests/ui/const-generics/generic_const_exprs/bad-multiply.stderr b/tests/ui/const-generics/generic_const_exprs/bad-multiply.stderr index a8d6cebabe71..7719831e20cd 100644 --- a/tests/ui/const-generics/generic_const_exprs/bad-multiply.stderr +++ b/tests/ui/const-generics/generic_const_exprs/bad-multiply.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | SmallVec<{ D * 2 }>:, | ^ cannot perform const operation using `D` | - = help: const parameters may only be used as standalone arguments, i.e. `D` + = help: const parameters may only be used as standalone arguments here, i.e. `D` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error[E0747]: constant provided when a type was expected diff --git a/tests/ui/const-generics/generic_const_exprs/feature-gate-generic_const_exprs.stderr b/tests/ui/const-generics/generic_const_exprs/feature-gate-generic_const_exprs.stderr index 9c4e3d8583c0..3208bbbd86b8 100644 --- a/tests/ui/const-generics/generic_const_exprs/feature-gate-generic_const_exprs.stderr +++ b/tests/ui/const-generics/generic_const_exprs/feature-gate-generic_const_exprs.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | type Arr = [u8; N - 1]; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 1 previous error diff --git a/tests/ui/const-generics/generic_const_exprs/issue-72787.min.stderr b/tests/ui/const-generics/generic_const_exprs/issue-72787.min.stderr index 2454b3119213..cccf6dc6ae01 100644 --- a/tests/ui/const-generics/generic_const_exprs/issue-72787.min.stderr +++ b/tests/ui/const-generics/generic_const_exprs/issue-72787.min.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | Condition<{ LHS <= RHS }>: True | ^^^ cannot perform const operation using `LHS` | - = help: const parameters may only be used as standalone arguments, i.e. `LHS` + = help: const parameters may only be used as standalone arguments here, i.e. `LHS` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | Condition<{ LHS <= RHS }>: True | ^^^ cannot perform const operation using `RHS` | - = help: const parameters may only be used as standalone arguments, i.e. `RHS` + = help: const parameters may only be used as standalone arguments here, i.e. `RHS` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -22,7 +22,7 @@ error: generic parameters may not be used in const operations LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True, | ^ cannot perform const operation using `I` | - = help: const parameters may only be used as standalone arguments, i.e. `I` + = help: const parameters may only be used as standalone arguments here, i.e. `I` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -31,7 +31,7 @@ error: generic parameters may not be used in const operations LL | IsLessOrEqual<{ 8 - I }, { 8 - J }>: True, | ^ cannot perform const operation using `J` | - = help: const parameters may only be used as standalone arguments, i.e. `J` + = help: const parameters may only be used as standalone arguments here, i.e. `J` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 4 previous errors diff --git a/tests/ui/const-generics/generic_const_exprs/issue-72819-generic-in-const-eval.min.stderr b/tests/ui/const-generics/generic_const_exprs/issue-72819-generic-in-const-eval.min.stderr index c504464127af..f91a2a302869 100644 --- a/tests/ui/const-generics/generic_const_exprs/issue-72819-generic-in-const-eval.min.stderr +++ b/tests/ui/const-generics/generic_const_exprs/issue-72819-generic-in-const-eval.min.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | where Assert::<{N < usize::MAX / 2}>: IsTrue, | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 1 previous error diff --git a/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.full.stderr b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.full.stderr new file mode 100644 index 000000000000..586ac63016c8 --- /dev/null +++ b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.full.stderr @@ -0,0 +1,13 @@ +error: unconstrained generic constant + --> $DIR/trivial-anon-const-use-cases.rs:14:12 + | +LL | stuff: [u8; { S + 1 }], // `S + 1` is NOT a valid const expression in this context. + | ^^^^^^^^^^^^^^^ + | +help: try adding a `where` bound + | +LL | struct Y where [(); { S + 1 }]: { + | ++++++++++++++++++++++ + +error: aborting due to 1 previous error + diff --git a/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.min.stderr b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.min.stderr new file mode 100644 index 000000000000..6a868e95c895 --- /dev/null +++ b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.min.stderr @@ -0,0 +1,11 @@ +error: generic parameters may not be used in const operations + --> $DIR/trivial-anon-const-use-cases.rs:14:19 + | +LL | stuff: [u8; { S + 1 }], // `S + 1` is NOT a valid const expression in this context. + | ^ cannot perform const operation using `S` + | + = help: const parameters may only be used as standalone arguments here, i.e. `S` + = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions + +error: aborting due to 1 previous error + diff --git a/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.rs b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.rs new file mode 100644 index 000000000000..b1fd4cbc6611 --- /dev/null +++ b/tests/ui/const-generics/generic_const_exprs/trivial-anon-const-use-cases.rs @@ -0,0 +1,19 @@ +//! Regression test for . + +//@ revisions: full min +#![cfg_attr(full, feature(generic_const_exprs))] +#![cfg_attr(full, allow(incomplete_features))] + +struct X; + +impl X { + const LEN: usize = S + 1; // `S + 1` is a valid const expression in this context. +} + +struct Y { + stuff: [u8; { S + 1 }], // `S + 1` is NOT a valid const expression in this context. + //[min]~^ ERROR generic parameters may not be used in const operations + //[full]~^^ ERROR unconstrained generic constant +} + +fn main() {} diff --git a/tests/ui/const-generics/issues/issue-68366.min.stderr b/tests/ui/const-generics/issues/issue-68366.min.stderr index 10b5a06682f5..4d721e958cbc 100644 --- a/tests/ui/const-generics/issues/issue-68366.min.stderr +++ b/tests/ui/const-generics/issues/issue-68366.min.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | impl Collatz<{Some(N)}> {} | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: `Option` is forbidden as the type of a const generic parameter diff --git a/tests/ui/const-generics/issues/issue-76701-ty-param-in-const.stderr b/tests/ui/const-generics/issues/issue-76701-ty-param-in-const.stderr index da2fbc52a6ca..e58c894a2703 100644 --- a/tests/ui/const-generics/issues/issue-76701-ty-param-in-const.stderr +++ b/tests/ui/const-generics/issues/issue-76701-ty-param-in-const.stderr @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | fn const_param() -> [u8; N + 1] { | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 2 previous errors diff --git a/tests/ui/const-generics/issues/issue-80375.stderr b/tests/ui/const-generics/issues/issue-80375.stderr index 015196f86053..9a15e0380a19 100644 --- a/tests/ui/const-generics/issues/issue-80375.stderr +++ b/tests/ui/const-generics/issues/issue-80375.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | struct MyArray([u8; COUNT + 1]); | ^^^^^ cannot perform const operation using `COUNT` | - = help: const parameters may only be used as standalone arguments, i.e. `COUNT` + = help: const parameters may only be used as standalone arguments here, i.e. `COUNT` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 1 previous error diff --git a/tests/ui/const-generics/legacy-const-generics-bad.stderr b/tests/ui/const-generics/legacy-const-generics-bad.stderr index 3a5fa417075a..a8681d620530 100644 --- a/tests/ui/const-generics/legacy-const-generics-bad.stderr +++ b/tests/ui/const-generics/legacy-const-generics-bad.stderr @@ -16,7 +16,7 @@ error: generic parameters may not be used in const operations LL | legacy_const_generics::foo(0, N + 1, 2); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 2 previous errors diff --git a/tests/ui/const-generics/min_const_generics/complex-expression.stderr b/tests/ui/const-generics/min_const_generics/complex-expression.stderr index 3affdcf9b03e..35039bb41090 100644 --- a/tests/ui/const-generics/min_const_generics/complex-expression.stderr +++ b/tests/ui/const-generics/min_const_generics/complex-expression.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | struct Break0([u8; { N + 1 }]); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | struct Break1([u8; { { N } }]); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -22,7 +22,7 @@ error: generic parameters may not be used in const operations LL | let _: [u8; N + 1]; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -31,7 +31,7 @@ error: generic parameters may not be used in const operations LL | let _ = [0; N + 1]; | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations diff --git a/tests/ui/const-generics/repeat_expr_hack_gives_right_generics.stderr b/tests/ui/const-generics/repeat_expr_hack_gives_right_generics.stderr index ead6c621d60b..fe32fbcc87d5 100644 --- a/tests/ui/const-generics/repeat_expr_hack_gives_right_generics.stderr +++ b/tests/ui/const-generics/repeat_expr_hack_gives_right_generics.stderr @@ -4,7 +4,7 @@ error: generic parameters may not be used in const operations LL | bar::<{ [1; N] }>(); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: generic parameters may not be used in const operations @@ -13,7 +13,7 @@ error: generic parameters may not be used in const operations LL | bar::<{ [1; { N + 1 }] }>(); | ^ cannot perform const operation using `N` | - = help: const parameters may only be used as standalone arguments, i.e. `N` + = help: const parameters may only be used as standalone arguments here, i.e. `N` = help: add `#![feature(generic_const_exprs)]` to allow generic const expressions error: aborting due to 2 previous errors diff --git a/tests/ui/consts/auxiliary/unstable_intrinsic.rs b/tests/ui/consts/auxiliary/unstable_intrinsic.rs index 45631df78591..c1c7571e0c90 100644 --- a/tests/ui/consts/auxiliary/unstable_intrinsic.rs +++ b/tests/ui/consts/auxiliary/unstable_intrinsic.rs @@ -8,4 +8,4 @@ pub const unsafe fn size_of_val(x: *const T) -> usize; #[unstable(feature = "unstable", issue = "42")] #[rustc_const_unstable(feature = "unstable", issue = "42")] #[rustc_intrinsic] -pub const unsafe fn min_align_of_val(x: *const T) -> usize; +pub const unsafe fn align_of_val(x: *const T) -> usize; diff --git a/tests/ui/consts/const-adt-align-mismatch.rs b/tests/ui/consts/const-adt-align-mismatch.rs index 8faddbff30da..6ff74ad3a9ce 100644 --- a/tests/ui/consts/const-adt-align-mismatch.rs +++ b/tests/ui/consts/const-adt-align-mismatch.rs @@ -18,5 +18,5 @@ static FOO: Foo = Foo::C; fn main() { assert_eq!(FOO, Foo::C); assert_eq!(mem::size_of::(), 12); - assert_eq!(mem::min_align_of::(), 4); + assert_eq!(mem::align_of::(), 4); } diff --git a/tests/ui/consts/const-size_of_val-align_of_val-extern-type.rs b/tests/ui/consts/const-size_of_val-align_of_val-extern-type.rs index 14cdf6bb7c66..423ff37baef8 100644 --- a/tests/ui/consts/const-size_of_val-align_of_val-extern-type.rs +++ b/tests/ui/consts/const-size_of_val-align_of_val-extern-type.rs @@ -1,13 +1,13 @@ #![feature(extern_types)] #![feature(core_intrinsics)] -use std::intrinsics::{min_align_of_val, size_of_val}; +use std::intrinsics::{align_of_val, size_of_val}; extern "C" { type Opaque; } const _SIZE: usize = unsafe { size_of_val(&4 as *const i32 as *const Opaque) }; //~ ERROR layout -const _ALIGN: usize = unsafe { min_align_of_val(&4 as *const i32 as *const Opaque) }; //~ ERROR layout +const _ALIGN: usize = unsafe { align_of_val(&4 as *const i32 as *const Opaque) }; //~ ERROR layout fn main() {} diff --git a/tests/ui/consts/const-size_of_val-align_of_val-extern-type.stderr b/tests/ui/consts/const-size_of_val-align_of_val-extern-type.stderr index 64b7a4129e07..c78626bdefc5 100644 --- a/tests/ui/consts/const-size_of_val-align_of_val-extern-type.stderr +++ b/tests/ui/consts/const-size_of_val-align_of_val-extern-type.stderr @@ -7,8 +7,8 @@ LL | const _SIZE: usize = unsafe { size_of_val(&4 as *const i32 as *const Opaque error[E0080]: `extern type` does not have known layout --> $DIR/const-size_of_val-align_of_val-extern-type.rs:11:32 | -LL | const _ALIGN: usize = unsafe { min_align_of_val(&4 as *const i32 as *const Opaque) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ evaluation of `_ALIGN` failed here +LL | const _ALIGN: usize = unsafe { align_of_val(&4 as *const i32 as *const Opaque) }; + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ evaluation of `_ALIGN` failed here error: aborting due to 2 previous errors diff --git a/tests/ui/consts/const-unstable-intrinsic.rs b/tests/ui/consts/const-unstable-intrinsic.rs index 890a30c73c8a..d130eb6c707f 100644 --- a/tests/ui/consts/const-unstable-intrinsic.rs +++ b/tests/ui/consts/const-unstable-intrinsic.rs @@ -17,13 +17,13 @@ const fn const_main() { unstable_intrinsic::size_of_val(&x); //~^ERROR: unstable library feature `unstable` //~|ERROR: not yet stable as a const intrinsic - unstable_intrinsic::min_align_of_val(&x); + unstable_intrinsic::align_of_val(&x); //~^ERROR: unstable library feature `unstable` //~|ERROR: not yet stable as a const intrinsic size_of_val(&x); //~^ERROR: cannot use `#[feature(local)]` - min_align_of_val(&x); + align_of_val(&x); //~^ERROR: cannot use `#[feature(local)]` } } @@ -35,7 +35,7 @@ pub const unsafe fn size_of_val(x: *const T) -> usize; #[unstable(feature = "local", issue = "42")] #[rustc_const_unstable(feature = "local", issue = "42")] #[rustc_intrinsic] -pub const unsafe fn min_align_of_val(x: *const T) -> usize; +pub const unsafe fn align_of_val(x: *const T) -> usize; #[stable(feature = "rust1", since = "1.0.0")] #[rustc_const_stable(feature = "const_intrinsic_copy", since = "1.63.0")] diff --git a/tests/ui/consts/const-unstable-intrinsic.stderr b/tests/ui/consts/const-unstable-intrinsic.stderr index 7e7ba966cee1..973c7bae5869 100644 --- a/tests/ui/consts/const-unstable-intrinsic.stderr +++ b/tests/ui/consts/const-unstable-intrinsic.stderr @@ -11,8 +11,8 @@ LL | unstable_intrinsic::size_of_val(&x); error[E0658]: use of unstable library feature `unstable` --> $DIR/const-unstable-intrinsic.rs:20:9 | -LL | unstable_intrinsic::min_align_of_val(&x); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | unstable_intrinsic::align_of_val(&x); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = note: see issue #42 for more information = help: add `#![feature(unstable)]` to the crate attributes to enable @@ -29,11 +29,11 @@ help: add `#![feature(unstable)]` to the crate attributes to enable LL + #![feature(unstable)] | -error: `min_align_of_val` is not yet stable as a const intrinsic +error: `align_of_val` is not yet stable as a const intrinsic --> $DIR/const-unstable-intrinsic.rs:20:9 | -LL | unstable_intrinsic::min_align_of_val(&x); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | unstable_intrinsic::align_of_val(&x); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | help: add `#![feature(unstable)]` to the crate attributes to enable | @@ -55,8 +55,8 @@ LL | const fn const_main() { error: const function that might be (indirectly) exposed to stable cannot use `#[feature(local)]` --> $DIR/const-unstable-intrinsic.rs:26:9 | -LL | min_align_of_val(&x); - | ^^^^^^^^^^^^^^^^^^^^ +LL | align_of_val(&x); + | ^^^^^^^^^^^^^^^^ | help: if the function is not (yet) meant to be exposed to stable const contexts, add `#[rustc_const_unstable]` | diff --git a/tests/ui/consts/gate-do-not-const-check.rs b/tests/ui/consts/gate-do-not-const-check.rs index be7e70dfabba..0ebb1e7c82e2 100644 --- a/tests/ui/consts/gate-do-not-const-check.rs +++ b/tests/ui/consts/gate-do-not-const-check.rs @@ -1,5 +1,7 @@ #[rustc_do_not_const_check] -//~^ ERROR this is an internal attribute that will never be stable +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_do_not_const_check]` attribute is an internal implementation detail that will never be stable +//~| NOTE `#[rustc_do_not_const_check]` skips const-check for this function's body const fn foo() {} fn main() {} diff --git a/tests/ui/consts/gate-do-not-const-check.stderr b/tests/ui/consts/gate-do-not-const-check.stderr index 74ea71c4ed80..778ee50e71b6 100644 --- a/tests/ui/consts/gate-do-not-const-check.stderr +++ b/tests/ui/consts/gate-do-not-const-check.stderr @@ -1,11 +1,12 @@ -error[E0658]: this is an internal attribute that will never be stable +error[E0658]: use of an internal attribute --> $DIR/gate-do-not-const-check.rs:1:1 | LL | #[rustc_do_not_const_check] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_do_not_const_check]` attribute is an internal implementation detail that will never be stable + = note: `#[rustc_do_not_const_check]` skips const-check for this function's body error: aborting due to 1 previous error diff --git a/tests/ui/coroutine/auto-trait-regions.stderr b/tests/ui/coroutine/auto-trait-regions.stderr index a9a0bde2ba01..a3b5a5f006e6 100644 --- a/tests/ui/coroutine/auto-trait-regions.stderr +++ b/tests/ui/coroutine/auto-trait-regions.stderr @@ -11,7 +11,7 @@ LL | assert_foo(a); | help: consider using a `let` binding to create a longer lived value | -LL ~ let binding = true; +LL ~ let mut binding = true; LL ~ let a = A(&mut binding, &mut true, No); | @@ -28,7 +28,7 @@ LL | assert_foo(a); | help: consider using a `let` binding to create a longer lived value | -LL ~ let binding = true; +LL ~ let mut binding = true; LL ~ let a = A(&mut true, &mut binding, No); | diff --git a/tests/ui/deprecation/deprecated_no_stack_check.rs b/tests/ui/deprecation/deprecated_no_stack_check.rs index 8e1f5bbf045a..ef482098634a 100644 --- a/tests/ui/deprecation/deprecated_no_stack_check.rs +++ b/tests/ui/deprecation/deprecated_no_stack_check.rs @@ -1,3 +1,5 @@ +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" + #![deny(warnings)] #![feature(no_stack_check)] //~^ ERROR: feature has been removed [E0557] diff --git a/tests/ui/deprecation/deprecated_no_stack_check.stderr b/tests/ui/deprecation/deprecated_no_stack_check.stderr index d78ca20f10b4..2d08b1b8db54 100644 --- a/tests/ui/deprecation/deprecated_no_stack_check.stderr +++ b/tests/ui/deprecation/deprecated_no_stack_check.stderr @@ -1,8 +1,10 @@ error[E0557]: feature has been removed - --> $DIR/deprecated_no_stack_check.rs:2:12 + --> $DIR/deprecated_no_stack_check.rs:4:12 | LL | #![feature(no_stack_check)] | ^^^^^^^^^^^^^^ feature has been removed + | + = note: removed in 1.0.0 (you are using $RUSTC_VERSION); see for more information error: aborting due to 1 previous error diff --git a/tests/ui/exclusive-drop-and-copy.rs b/tests/ui/derives/copy-drop-mutually-exclusive.rs similarity index 79% rename from tests/ui/exclusive-drop-and-copy.rs rename to tests/ui/derives/copy-drop-mutually-exclusive.rs index 210ecaed7567..5147605910d7 100644 --- a/tests/ui/exclusive-drop-and-copy.rs +++ b/tests/ui/derives/copy-drop-mutually-exclusive.rs @@ -1,4 +1,4 @@ -// issue #20126 +//! Regression test for issue #20126: Copy and Drop traits are mutually exclusive #[derive(Copy, Clone)] //~ ERROR the trait `Copy` cannot be implemented struct Foo; diff --git a/tests/ui/exclusive-drop-and-copy.stderr b/tests/ui/derives/copy-drop-mutually-exclusive.stderr similarity index 83% rename from tests/ui/exclusive-drop-and-copy.stderr rename to tests/ui/derives/copy-drop-mutually-exclusive.stderr index 340ca89c396b..771bbc925695 100644 --- a/tests/ui/exclusive-drop-and-copy.stderr +++ b/tests/ui/derives/copy-drop-mutually-exclusive.stderr @@ -1,11 +1,11 @@ error[E0184]: the trait `Copy` cannot be implemented for this type; the type has a destructor - --> $DIR/exclusive-drop-and-copy.rs:3:10 + --> $DIR/copy-drop-mutually-exclusive.rs:3:10 | LL | #[derive(Copy, Clone)] | ^^^^ `Copy` not allowed on types with destructors error[E0184]: the trait `Copy` cannot be implemented for this type; the type has a destructor - --> $DIR/exclusive-drop-and-copy.rs:10:10 + --> $DIR/copy-drop-mutually-exclusive.rs:10:10 | LL | #[derive(Copy, Clone)] | ^^^^ `Copy` not allowed on types with destructors diff --git a/tests/ui/diagnostic_namespace/multiline_spans.rs b/tests/ui/diagnostic_namespace/multiline_spans.rs new file mode 100644 index 000000000000..994dd9fd011c --- /dev/null +++ b/tests/ui/diagnostic_namespace/multiline_spans.rs @@ -0,0 +1,55 @@ +#![crate_type = "lib"] +#![deny(unknown_or_malformed_diagnostic_attributes)] + + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string \ + {unknown}")] +//~^ ERROR there is no parameter `unknown` on trait `MultiLine` [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLine {} + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string {unknown}")] +//~^ ERROR there is no parameter `unknown` on trait `MultiLine2` [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLine2 {} + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string {unknown}")] +//~^ ERROR there is no parameter `unknown` on trait `MultiLine3` [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLine3 {} + + +#[diagnostic::on_unimplemented(message = "here is a big \ +\ + \ + \ + \ + multiline string {unknown}")] +//~^ ERROR there is no parameter `unknown` on trait `MultiLine4` [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLine4 {} + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string \ + {Self:+}")] +//~^ ERROR invalid format specifier [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLineFmt {} + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string {Self:X}")] +//~^ ERROR invalid format specifier [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLineFmt2 {} + +#[diagnostic::on_unimplemented(message = "here is a big \ + multiline string {Self:#}")] +//~^ ERROR invalid format specifier [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLineFmt3 {} + + +#[diagnostic::on_unimplemented(message = "here is a big \ +\ + \ + \ + \ + multiline string {Self:?}")] +//~^ ERROR invalid format specifier [unknown_or_malformed_diagnostic_attributes] +pub trait MultiLineFmt4 {} diff --git a/tests/ui/diagnostic_namespace/multiline_spans.stderr b/tests/ui/diagnostic_namespace/multiline_spans.stderr new file mode 100644 index 000000000000..894bfe3d90a5 --- /dev/null +++ b/tests/ui/diagnostic_namespace/multiline_spans.stderr @@ -0,0 +1,71 @@ +error: there is no parameter `unknown` on trait `MultiLine` + --> $DIR/multiline_spans.rs:7:43 + | +LL | ... {unknown}")] + | ^^^^^^^ + | + = help: expect either a generic argument name or `{Self}` as format argument +note: the lint level is defined here + --> $DIR/multiline_spans.rs:2:9 + | +LL | #![deny(unknown_or_malformed_diagnostic_attributes)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: there is no parameter `unknown` on trait `MultiLine2` + --> $DIR/multiline_spans.rs:12:60 + | +LL | ... multiline string {unknown}")] + | ^^^^^^^ + | + = help: expect either a generic argument name or `{Self}` as format argument + +error: there is no parameter `unknown` on trait `MultiLine3` + --> $DIR/multiline_spans.rs:17:23 + | +LL | multiline string {unknown}")] + | ^^^^^^^ + | + = help: expect either a generic argument name or `{Self}` as format argument + +error: there is no parameter `unknown` on trait `MultiLine4` + --> $DIR/multiline_spans.rs:27:23 + | +LL | multiline string {unknown}")] + | ^^^^^^^ + | + = help: expect either a generic argument name or `{Self}` as format argument + +error: invalid format specifier + --> $DIR/multiline_spans.rs:33:47 + | +LL | ... {Self:+}")] + | ^^ + | + = help: no format specifier are supported in this position + +error: invalid format specifier + --> $DIR/multiline_spans.rs:38:64 + | +LL | ... multiline string {Self:X}")] + | ^^ + | + = help: no format specifier are supported in this position + +error: invalid format specifier + --> $DIR/multiline_spans.rs:43:27 + | +LL | multiline string {Self:#}")] + | ^^ + | + = help: no format specifier are supported in this position + +error: invalid format specifier + --> $DIR/multiline_spans.rs:53:27 + | +LL | multiline string {Self:?}")] + | ^^ + | + = help: no format specifier are supported in this position + +error: aborting due to 8 previous errors + diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.rs b/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.rs index 44f269eb9670..4762d9e793fa 100644 --- a/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.rs +++ b/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.rs @@ -12,6 +12,8 @@ trait ImportantTrait2 {} #[diagnostic::on_unimplemented(message = "Test {1:}")] //~^WARN positional format arguments are not allowed here //~|WARN positional format arguments are not allowed here +//~|WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] +//~|WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] trait ImportantTrait3 {} #[diagnostic::on_unimplemented(message = "Test {Self:123}")] @@ -20,17 +22,22 @@ trait ImportantTrait3 {} trait ImportantTrait4 {} #[diagnostic::on_unimplemented(message = "Test {Self:!}")] -//~^WARN expected `}`, found `!` -//~|WARN expected `}`, found `!` -//~|WARN unmatched `}` found -//~|WARN unmatched `}` found +//~^WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] +//~|WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] trait ImportantTrait5 {} +#[diagnostic::on_unimplemented(message = "Test {Self:}")] +//~^WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] +//~|WARN invalid format specifier [unknown_or_malformed_diagnostic_attributes] +trait ImportantTrait6 {} + + fn check_1(_: impl ImportantTrait1) {} fn check_2(_: impl ImportantTrait2) {} fn check_3(_: impl ImportantTrait3) {} fn check_4(_: impl ImportantTrait4) {} fn check_5(_: impl ImportantTrait5) {} +fn check_6(_: impl ImportantTrait6) {} fn main() { check_1(()); @@ -42,5 +49,7 @@ fn main() { check_4(()); //~^ERROR Test () check_5(()); - //~^ERROR Test {Self:!} + //~^ERROR Test () + check_6(()); + //~^ERROR Test () } diff --git a/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.stderr b/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.stderr index a82a1e78da0c..2670d0630f7f 100644 --- a/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.stderr +++ b/tests/ui/diagnostic_namespace/on_unimplemented/broken_format.stderr @@ -14,6 +14,14 @@ LL | #[diagnostic::on_unimplemented(message = "Test {}")] | = help: only named format arguments with the name of one of the generic types are allowed in this context +warning: invalid format specifier + --> $DIR/broken_format.rs:12:50 + | +LL | #[diagnostic::on_unimplemented(message = "Test {1:}")] + | ^ + | + = help: no format specifier are supported in this position + warning: positional format arguments are not allowed here --> $DIR/broken_format.rs:12:49 | @@ -23,24 +31,28 @@ LL | #[diagnostic::on_unimplemented(message = "Test {1:}")] = help: only named format arguments with the name of one of the generic types are allowed in this context warning: invalid format specifier - --> $DIR/broken_format.rs:17:42 + --> $DIR/broken_format.rs:19:53 | LL | #[diagnostic::on_unimplemented(message = "Test {Self:123}")] - | ^^^^^^^^^^^^^^^^^ + | ^^^^ | = help: no format specifier are supported in this position -warning: expected `}`, found `!` - --> $DIR/broken_format.rs:22:42 +warning: invalid format specifier + --> $DIR/broken_format.rs:24:53 | LL | #[diagnostic::on_unimplemented(message = "Test {Self:!}")] - | ^^^^^^^^^^^^^^^ + | ^^ + | + = help: no format specifier are supported in this position -warning: unmatched `}` found - --> $DIR/broken_format.rs:22:42 +warning: invalid format specifier + --> $DIR/broken_format.rs:29:53 | -LL | #[diagnostic::on_unimplemented(message = "Test {Self:!}")] - | ^^^^^^^^^^^^^^^ +LL | #[diagnostic::on_unimplemented(message = "Test {Self:}")] + | ^ + | + = help: no format specifier are supported in this position warning: unmatched `}` found --> $DIR/broken_format.rs:2:42 @@ -51,7 +63,7 @@ LL | #[diagnostic::on_unimplemented(message = "{{Test } thing")] = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error[E0277]: {{Test } thing - --> $DIR/broken_format.rs:36:13 + --> $DIR/broken_format.rs:43:13 | LL | check_1(()); | ------- ^^ the trait `ImportantTrait1` is not implemented for `()` @@ -64,7 +76,7 @@ help: this trait has no implementations, consider adding one LL | trait ImportantTrait1 {} | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `check_1` - --> $DIR/broken_format.rs:29:20 + --> $DIR/broken_format.rs:35:20 | LL | fn check_1(_: impl ImportantTrait1) {} | ^^^^^^^^^^^^^^^ required by this bound in `check_1` @@ -79,7 +91,7 @@ LL | #[diagnostic::on_unimplemented(message = "Test {}")] = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error[E0277]: Test {} - --> $DIR/broken_format.rs:38:13 + --> $DIR/broken_format.rs:45:13 | LL | check_2(()); | ------- ^^ the trait `ImportantTrait2` is not implemented for `()` @@ -92,11 +104,20 @@ help: this trait has no implementations, consider adding one LL | trait ImportantTrait2 {} | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `check_2` - --> $DIR/broken_format.rs:30:20 + --> $DIR/broken_format.rs:36:20 | LL | fn check_2(_: impl ImportantTrait2) {} | ^^^^^^^^^^^^^^^ required by this bound in `check_2` +warning: invalid format specifier + --> $DIR/broken_format.rs:12:50 + | +LL | #[diagnostic::on_unimplemented(message = "Test {1:}")] + | ^ + | + = help: no format specifier are supported in this position + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + warning: positional format arguments are not allowed here --> $DIR/broken_format.rs:12:49 | @@ -107,7 +128,7 @@ LL | #[diagnostic::on_unimplemented(message = "Test {1:}")] = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error[E0277]: Test {1} - --> $DIR/broken_format.rs:40:13 + --> $DIR/broken_format.rs:47:13 | LL | check_3(()); | ------- ^^ the trait `ImportantTrait3` is not implemented for `()` @@ -115,27 +136,27 @@ LL | check_3(()); | required by a bound introduced by this call | help: this trait has no implementations, consider adding one - --> $DIR/broken_format.rs:15:1 + --> $DIR/broken_format.rs:17:1 | LL | trait ImportantTrait3 {} | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `check_3` - --> $DIR/broken_format.rs:31:20 + --> $DIR/broken_format.rs:37:20 | LL | fn check_3(_: impl ImportantTrait3) {} | ^^^^^^^^^^^^^^^ required by this bound in `check_3` warning: invalid format specifier - --> $DIR/broken_format.rs:17:42 + --> $DIR/broken_format.rs:19:53 | LL | #[diagnostic::on_unimplemented(message = "Test {Self:123}")] - | ^^^^^^^^^^^^^^^^^ + | ^^^^ | = help: no format specifier are supported in this position = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error[E0277]: Test () - --> $DIR/broken_format.rs:42:13 + --> $DIR/broken_format.rs:49:13 | LL | check_4(()); | ------- ^^ the trait `ImportantTrait4` is not implemented for `()` @@ -143,34 +164,27 @@ LL | check_4(()); | required by a bound introduced by this call | help: this trait has no implementations, consider adding one - --> $DIR/broken_format.rs:20:1 + --> $DIR/broken_format.rs:22:1 | LL | trait ImportantTrait4 {} | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `check_4` - --> $DIR/broken_format.rs:32:20 + --> $DIR/broken_format.rs:38:20 | LL | fn check_4(_: impl ImportantTrait4) {} | ^^^^^^^^^^^^^^^ required by this bound in `check_4` -warning: expected `}`, found `!` - --> $DIR/broken_format.rs:22:42 +warning: invalid format specifier + --> $DIR/broken_format.rs:24:53 | LL | #[diagnostic::on_unimplemented(message = "Test {Self:!}")] - | ^^^^^^^^^^^^^^^ + | ^^ | + = help: no format specifier are supported in this position = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` -warning: unmatched `}` found - --> $DIR/broken_format.rs:22:42 - | -LL | #[diagnostic::on_unimplemented(message = "Test {Self:!}")] - | ^^^^^^^^^^^^^^^ - | - = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` - -error[E0277]: Test {Self:!} - --> $DIR/broken_format.rs:44:13 +error[E0277]: Test () + --> $DIR/broken_format.rs:51:13 | LL | check_5(()); | ------- ^^ the trait `ImportantTrait5` is not implemented for `()` @@ -183,11 +197,39 @@ help: this trait has no implementations, consider adding one LL | trait ImportantTrait5 {} | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `check_5` - --> $DIR/broken_format.rs:33:20 + --> $DIR/broken_format.rs:39:20 | LL | fn check_5(_: impl ImportantTrait5) {} | ^^^^^^^^^^^^^^^ required by this bound in `check_5` -error: aborting due to 5 previous errors; 12 warnings emitted +warning: invalid format specifier + --> $DIR/broken_format.rs:29:53 + | +LL | #[diagnostic::on_unimplemented(message = "Test {Self:}")] + | ^ + | + = help: no format specifier are supported in this position + = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` + +error[E0277]: Test () + --> $DIR/broken_format.rs:53:13 + | +LL | check_6(()); + | ------- ^^ the trait `ImportantTrait6` is not implemented for `()` + | | + | required by a bound introduced by this call + | +help: this trait has no implementations, consider adding one + --> $DIR/broken_format.rs:32:1 + | +LL | trait ImportantTrait6 {} + | ^^^^^^^^^^^^^^^^^^^^^ +note: required by a bound in `check_6` + --> $DIR/broken_format.rs:40:20 + | +LL | fn check_6(_: impl ImportantTrait6) {} + | ^^^^^^^^^^^^^^^ required by this bound in `check_6` + +error: aborting due to 6 previous errors; 14 warnings emitted For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/illegal-ufcs-drop.fixed b/tests/ui/drop/explicit-drop-call-error.fixed similarity index 75% rename from tests/ui/illegal-ufcs-drop.fixed rename to tests/ui/drop/explicit-drop-call-error.fixed index 2b1c967ed1e0..f2f0245df96f 100644 --- a/tests/ui/illegal-ufcs-drop.fixed +++ b/tests/ui/drop/explicit-drop-call-error.fixed @@ -1,3 +1,5 @@ +//! Test error for explicit destructor method calls via UFCS + //@ run-rustfix #![allow(dropping_references)] diff --git a/tests/ui/illegal-ufcs-drop.rs b/tests/ui/drop/explicit-drop-call-error.rs similarity index 75% rename from tests/ui/illegal-ufcs-drop.rs rename to tests/ui/drop/explicit-drop-call-error.rs index 99dda0dab340..e41c806bd1e0 100644 --- a/tests/ui/illegal-ufcs-drop.rs +++ b/tests/ui/drop/explicit-drop-call-error.rs @@ -1,3 +1,5 @@ +//! Test error for explicit destructor method calls via UFCS + //@ run-rustfix #![allow(dropping_references)] diff --git a/tests/ui/illegal-ufcs-drop.stderr b/tests/ui/drop/explicit-drop-call-error.stderr similarity index 88% rename from tests/ui/illegal-ufcs-drop.stderr rename to tests/ui/drop/explicit-drop-call-error.stderr index 4f214a12747e..95d5c31ab6d0 100644 --- a/tests/ui/illegal-ufcs-drop.stderr +++ b/tests/ui/drop/explicit-drop-call-error.stderr @@ -1,5 +1,5 @@ error[E0040]: explicit use of destructor method - --> $DIR/illegal-ufcs-drop.rs:12:5 + --> $DIR/explicit-drop-call-error.rs:14:5 | LL | Drop::drop(&mut Foo) | ^^^^^^^^^^ diff --git a/tests/ui/editions/edition-keywords-2018-2015-parsing.stderr b/tests/ui/editions/edition-keywords-2018-2015-parsing.stderr index 152a6f3a41e6..34f5c7d30842 100644 --- a/tests/ui/editions/edition-keywords-2018-2015-parsing.stderr +++ b/tests/ui/editions/edition-keywords-2018-2015-parsing.stderr @@ -44,22 +44,22 @@ note: while trying to match `r#async` LL | (r#async) => (1) | ^^^^^^^ -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/auxiliary/edition-kw-macro-2015.rs:27:23 | LL | ($i: ident) => ($i) - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` | ::: $DIR/edition-keywords-2018-2015-parsing.rs:22:8 | LL | if passes_ident!(async) == 1 {} // FIXME: Edition hygiene bug, async here is 2018 and reserved | -------------------- in this macro invocation -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/edition-keywords-2018-2015-parsing.rs:24:24 | LL | if passes_tt!(async) == 1 {} - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` error[E0308]: mismatched types --> $DIR/edition-keywords-2018-2015-parsing.rs:29:33 diff --git a/tests/ui/editions/edition-keywords-2018-2018-parsing.stderr b/tests/ui/editions/edition-keywords-2018-2018-parsing.stderr index 53f1b827f9c6..dd3f4938c74b 100644 --- a/tests/ui/editions/edition-keywords-2018-2018-parsing.stderr +++ b/tests/ui/editions/edition-keywords-2018-2018-parsing.stderr @@ -44,34 +44,34 @@ note: while trying to match `r#async` LL | (r#async) => (1) | ^^^^^^^ -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/auxiliary/edition-kw-macro-2018.rs:27:23 | LL | ($i: ident) => ($i) - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` | ::: $DIR/edition-keywords-2018-2018-parsing.rs:29:8 | LL | if passes_ident!(async) == 1 {} // FIXME: Edition hygiene bug, async here is 2018 and reserved | -------------------- in this macro invocation -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/edition-keywords-2018-2018-parsing.rs:31:24 | LL | if passes_tt!(async) == 1 {} - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/edition-keywords-2018-2018-parsing.rs:14:23 | LL | ($i: ident) => ($i) - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` -error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `|`, or `||` +error: macro expansion ends with an incomplete expression: expected one of `move`, `use`, `{`, `|`, or `||` --> $DIR/edition-keywords-2018-2018-parsing.rs:35:30 | LL | if local_passes_tt!(async) == 1 {} - | ^ expected one of `move`, `use`, `|`, or `||` + | ^ expected one of `move`, `use`, `{`, `|`, or `||` error[E0308]: mismatched types --> $DIR/edition-keywords-2018-2018-parsing.rs:40:33 diff --git a/tests/ui/editions/unsafe-attr-edition-span.e2024.stderr b/tests/ui/editions/unsafe-attr-edition-span.e2024.stderr new file mode 100644 index 000000000000..28871a1cce4f --- /dev/null +++ b/tests/ui/editions/unsafe-attr-edition-span.e2024.stderr @@ -0,0 +1,24 @@ +error: unsafe attribute used without unsafe + --> $DIR/unsafe-attr-edition-span.rs:21:3 + | +LL | #[no_mangle] + | ^^^^^^^^^ usage of unsafe attribute + | +help: wrap the attribute in `unsafe(...)` + | +LL | #[unsafe(no_mangle)] + | +++++++ + + +error: unsafe attribute used without unsafe + --> $DIR/unsafe-attr-edition-span.rs:25:7 + | +LL | #[no_mangle] + | ^^^^^^^^^ usage of unsafe attribute + | +help: wrap the attribute in `unsafe(...)` + | +LL | #[unsafe(no_mangle)] + | +++++++ + + +error: aborting due to 2 previous errors + diff --git a/tests/ui/editions/unsafe-attr-edition-span.rs b/tests/ui/editions/unsafe-attr-edition-span.rs new file mode 100644 index 000000000000..bc44b34063cc --- /dev/null +++ b/tests/ui/editions/unsafe-attr-edition-span.rs @@ -0,0 +1,27 @@ +// Tests that the correct span is used to determine the edition of an attribute that was safe to use +// in earlier editions, but has become `unsafe` in later editions. +// +// Determining the correct edition is non-trivial because of macro expansion. For instance, +// the `thread_local!` macro (defined in std and hence using the most recent edition) parses the +// attribute, and then re-emits it. Therefore, the span of the `#` token starting the +// `#[no_mangle]` attribute has std's edition, while the attribute name has the edition of this +// file, which may be different. + +//@ revisions: e2015 e2018 e2021 e2024 + +//@[e2018] edition:2018 +//@[e2021] edition:2021 +//@[e2024] edition:2024 +// +//@[e2015] check-pass +//@[e2018] check-pass +//@[e2021] check-pass +#![crate_type = "lib"] + +#[no_mangle] //[e2024]~ ERROR unsafe attribute used without unsafe +static TEST_OUTSIDE: usize = 0; + +thread_local! { + #[no_mangle]//[e2024]~ ERROR unsafe attribute used without unsafe + static TEST: usize = 0; +} diff --git a/tests/ui/empty-allocation-rvalue-non-null.rs b/tests/ui/empty-allocation-rvalue-non-null.rs deleted file mode 100644 index 0cd4fde73eda..000000000000 --- a/tests/ui/empty-allocation-rvalue-non-null.rs +++ /dev/null @@ -1,7 +0,0 @@ -//@ run-pass - -#![allow(unused_variables)] - -pub fn main() { - let x: () = *Box::new(()); -} diff --git a/tests/ui/empty-type-parameter-list.rs b/tests/ui/empty-type-parameter-list.rs deleted file mode 100644 index e8d6b2a99640..000000000000 --- a/tests/ui/empty-type-parameter-list.rs +++ /dev/null @@ -1,24 +0,0 @@ -//@ run-pass -// Test that empty type parameter list (<>) is synonymous with -// no type parameters at all - -struct S<>; -trait T<> {} //~ WARN trait `T` is never used -enum E<> { V } -impl<> T<> for S<> {} -impl T for E {} -fn foo<>() {} -fn bar() {} - -fn main() { - let _ = S; - let _ = S::<>; - let _ = E::V; - let _ = E::<>::V; - foo(); - foo::<>(); - - // Test that we can supply <> to non generic things - bar::<>(); - let _: i32<>; -} diff --git a/tests/ui/enum/dead-code-associated-function.rs b/tests/ui/enum/dead-code-associated-function.rs new file mode 100644 index 000000000000..d172ceb41dde --- /dev/null +++ b/tests/ui/enum/dead-code-associated-function.rs @@ -0,0 +1,20 @@ +//@ check-pass +#![warn(dead_code)] + +enum E { + F(), + C(), +} + +impl E { + #[expect(non_snake_case)] + fn F() {} + //~^ WARN: associated items `F` and `C` are never used + + const C: () = (); +} + +fn main() { + let _: E = E::F(); + let _: E = E::C(); +} diff --git a/tests/ui/enum/dead-code-associated-function.stderr b/tests/ui/enum/dead-code-associated-function.stderr new file mode 100644 index 000000000000..e3c1a4c81a49 --- /dev/null +++ b/tests/ui/enum/dead-code-associated-function.stderr @@ -0,0 +1,30 @@ +warning: associated items `F` and `C` are never used + --> $DIR/dead-code-associated-function.rs:11:8 + | +LL | impl E { + | ------ associated items in this implementation +LL | #[expect(non_snake_case)] +LL | fn F() {} + | ^ +... +LL | const C: () = (); + | ^ + | +note: it is impossible to refer to the associated function `F` because it is shadowed by this enum variant with the same name + --> $DIR/dead-code-associated-function.rs:5:5 + | +LL | F(), + | ^ +note: it is impossible to refer to the associated constant `C` because it is shadowed by this enum variant with the same name + --> $DIR/dead-code-associated-function.rs:6:5 + | +LL | C(), + | ^ +note: the lint level is defined here + --> $DIR/dead-code-associated-function.rs:2:9 + | +LL | #![warn(dead_code)] + | ^^^^^^^^^ + +warning: 1 warning emitted + diff --git a/tests/ui/error-should-say-copy-not-pod.rs b/tests/ui/error-should-say-copy-not-pod.rs deleted file mode 100644 index 40c4730ef699..000000000000 --- a/tests/ui/error-should-say-copy-not-pod.rs +++ /dev/null @@ -1,7 +0,0 @@ -// Tests that the error message uses the word Copy, not Pod. - -fn check_bound(_: T) {} - -fn main() { - check_bound("nocopy".to_string()); //~ ERROR : Copy` is not satisfied -} diff --git a/tests/ui/error-should-say-copy-not-pod.stderr b/tests/ui/error-should-say-copy-not-pod.stderr deleted file mode 100644 index 6aa129fa29b5..000000000000 --- a/tests/ui/error-should-say-copy-not-pod.stderr +++ /dev/null @@ -1,22 +0,0 @@ -error[E0277]: the trait bound `String: Copy` is not satisfied - --> $DIR/error-should-say-copy-not-pod.rs:6:17 - | -LL | check_bound("nocopy".to_string()); - | ----------- ^^^^^^^^^^^^^^^^^^^^ the trait `Copy` is not implemented for `String` - | | - | required by a bound introduced by this call - | -note: required by a bound in `check_bound` - --> $DIR/error-should-say-copy-not-pod.rs:3:18 - | -LL | fn check_bound(_: T) {} - | ^^^^ required by this bound in `check_bound` -help: consider removing this method call, as the receiver has type `&'static str` and `&'static str: Copy` trivially holds - | -LL - check_bound("nocopy".to_string()); -LL + check_bound("nocopy"); - | - -error: aborting due to 1 previous error - -For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/explicit-i-suffix.rs b/tests/ui/explicit-i-suffix.rs deleted file mode 100644 index 0a6ed49ae270..000000000000 --- a/tests/ui/explicit-i-suffix.rs +++ /dev/null @@ -1,13 +0,0 @@ -//@ run-pass - -#![allow(unused_must_use)] - -pub fn main() { - let x: isize = 8; - let y = 9; - x + y; - - let q: isize = -8; - let r = -9; - q + r; -} diff --git a/tests/ui/ext-nonexistent.rs b/tests/ui/ext-nonexistent.rs deleted file mode 100644 index 1293324b67eb..000000000000 --- a/tests/ui/ext-nonexistent.rs +++ /dev/null @@ -1,2 +0,0 @@ -fn main() { iamnotanextensionthatexists!(""); } -//~^ ERROR cannot find macro `iamnotanextensionthatexists` in this scope diff --git a/tests/ui/ext-nonexistent.stderr b/tests/ui/ext-nonexistent.stderr deleted file mode 100644 index edb59bba6e5d..000000000000 --- a/tests/ui/ext-nonexistent.stderr +++ /dev/null @@ -1,8 +0,0 @@ -error: cannot find macro `iamnotanextensionthatexists` in this scope - --> $DIR/ext-nonexistent.rs:1:13 - | -LL | fn main() { iamnotanextensionthatexists!(""); } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -error: aborting due to 1 previous error - diff --git a/tests/ui/fact.rs b/tests/ui/fact.rs deleted file mode 100644 index e94c12da0134..000000000000 --- a/tests/ui/fact.rs +++ /dev/null @@ -1,26 +0,0 @@ -//@ run-pass - -fn f(x: isize) -> isize { - // println!("in f:"); - - println!("{}", x); - if x == 1 { - // println!("bottoming out"); - - return 1; - } else { - // println!("recurring"); - - let y: isize = x * f(x - 1); - // println!("returned"); - - println!("{}", y); - return y; - } -} - -pub fn main() { - assert_eq!(f(5), 120); - // println!("all done"); - -} diff --git a/tests/ui/feature-gates/feature-gate-abi-custom.rs b/tests/ui/feature-gates/feature-gate-abi-custom.rs new file mode 100644 index 000000000000..3ddce974dd7d --- /dev/null +++ b/tests/ui/feature-gates/feature-gate-abi-custom.rs @@ -0,0 +1,51 @@ +//@ add-core-stubs +//@ needs-asm-support +#![no_core] +#![feature(no_core, lang_items)] +#![crate_type = "rlib"] + +extern crate minicore; +use minicore::*; + +#[unsafe(naked)] +unsafe extern "custom" fn f7() { + //~^ ERROR "custom" ABI is experimental + naked_asm!("") +} +trait Tr { + extern "custom" fn m7(); + //~^ ERROR "custom" ABI is experimental + //~| ERROR functions with the `"custom"` ABI must be unsafe + #[unsafe(naked)] + extern "custom" fn dm7() { + //~^ ERROR "custom" ABI is experimental + //~| ERROR functions with the `"custom"` ABI must be unsafe + naked_asm!("") + } +} + +struct S; + +// Methods in trait impl +impl Tr for S { + #[unsafe(naked)] + extern "custom" fn m7() { + //~^ ERROR "custom" ABI is experimental + //~| ERROR functions with the `"custom"` ABI must be unsafe + naked_asm!("") + } +} + +// Methods in inherent impl +impl S { + #[unsafe(naked)] + extern "custom" fn im7() { + //~^ ERROR "custom" ABI is experimental + //~| ERROR functions with the `"custom"` ABI must be unsafe + naked_asm!("") + } +} + +type A7 = extern "custom" fn(); //~ ERROR "custom" ABI is experimental + +extern "custom" {} //~ ERROR "custom" ABI is experimental diff --git a/tests/ui/feature-gates/feature-gate-abi-custom.stderr b/tests/ui/feature-gates/feature-gate-abi-custom.stderr new file mode 100644 index 000000000000..e6dce0126d64 --- /dev/null +++ b/tests/ui/feature-gates/feature-gate-abi-custom.stderr @@ -0,0 +1,117 @@ +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/feature-gate-abi-custom.rs:16:5 + | +LL | extern "custom" fn m7(); + | ^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn m7(); + | ++++++ + +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/feature-gate-abi-custom.rs:20:5 + | +LL | extern "custom" fn dm7() { + | ^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn dm7() { + | ++++++ + +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/feature-gate-abi-custom.rs:32:5 + | +LL | extern "custom" fn m7() { + | ^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn m7() { + | ++++++ + +error: functions with the `"custom"` ABI must be unsafe + --> $DIR/feature-gate-abi-custom.rs:42:5 + | +LL | extern "custom" fn im7() { + | ^^^^^^^^^^^^^^^^^^^^^^^^ + | +help: add the `unsafe` keyword to this definition + | +LL | unsafe extern "custom" fn im7() { + | ++++++ + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:11:15 + | +LL | unsafe extern "custom" fn f7() { + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:16:12 + | +LL | extern "custom" fn m7(); + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:20:12 + | +LL | extern "custom" fn dm7() { + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:32:12 + | +LL | extern "custom" fn m7() { + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:42:12 + | +LL | extern "custom" fn im7() { + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:49:18 + | +LL | type A7 = extern "custom" fn(); + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error[E0658]: the extern "custom" ABI is experimental and subject to change + --> $DIR/feature-gate-abi-custom.rs:51:8 + | +LL | extern "custom" {} + | ^^^^^^^^ + | + = note: see issue #140829 for more information + = help: add `#![feature(abi_custom)]` to the crate attributes to enable + = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + +error: aborting due to 11 previous errors + +For more information about this error, try `rustc --explain E0658`. diff --git a/tests/ui/feature-gates/feature-gate-coverage-attribute.rs b/tests/ui/feature-gates/feature-gate-coverage-attribute.rs index 0a463755f137..2cf4b76180e1 100644 --- a/tests/ui/feature-gates/feature-gate-coverage-attribute.rs +++ b/tests/ui/feature-gates/feature-gate-coverage-attribute.rs @@ -1,3 +1,5 @@ +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" + #![crate_type = "lib"] #![feature(no_coverage)] //~ ERROR feature has been removed [E0557] diff --git a/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr b/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr index 00e0f0afbde6..8c23544698d0 100644 --- a/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr +++ b/tests/ui/feature-gates/feature-gate-coverage-attribute.stderr @@ -1,13 +1,14 @@ error[E0557]: feature has been removed - --> $DIR/feature-gate-coverage-attribute.rs:2:12 + --> $DIR/feature-gate-coverage-attribute.rs:4:12 | LL | #![feature(no_coverage)] | ^^^^^^^^^^^ feature has been removed | + = note: removed in 1.74.0 (you are using $RUSTC_VERSION); see for more information = note: renamed to `coverage_attribute` error[E0658]: the `#[coverage]` attribute is an experimental feature - --> $DIR/feature-gate-coverage-attribute.rs:10:1 + --> $DIR/feature-gate-coverage-attribute.rs:12:1 | LL | #[coverage(off)] | ^^^^^^^^^^^^^^^^ diff --git a/tests/ui/feature-gates/feature-gate-keylocker_x86.rs b/tests/ui/feature-gates/feature-gate-keylocker_x86.rs deleted file mode 100644 index cef80ad41a89..000000000000 --- a/tests/ui/feature-gates/feature-gate-keylocker_x86.rs +++ /dev/null @@ -1,6 +0,0 @@ -//@ only-x86_64 -#[target_feature(enable = "kl")] -//~^ ERROR: currently unstable -unsafe fn foo() {} - -fn main() {} diff --git a/tests/ui/feature-gates/feature-gate-keylocker_x86.stderr b/tests/ui/feature-gates/feature-gate-keylocker_x86.stderr deleted file mode 100644 index ed814d3a3ce2..000000000000 --- a/tests/ui/feature-gates/feature-gate-keylocker_x86.stderr +++ /dev/null @@ -1,13 +0,0 @@ -error[E0658]: the target feature `kl` is currently unstable - --> $DIR/feature-gate-keylocker_x86.rs:2:18 - | -LL | #[target_feature(enable = "kl")] - | ^^^^^^^^^^^^^ - | - = note: see issue #134813 for more information - = help: add `#![feature(keylocker_x86)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date - -error: aborting due to 1 previous error - -For more information about this error, try `rustc --explain E0658`. diff --git a/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.rs b/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.rs index d1f6f4755f08..ffb444cd9aaf 100644 --- a/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.rs +++ b/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.rs @@ -1,6 +1,8 @@ // check that `pattern_complexity_limit` is feature-gated #![pattern_complexity_limit = "42"] -//~^ ERROR: the `#[pattern_complexity_limit]` attribute is just used for rustc unit tests +//~^ ERROR: use of an internal attribute [E0658] +//~| NOTE the `#[pattern_complexity_limit]` attribute is an internal implementation detail that will never be stable +//~| NOTE: the `#[pattern_complexity_limit]` attribute is used for rustc unit tests fn main() {} diff --git a/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.stderr b/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.stderr index e6f17710e096..9ddea866ea99 100644 --- a/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.stderr +++ b/tests/ui/feature-gates/feature-gate-pattern-complexity-limit.stderr @@ -1,11 +1,12 @@ -error[E0658]: the `#[pattern_complexity_limit]` attribute is just used for rustc unit tests and will never be stable +error[E0658]: use of an internal attribute --> $DIR/feature-gate-pattern-complexity-limit.rs:3:1 | LL | #![pattern_complexity_limit = "42"] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[pattern_complexity_limit]` attribute is an internal implementation detail that will never be stable + = note: the `#[pattern_complexity_limit]` attribute is used for rustc unit tests error: aborting due to 1 previous error diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs index 025b4b52f12f..17556723622e 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.rs @@ -1,6 +1,12 @@ // Test that `#[rustc_*]` attributes are gated by `rustc_attrs` feature gate. -#[rustc_variance] //~ ERROR the `#[rustc_variance]` attribute is just used for rustc unit tests and will never be stable -#[rustc_nonnull_optimization_guaranteed] //~ ERROR the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in libcore and libstd and will never be stable - +#[rustc_variance] +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_variance]` attribute is used for rustc unit tests +#[rustc_nonnull_optimization_guaranteed] +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_nonnull_optimization_guaranteed]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in the standard library +//~| NOTE the compiler does not even check whether the type indeed is being non-null-optimized; it is your responsibility to ensure that the attribute is only used on types that are optimized fn main() {} diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr index 0f760e0602d2..159d383e4089 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs-1.stderr @@ -1,21 +1,23 @@ -error[E0658]: the `#[rustc_variance]` attribute is just used for rustc unit tests and will never be stable +error[E0658]: use of an internal attribute --> $DIR/feature-gate-rustc-attrs-1.rs:3:1 | LL | #[rustc_variance] | ^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_variance]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_variance]` attribute is used for rustc unit tests -error[E0658]: the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in libcore and libstd and will never be stable - (note that the compiler does not even check whether the type indeed is being non-null-optimized; it is your responsibility to ensure that the attribute is only used on types that are optimized) - --> $DIR/feature-gate-rustc-attrs-1.rs:4:1 +error[E0658]: use of an internal attribute + --> $DIR/feature-gate-rustc-attrs-1.rs:7:1 | LL | #[rustc_nonnull_optimization_guaranteed] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_nonnull_optimization_guaranteed]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_nonnull_optimization_guaranteed]` attribute is just used to document guaranteed niche optimizations in the standard library + = note: the compiler does not even check whether the type indeed is being non-null-optimized; it is your responsibility to ensure that the attribute is only used on types that are optimized error: aborting due to 2 previous errors diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs.rs b/tests/ui/feature-gates/feature-gate-rustc-attrs.rs index c985298a30ae..e7b2eca6f858 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs.rs +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs.rs @@ -8,15 +8,19 @@ mod unknown { pub macro rustc() {} } #[rustc::unknown] //~^ ERROR attributes starting with `rustc` are reserved for use by the `rustc` compiler //~| ERROR expected attribute, found macro `rustc::unknown` +//~| NOTE not an attribute fn f() {} #[unknown::rustc] //~^ ERROR attributes starting with `rustc` are reserved for use by the `rustc` compiler //~| ERROR expected attribute, found macro `unknown::rustc` +//~| NOTE not an attribute fn g() {} #[rustc_dummy] -//~^ ERROR the `#[rustc_dummy]` attribute is just used for rustc unit tests +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_dummy]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_dummy]` attribute is used for rustc unit tests #[rustc_unknown] //~^ ERROR attributes starting with `rustc` are reserved for use by the `rustc` compiler //~| ERROR cannot find attribute `rustc_unknown` in this scope diff --git a/tests/ui/feature-gates/feature-gate-rustc-attrs.stderr b/tests/ui/feature-gates/feature-gate-rustc-attrs.stderr index c7a5ef3e44be..d58603883f15 100644 --- a/tests/ui/feature-gates/feature-gate-rustc-attrs.stderr +++ b/tests/ui/feature-gates/feature-gate-rustc-attrs.stderr @@ -11,37 +11,38 @@ LL | #[rustc::unknown] | ^^^^^^^^^^^^^^ not an attribute error: attributes starting with `rustc` are reserved for use by the `rustc` compiler - --> $DIR/feature-gate-rustc-attrs.rs:13:12 + --> $DIR/feature-gate-rustc-attrs.rs:14:12 | LL | #[unknown::rustc] | ^^^^^ error: expected attribute, found macro `unknown::rustc` - --> $DIR/feature-gate-rustc-attrs.rs:13:3 + --> $DIR/feature-gate-rustc-attrs.rs:14:3 | LL | #[unknown::rustc] | ^^^^^^^^^^^^^^ not an attribute error: attributes starting with `rustc` are reserved for use by the `rustc` compiler - --> $DIR/feature-gate-rustc-attrs.rs:20:3 + --> $DIR/feature-gate-rustc-attrs.rs:24:3 | LL | #[rustc_unknown] | ^^^^^^^^^^^^^ error: cannot find attribute `rustc_unknown` in this scope - --> $DIR/feature-gate-rustc-attrs.rs:20:3 + --> $DIR/feature-gate-rustc-attrs.rs:24:3 | LL | #[rustc_unknown] | ^^^^^^^^^^^^^ -error[E0658]: the `#[rustc_dummy]` attribute is just used for rustc unit tests and will never be stable - --> $DIR/feature-gate-rustc-attrs.rs:18:1 +error[E0658]: use of an internal attribute + --> $DIR/feature-gate-rustc-attrs.rs:20:1 | LL | #[rustc_dummy] | ^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_dummy]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_dummy]` attribute is used for rustc unit tests error: aborting due to 7 previous errors diff --git a/tests/ui/feature-gates/gated-bad-feature.rs b/tests/ui/feature-gates/gated-bad-feature.rs index 51f2db5556e2..3114f661dc5b 100644 --- a/tests/ui/feature-gates/gated-bad-feature.rs +++ b/tests/ui/feature-gates/gated-bad-feature.rs @@ -1,3 +1,4 @@ +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" #![feature(foo_bar_baz, foo(bar), foo = "baz", foo)] //~^ ERROR malformed `feature` //~| ERROR malformed `feature` diff --git a/tests/ui/feature-gates/gated-bad-feature.stderr b/tests/ui/feature-gates/gated-bad-feature.stderr index 2d01bdf3c1df..0e75dff14f8a 100644 --- a/tests/ui/feature-gates/gated-bad-feature.stderr +++ b/tests/ui/feature-gates/gated-bad-feature.stderr @@ -1,41 +1,43 @@ error[E0556]: malformed `feature` attribute input - --> $DIR/gated-bad-feature.rs:1:25 + --> $DIR/gated-bad-feature.rs:2:25 | LL | #![feature(foo_bar_baz, foo(bar), foo = "baz", foo)] | ^^^^^^^^ help: expected just one word: `foo` error[E0556]: malformed `feature` attribute input - --> $DIR/gated-bad-feature.rs:1:35 + --> $DIR/gated-bad-feature.rs:2:35 | LL | #![feature(foo_bar_baz, foo(bar), foo = "baz", foo)] | ^^^^^^^^^^^ help: expected just one word: `foo` error[E0557]: feature has been removed - --> $DIR/gated-bad-feature.rs:8:12 + --> $DIR/gated-bad-feature.rs:9:12 | LL | #![feature(test_removed_feature)] | ^^^^^^^^^^^^^^^^^^^^ feature has been removed + | + = note: removed in 1.0.0 (you are using $RUSTC_VERSION) error: malformed `feature` attribute input - --> $DIR/gated-bad-feature.rs:6:1 + --> $DIR/gated-bad-feature.rs:7:1 | LL | #![feature] | ^^^^^^^^^^^ help: must be of the form: `#![feature(name1, name2, ...)]` error: malformed `feature` attribute input - --> $DIR/gated-bad-feature.rs:7:1 + --> $DIR/gated-bad-feature.rs:8:1 | LL | #![feature = "foo"] | ^^^^^^^^^^^^^^^^^^^ help: must be of the form: `#![feature(name1, name2, ...)]` error[E0635]: unknown feature `foo_bar_baz` - --> $DIR/gated-bad-feature.rs:1:12 + --> $DIR/gated-bad-feature.rs:2:12 | LL | #![feature(foo_bar_baz, foo(bar), foo = "baz", foo)] | ^^^^^^^^^^^ error[E0635]: unknown feature `foo` - --> $DIR/gated-bad-feature.rs:1:48 + --> $DIR/gated-bad-feature.rs:2:48 | LL | #![feature(foo_bar_baz, foo(bar), foo = "baz", foo)] | ^^^ diff --git a/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.rs b/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.rs index 02a56c7e6aa6..7fb11b7bde73 100644 --- a/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.rs +++ b/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.rs @@ -11,9 +11,11 @@ #![macro_export] //~^ ERROR: `macro_export` attribute cannot be used at crate level -#![rustc_main] //~ ERROR: the `#[rustc_main]` attribute is used internally to specify +#![rustc_main] //~^ ERROR: `rustc_main` attribute cannot be used at crate level -//~| NOTE: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date +//~| ERROR: use of an internal attribute [E0658] +//~| NOTE: the `#[rustc_main]` attribute is an internal implementation detail that will never be stable +//~| NOTE: the `#[rustc_main]` attribute is used internally to specify test entry point function #![repr()] //~^ ERROR: `repr` attribute cannot be used at crate level #![path = "3800"] diff --git a/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.stderr b/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.stderr index 5c2a3ae699c0..bdca6163473c 100644 --- a/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.stderr +++ b/tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.stderr @@ -1,14 +1,15 @@ -error[E0658]: the `#[rustc_main]` attribute is used internally to specify test entry point function +error[E0658]: use of an internal attribute --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:14:1 | LL | #![rustc_main] | ^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_main]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_main]` attribute is used internally to specify test entry point function error: valid forms for the attribute are `#[inline]` and `#[inline(always|never)]` - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:44:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:46:5 | LL | #[inline = "2100"] fn f() { } | ^^^^^^^^^^^^^^^^^^ @@ -18,7 +19,7 @@ LL | #[inline = "2100"] fn f() { } = note: `#[deny(ill_formed_attribute_input)]` on by default error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:30:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:32:1 | LL | #[inline] | ^^^^^^^^^ @@ -29,7 +30,7 @@ LL | | } | |_- not a function or closure error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:63:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:65:1 | LL | #[no_link] | ^^^^^^^^^^ @@ -43,7 +44,7 @@ LL | | } | |_- not an `extern crate` item error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:89:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:91:1 | LL | #[export_name = "2200"] | ^^^^^^^^^^^^^^^^^^^^^^^ @@ -57,7 +58,7 @@ LL | | } | |_- not a free function, impl method or static error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:123:8 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:125:8 | LL | #[repr(C)] | ^ @@ -70,7 +71,7 @@ LL | | } | |_- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:147:8 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:149:8 | LL | #[repr(Rust)] | ^^^^ @@ -83,19 +84,19 @@ LL | | } | |_- not a struct, enum, or union error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:24:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:26:1 | LL | #![no_link] | ^^^^^^^^^^^ not an `extern crate` item error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:26:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:28:1 | LL | #![export_name = "2200"] | ^^^^^^^^^^^^^^^^^^^^^^^^ not a free function, impl method or static error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:28:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:30:1 | LL | #![inline] | ^^^^^^^^^^ not a function or closure @@ -131,7 +132,7 @@ LL + #[rustc_main] | error: `path` attribute cannot be used at crate level - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:19:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:21:1 | LL | #![path = "3800"] | ^^^^^^^^^^^^^^^^^ @@ -146,7 +147,7 @@ LL + #[path = "3800"] | error: `automatically_derived` attribute cannot be used at crate level - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:21:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:23:1 | LL | #![automatically_derived] | ^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -161,7 +162,7 @@ LL + #[automatically_derived] | error: `repr` attribute cannot be used at crate level - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:17:1 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:19:1 | LL | #![repr()] | ^^^^^^^^^^ @@ -176,139 +177,139 @@ LL + #[repr()] | error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:40:17 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:42:17 | LL | mod inner { #![inline] } | ------------^^^^^^^^^^-- not a function or closure error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:50:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:52:5 | LL | #[inline] struct S; | ^^^^^^^^^ --------- not a function or closure error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:54:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:56:5 | LL | #[inline] type T = S; | ^^^^^^^^^ ----------- not a function or closure error[E0518]: attribute should be applied to function or closure - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:58:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:60:5 | LL | #[inline] impl S { } | ^^^^^^^^^ ---------- not a function or closure error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:68:17 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:70:17 | LL | mod inner { #![no_link] } | ------------^^^^^^^^^^^-- not an `extern crate` item error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:72:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:74:5 | LL | #[no_link] fn f() { } | ^^^^^^^^^^ ---------- not an `extern crate` item error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:76:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:78:5 | LL | #[no_link] struct S; | ^^^^^^^^^^ --------- not an `extern crate` item error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:80:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:82:5 | LL | #[no_link]type T = S; | ^^^^^^^^^^----------- not an `extern crate` item error: attribute should be applied to an `extern crate` item - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:84:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:86:5 | LL | #[no_link] impl S { } | ^^^^^^^^^^ ---------- not an `extern crate` item error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:94:17 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:96:17 | LL | mod inner { #![export_name="2200"] } | ------------^^^^^^^^^^^^^^^^^^^^^^-- not a free function, impl method or static error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:100:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:102:5 | LL | #[export_name = "2200"] struct S; | ^^^^^^^^^^^^^^^^^^^^^^^ --------- not a free function, impl method or static error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:104:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:106:5 | LL | #[export_name = "2200"] type T = S; | ^^^^^^^^^^^^^^^^^^^^^^^ ----------- not a free function, impl method or static error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:108:5 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:110:5 | LL | #[export_name = "2200"] impl S { } | ^^^^^^^^^^^^^^^^^^^^^^^ ---------- not a free function, impl method or static error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:113:9 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:115:9 | LL | #[export_name = "2200"] fn foo(); | ^^^^^^^^^^^^^^^^^^^^^^^ --------- not a free function, impl method or static error: attribute should be applied to a free function, impl method or static - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:117:9 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:119:9 | LL | #[export_name = "2200"] fn bar() {} | ^^^^^^^^^^^^^^^^^^^^^^^ ----------- not a free function, impl method or static error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:127:25 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:129:25 | LL | mod inner { #![repr(C)] } | --------------------^---- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:131:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:133:12 | LL | #[repr(C)] fn f() { } | ^ ---------- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:137:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:139:12 | LL | #[repr(C)] type T = S; | ^ ----------- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:141:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:143:12 | LL | #[repr(C)] impl S { } | ^ ---------- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:151:25 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:153:25 | LL | mod inner { #![repr(Rust)] } | --------------------^^^^---- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:155:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:157:12 | LL | #[repr(Rust)] fn f() { } | ^^^^ ---------- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:161:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:163:12 | LL | #[repr(Rust)] type T = S; | ^^^^ ----------- not a struct, enum, or union error[E0517]: attribute should be applied to a struct, enum, or union - --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:165:12 + --> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:167:12 | LL | #[repr(Rust)] impl S { } | ^^^^ ---------- not a struct, enum, or union diff --git a/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.rs b/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.rs new file mode 100644 index 000000000000..ec6adb471ba5 --- /dev/null +++ b/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.rs @@ -0,0 +1,6 @@ +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" + +#![feature(external_doc)] //~ ERROR feature has been removed +#![doc(include("README.md"))] //~ ERROR unknown `doc` attribute `include` + +fn main(){} diff --git a/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.stderr b/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.stderr new file mode 100644 index 000000000000..43205c7360b2 --- /dev/null +++ b/tests/ui/feature-gates/removed-features-note-version-and-pr-issue-141619.stderr @@ -0,0 +1,20 @@ +error[E0557]: feature has been removed + --> $DIR/removed-features-note-version-and-pr-issue-141619.rs:3:12 + | +LL | #![feature(external_doc)] + | ^^^^^^^^^^^^ feature has been removed + | + = note: removed in 1.54.0 (you are using $RUSTC_VERSION); see for more information + = note: use #[doc = include_str!("filename")] instead, which handles macro invocations + +error: unknown `doc` attribute `include` + --> $DIR/removed-features-note-version-and-pr-issue-141619.rs:4:8 + | +LL | #![doc(include("README.md"))] + | ^^^^^^^^^^^^^^^^^^^^ + | + = note: `#[deny(invalid_doc_attributes)]` on by default + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0557`. diff --git a/tests/ui/format-no-std.rs b/tests/ui/fmt/format-macro-no-std.rs similarity index 81% rename from tests/ui/format-no-std.rs rename to tests/ui/fmt/format-macro-no-std.rs index 657b210a9a0b..d096b4de0139 100644 --- a/tests/ui/format-no-std.rs +++ b/tests/ui/fmt/format-macro-no-std.rs @@ -1,3 +1,5 @@ +//! Test format! macro functionality in no_std environment + //@ run-pass //@ ignore-emscripten no no_std executables //@ ignore-wasm different `main` convention @@ -9,7 +11,8 @@ // Import global allocator and panic handler. extern crate std as other; -#[macro_use] extern crate alloc; +#[macro_use] +extern crate alloc; use alloc::string::ToString; @@ -21,7 +24,7 @@ extern "C" fn main(_argc: core::ffi::c_int, _argv: *const *const u8) -> core::ff let s = format!("test"); assert_eq!(s, "test".to_string()); - let s = format!("{test}", test=3_isize); + let s = format!("{test}", test = 3_isize); assert_eq!(s, "3".to_string()); let s = format!("hello {}", "world"); diff --git a/tests/ui/force-inlining/gate.rs b/tests/ui/force-inlining/gate.rs index cea094c14f2d..5918b0d49790 100644 --- a/tests/ui/force-inlining/gate.rs +++ b/tests/ui/force-inlining/gate.rs @@ -2,11 +2,15 @@ #![allow(internal_features)] #[rustc_force_inline] -//~^ ERROR #[rustc_force_inline] forces a free function to be inlined +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_force_inline]` attribute is an internal implementation detail that will never be stable +//~| NOTE `#[rustc_force_inline]` forces a free function to be inlined pub fn bare() { } #[rustc_force_inline = "the test requires it"] -//~^ ERROR #[rustc_force_inline] forces a free function to be inlined +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_force_inline]` attribute is an internal implementation detail that will never be stable +//~| NOTE `#[rustc_force_inline]` forces a free function to be inlined pub fn justified() { } diff --git a/tests/ui/force-inlining/gate.stderr b/tests/ui/force-inlining/gate.stderr index 964d43fa18f6..6c2df08b1a3f 100644 --- a/tests/ui/force-inlining/gate.stderr +++ b/tests/ui/force-inlining/gate.stderr @@ -1,20 +1,22 @@ -error[E0658]: #[rustc_force_inline] forces a free function to be inlined +error[E0658]: use of an internal attribute --> $DIR/gate.rs:4:1 | LL | #[rustc_force_inline] | ^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_force_inline]` attribute is an internal implementation detail that will never be stable + = note: `#[rustc_force_inline]` forces a free function to be inlined -error[E0658]: #[rustc_force_inline] forces a free function to be inlined - --> $DIR/gate.rs:9:1 +error[E0658]: use of an internal attribute + --> $DIR/gate.rs:11:1 | LL | #[rustc_force_inline = "the test requires it"] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_force_inline]` attribute is an internal implementation detail that will never be stable + = note: `#[rustc_force_inline]` forces a free function to be inlined error: aborting due to 2 previous errors diff --git a/tests/ui/fun-indirect-call.rs b/tests/ui/fun-indirect-call.rs deleted file mode 100644 index 7919be07f7e4..000000000000 --- a/tests/ui/fun-indirect-call.rs +++ /dev/null @@ -1,9 +0,0 @@ -//@ run-pass - -fn f() -> isize { return 42; } - -pub fn main() { - let g: fn() -> isize = f; - let i: isize = g(); - assert_eq!(i, 42); -} diff --git a/tests/ui/future-incompatible-lint-group.rs b/tests/ui/future-incompatible-lint-group.rs deleted file mode 100644 index ed2c47bb6090..000000000000 --- a/tests/ui/future-incompatible-lint-group.rs +++ /dev/null @@ -1,15 +0,0 @@ -// Ensure that the future_incompatible lint group only includes -// lints for changes that are not tied to an edition -#![deny(future_incompatible)] - -// Error since this is a `future_incompatible` lint -macro_rules! m { ($i) => {} } //~ ERROR missing fragment specifier - //~| WARN this was previously accepted - -trait Tr { - // Warn only since this is not a `future_incompatible` lint - fn f(u8) {} //~ WARN anonymous parameters are deprecated - //~| WARN this is accepted in the current edition -} - -fn main() {} diff --git a/tests/ui/future-incompatible-lint-group.stderr b/tests/ui/future-incompatible-lint-group.stderr deleted file mode 100644 index 4c867e0aab3c..000000000000 --- a/tests/ui/future-incompatible-lint-group.stderr +++ /dev/null @@ -1,43 +0,0 @@ -error: missing fragment specifier - --> $DIR/future-incompatible-lint-group.rs:6:19 - | -LL | macro_rules! m { ($i) => {} } - | ^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/future-incompatible-lint-group.rs:3:9 - | -LL | #![deny(future_incompatible)] - | ^^^^^^^^^^^^^^^^^^^ - = note: `#[deny(missing_fragment_specifier)]` implied by `#[deny(future_incompatible)]` - -warning: anonymous parameters are deprecated and will be removed in the next edition - --> $DIR/future-incompatible-lint-group.rs:11:10 - | -LL | fn f(u8) {} - | ^^ help: try naming the parameter or explicitly ignoring it: `_: u8` - | - = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! - = note: for more information, see issue #41686 - = note: `#[warn(anonymous_parameters)]` on by default - -error: aborting due to 1 previous error; 1 warning emitted - -Future incompatibility report: Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/future-incompatible-lint-group.rs:6:19 - | -LL | macro_rules! m { ($i) => {} } - | ^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/future-incompatible-lint-group.rs:3:9 - | -LL | #![deny(future_incompatible)] - | ^^^^^^^^^^^^^^^^^^^ - = note: `#[deny(missing_fragment_specifier)]` implied by `#[deny(future_incompatible)]` - diff --git a/tests/ui/generics/empty-generic-brackets-equiv.rs b/tests/ui/generics/empty-generic-brackets-equiv.rs new file mode 100644 index 000000000000..d84498a60f80 --- /dev/null +++ b/tests/ui/generics/empty-generic-brackets-equiv.rs @@ -0,0 +1,27 @@ +//! Test that empty type parameter list <> is equivalent to no type parameters +//! +//! Checks` that empty angle brackets <> are syntactically valid and equivalent +//! to omitting type parameters entirely across various language constructs. + +//@ run-pass + +struct S<>; +trait T<> {} //~ WARN trait `T` is never used +enum E<> { + V +} +impl<> T<> for S<> {} +impl T for E {} +fn foo<>() {} +fn bar() {} +fn main() { + let _ = S; + let _ = S::<>; + let _ = E::V; + let _ = E::<>::V; + foo(); + foo::<>(); + // Test that we can supply <> to non-generic things + bar::<>(); + let _: i32<>; +} diff --git a/tests/ui/empty-type-parameter-list.stderr b/tests/ui/generics/empty-generic-brackets-equiv.stderr similarity index 76% rename from tests/ui/empty-type-parameter-list.stderr rename to tests/ui/generics/empty-generic-brackets-equiv.stderr index 31a5015e9934..151ee4697b4c 100644 --- a/tests/ui/empty-type-parameter-list.stderr +++ b/tests/ui/generics/empty-generic-brackets-equiv.stderr @@ -1,5 +1,5 @@ warning: trait `T` is never used - --> $DIR/empty-type-parameter-list.rs:6:7 + --> $DIR/empty-generic-brackets-equiv.rs:9:7 | LL | trait T<> {} | ^ diff --git a/tests/ui/global-scope.rs b/tests/ui/global-scope.rs deleted file mode 100644 index 33b56bca940a..000000000000 --- a/tests/ui/global-scope.rs +++ /dev/null @@ -1,13 +0,0 @@ -//@ run-pass - -pub fn f() -> isize { return 1; } - -pub mod foo { - pub fn f() -> isize { return 2; } - pub fn g() { - assert_eq!(f(), 2); - assert_eq!(::f(), 1); - } -} - -pub fn main() { return foo::g(); } diff --git a/tests/ui/hello.rs b/tests/ui/hello.rs deleted file mode 100644 index f329ee086f90..000000000000 --- a/tests/ui/hello.rs +++ /dev/null @@ -1,10 +0,0 @@ -//@ run-pass -//@ revisions: e2015 e2018 e2021 e2024 - -//@[e2018] edition:2018 -//@[e2021] edition:2021 -//@[e2024] edition:2024 - -fn main() { - println!("hello"); -} diff --git a/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr b/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr index 54ceec0aff5d..5caf0eb2fd4e 100644 --- a/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr +++ b/tests/ui/impl-trait/auto-trait-selection-freeze.next.stderr @@ -1,9 +1,22 @@ -error[E0284]: type annotations needed: cannot satisfy `impl Sized == _` - --> $DIR/auto-trait-selection-freeze.rs:19:5 +error[E0283]: type annotations needed + --> $DIR/auto-trait-selection-freeze.rs:19:16 | LL | if false { is_trait(foo()) } else { Default::default() } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot satisfy `impl Sized == _` + | ^^^^^^^^ ----- type must be known at this point + | | + | cannot infer type of the type parameter `T` declared on the function `is_trait` + | + = note: cannot satisfy `_: Trait<_>` +note: required by a bound in `is_trait` + --> $DIR/auto-trait-selection-freeze.rs:11:16 + | +LL | fn is_trait, U: Default>(_: T) -> U { + | ^^^^^^^^ required by this bound in `is_trait` +help: consider specifying the generic arguments + | +LL | if false { is_trait::(foo()) } else { Default::default() } + | ++++++++ error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0283`. diff --git a/tests/ui/impl-trait/auto-trait-selection.next.stderr b/tests/ui/impl-trait/auto-trait-selection.next.stderr index 7acb9fd41b73..d34fdcc44967 100644 --- a/tests/ui/impl-trait/auto-trait-selection.next.stderr +++ b/tests/ui/impl-trait/auto-trait-selection.next.stderr @@ -1,9 +1,22 @@ -error[E0284]: type annotations needed: cannot satisfy `impl Sized == _` - --> $DIR/auto-trait-selection.rs:15:5 +error[E0283]: type annotations needed + --> $DIR/auto-trait-selection.rs:15:16 | LL | if false { is_trait(foo()) } else { Default::default() } - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot satisfy `impl Sized == _` + | ^^^^^^^^ ----- type must be known at this point + | | + | cannot infer type of the type parameter `T` declared on the function `is_trait` + | + = note: cannot satisfy `_: Trait<_>` +note: required by a bound in `is_trait` + --> $DIR/auto-trait-selection.rs:7:16 + | +LL | fn is_trait, U: Default>(_: T) -> U { + | ^^^^^^^^ required by this bound in `is_trait` +help: consider specifying the generic arguments + | +LL | if false { is_trait::(foo()) } else { Default::default() } + | ++++++++ error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0283`. diff --git a/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.next.stderr b/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.next.stderr index 9632d2ce6249..f2e249f2cbf9 100644 --- a/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.next.stderr +++ b/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.next.stderr @@ -25,7 +25,7 @@ LL | type LineStream<'c, 'd> = impl Stream; | = note: `LineStream` must be used in combination with a concrete type within the same impl -error[E0271]: type mismatch resolving `::LineStreamFut<'a, Repr> == ()` +error[E0271]: type mismatch resolving `::LineStreamFut<'a, Repr> normalizes-to ()` --> $DIR/ice-unexpected-param-type-whensubstituting-in-region-112823.rs:29:43 | LL | fn line_stream<'a, Repr>(&'a self) -> Self::LineStreamFut<'a, Repr> {} diff --git a/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.rs b/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.rs index 0b507ed948ae..7cf155ce01ef 100644 --- a/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.rs +++ b/tests/ui/impl-trait/ice-unexpected-param-type-whensubstituting-in-region-112823.rs @@ -29,7 +29,7 @@ impl X for Y { fn line_stream<'a, Repr>(&'a self) -> Self::LineStreamFut<'a, Repr> {} //~^ ERROR method `line_stream` is not a member of trait `X` //[current]~^^ ERROR `()` is not a future - //[next]~^^^ ERROR type mismatch resolving `::LineStreamFut<'a, Repr> == ()` + //[next]~^^^ ERROR type mismatch resolving `::LineStreamFut<'a, Repr> normalizes-to ()` //[next]~| ERROR type mismatch resolving `::LineStreamFut<'a, Repr> normalizes-to _` //[next]~| ERROR type mismatch resolving `::LineStreamFut<'a, Repr> normalizes-to _` } diff --git a/tests/ui/impl-trait/must_outlive_least_region_or_bound.stderr b/tests/ui/impl-trait/must_outlive_least_region_or_bound.stderr index ba7d7770e503..53c556866041 100644 --- a/tests/ui/impl-trait/must_outlive_least_region_or_bound.stderr +++ b/tests/ui/impl-trait/must_outlive_least_region_or_bound.stderr @@ -65,9 +65,12 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/must_outlive_least_region_or_bound.rs:15:41 | LL | fn foo<'a>(x: &i32) -> impl Copy + 'a { x } - | ---- ^ lifetime `'a` required - | | - | help: add explicit lifetime `'a` to the type of `x`: `&'a i32` + | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo<'a>(x: &'a i32) -> impl Copy + 'a { x } + | ++ error: lifetime may not live long enough --> $DIR/must_outlive_least_region_or_bound.rs:30:55 diff --git a/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr b/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr index 132f7de4ef23..5ce6eb0fc398 100644 --- a/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr +++ b/tests/ui/impl-trait/recursive-coroutine-boxed.next.stderr @@ -1,5 +1,5 @@ error[E0282]: type annotations needed - --> $DIR/recursive-coroutine-boxed.rs:14:23 + --> $DIR/recursive-coroutine-boxed.rs:11:23 | LL | let mut gen = Box::pin(foo()); | ^^^^^^^^ cannot infer type of the type parameter `T` declared on the struct `Box` diff --git a/tests/ui/impl-trait/recursive-coroutine-boxed.rs b/tests/ui/impl-trait/recursive-coroutine-boxed.rs index 8d38e6aed124..306edc3591e9 100644 --- a/tests/ui/impl-trait/recursive-coroutine-boxed.rs +++ b/tests/ui/impl-trait/recursive-coroutine-boxed.rs @@ -7,9 +7,6 @@ use std::ops::{Coroutine, CoroutineState}; fn foo() -> impl Coroutine { - // FIXME(-Znext-solver): this fails with a mismatched types as the - // hidden type of the opaque ends up as {type error}. We should not - // emit errors for such goals. #[coroutine] || { let mut gen = Box::pin(foo()); //[next]~^ ERROR type annotations needed diff --git a/tests/ui/impl-trait/recursive-in-exhaustiveness.next.stderr b/tests/ui/impl-trait/recursive-in-exhaustiveness.next.stderr index a3609b93cb3a..db57be73acce 100644 --- a/tests/ui/impl-trait/recursive-in-exhaustiveness.next.stderr +++ b/tests/ui/impl-trait/recursive-in-exhaustiveness.next.stderr @@ -1,8 +1,8 @@ -error[E0284]: type annotations needed: cannot satisfy `impl Sized == _` - --> $DIR/recursive-in-exhaustiveness.rs:19:17 +error[E0284]: type annotations needed: cannot normalize `build<_>::{opaque#0}` + --> $DIR/recursive-in-exhaustiveness.rs:20:5 | -LL | let (x,) = (build(x),); - | ^^^^^^^^ cannot satisfy `impl Sized == _` +LL | build(x) + | ^^^^^^^^ cannot normalize `build<_>::{opaque#0}` error[E0271]: type mismatch resolving `build2<(_,)>::{opaque#0} normalizes-to _` --> $DIR/recursive-in-exhaustiveness.rs:30:6 diff --git a/tests/ui/impl-trait/recursive-in-exhaustiveness.rs b/tests/ui/impl-trait/recursive-in-exhaustiveness.rs index fa8fa0e81743..dabef22af868 100644 --- a/tests/ui/impl-trait/recursive-in-exhaustiveness.rs +++ b/tests/ui/impl-trait/recursive-in-exhaustiveness.rs @@ -17,8 +17,8 @@ fn build(x: T) -> impl Sized { //[current]~^ ERROR cannot resolve opaque type let (x,) = (build(x),); - //[next]~^ ERROR type annotations needed build(x) + //[next]~^ ERROR type annotations needed: cannot normalize `build<_>::{opaque#0}` } // Opaque = (Opaque,) diff --git a/tests/ui/impl-trait/two_tait_defining_each_other2.next.stderr b/tests/ui/impl-trait/two_tait_defining_each_other2.next.stderr index 1a4c0f5f7eef..fac4776905d0 100644 --- a/tests/ui/impl-trait/two_tait_defining_each_other2.next.stderr +++ b/tests/ui/impl-trait/two_tait_defining_each_other2.next.stderr @@ -1,9 +1,9 @@ -error[E0284]: type annotations needed: cannot satisfy `_ == A` - --> $DIR/two_tait_defining_each_other2.rs:12:8 +error[E0282]: type annotations needed + --> $DIR/two_tait_defining_each_other2.rs:12:11 | LL | fn muh(x: A) -> B { - | ^ cannot satisfy `_ == A` + | ^ cannot infer type error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0282`. diff --git a/tests/ui/impl-trait/two_tait_defining_each_other2.rs b/tests/ui/impl-trait/two_tait_defining_each_other2.rs index 6c454bba5023..ec2963249f9d 100644 --- a/tests/ui/impl-trait/two_tait_defining_each_other2.rs +++ b/tests/ui/impl-trait/two_tait_defining_each_other2.rs @@ -10,7 +10,7 @@ trait Foo {} #[define_opaque(A, B)] fn muh(x: A) -> B { - //[next]~^ ERROR: cannot satisfy `_ == A` + //[next]~^ ERROR: type annotations needed x // B's hidden type is A (opaquely) //[current]~^ ERROR opaque type's hidden type cannot be another opaque type } diff --git a/tests/ui/include-macros/parent_dir.rs b/tests/ui/include-macros/parent_dir.rs index 1dcf27324d1f..9a81a6deeb12 100644 --- a/tests/ui/include-macros/parent_dir.rs +++ b/tests/ui/include-macros/parent_dir.rs @@ -3,8 +3,6 @@ fn main() { let _ = include_str!("include-macros/file.txt"); //~ ERROR couldn't read //~^HELP different directory - let _ = include_str!("hello.rs"); //~ ERROR couldn't read - //~^HELP different directory let _ = include_bytes!("../../data.bin"); //~ ERROR couldn't read //~^HELP different directory let _ = include_str!("tests/ui/include-macros/file.txt"); //~ ERROR couldn't read diff --git a/tests/ui/include-macros/parent_dir.stderr b/tests/ui/include-macros/parent_dir.stderr index 4ee6fe104b06..7a18b1de5d16 100644 --- a/tests/ui/include-macros/parent_dir.stderr +++ b/tests/ui/include-macros/parent_dir.stderr @@ -10,19 +10,8 @@ LL - let _ = include_str!("include-macros/file.txt"); LL + let _ = include_str!("file.txt"); | -error: couldn't read `$DIR/hello.rs`: $FILE_NOT_FOUND_MSG - --> $DIR/parent_dir.rs:6:13 - | -LL | let _ = include_str!("hello.rs"); - | ^^^^^^^^^^^^^^^^^^^^^^^^ - | -help: there is a file with the same name in a different directory - | -LL | let _ = include_str!("../hello.rs"); - | +++ - error: couldn't read `$DIR/../../data.bin`: $FILE_NOT_FOUND_MSG - --> $DIR/parent_dir.rs:8:13 + --> $DIR/parent_dir.rs:6:13 | LL | let _ = include_bytes!("../../data.bin"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -34,7 +23,7 @@ LL + let _ = include_bytes!("data.bin"); | error: couldn't read `$DIR/tests/ui/include-macros/file.txt`: $FILE_NOT_FOUND_MSG - --> $DIR/parent_dir.rs:10:13 + --> $DIR/parent_dir.rs:8:13 | LL | let _ = include_str!("tests/ui/include-macros/file.txt"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -45,5 +34,5 @@ LL - let _ = include_str!("tests/ui/include-macros/file.txt"); LL + let _ = include_str!("file.txt"); | -error: aborting due to 4 previous errors +error: aborting due to 3 previous errors diff --git a/tests/ui/inline-const/break-inside-inline-const-issue-128604.rs b/tests/ui/inline-const/break-inside-inline-const-issue-128604.rs index a9795d1569c8..cc0d757885de 100644 --- a/tests/ui/inline-const/break-inside-inline-const-issue-128604.rs +++ b/tests/ui/inline-const/break-inside-inline-const-issue-128604.rs @@ -23,3 +23,9 @@ fn main() { } } } + +const FOO: () = break; +//~^ ERROR: `break` outside of a loop or labeled block + +static BAR: () = break; +//~^ ERROR: `break` outside of a loop or labeled block diff --git a/tests/ui/inline-const/break-inside-inline-const-issue-128604.stderr b/tests/ui/inline-const/break-inside-inline-const-issue-128604.stderr index 300cd45ad691..6a967c598642 100644 --- a/tests/ui/inline-const/break-inside-inline-const-issue-128604.stderr +++ b/tests/ui/inline-const/break-inside-inline-const-issue-128604.stderr @@ -10,17 +10,6 @@ error[E0268]: `break` outside of a loop or labeled block LL | break; | ^^^^^ cannot `break` outside of a loop or labeled block -error[E0268]: `break` outside of a loop or labeled block - --> $DIR/break-inside-inline-const-issue-128604.rs:2:21 - | -LL | let _ = ['a'; { break 2; 1 }]; - | ^^^^^^^ cannot `break` outside of a loop or labeled block - | -help: consider labeling this block to be able to break within it - | -LL | let _ = ['a'; 'block: { break 'block 2; 1 }]; - | +++++++ ++++++ - error[E0268]: `break` outside of a loop or labeled block --> $DIR/break-inside-inline-const-issue-128604.rs:9:13 | @@ -34,6 +23,29 @@ LL | LL ~ break 'block; | -error: aborting due to 4 previous errors +error[E0268]: `break` outside of a loop or labeled block + --> $DIR/break-inside-inline-const-issue-128604.rs:2:21 + | +LL | let _ = ['a'; { break 2; 1 }]; + | ^^^^^^^ cannot `break` outside of a loop or labeled block + | +help: consider labeling this block to be able to break within it + | +LL | let _ = ['a'; 'block: { break 'block 2; 1 }]; + | +++++++ ++++++ + +error[E0268]: `break` outside of a loop or labeled block + --> $DIR/break-inside-inline-const-issue-128604.rs:27:17 + | +LL | const FOO: () = break; + | ^^^^^ cannot `break` outside of a loop or labeled block + +error[E0268]: `break` outside of a loop or labeled block + --> $DIR/break-inside-inline-const-issue-128604.rs:30:18 + | +LL | static BAR: () = break; + | ^^^^^ cannot `break` outside of a loop or labeled block + +error: aborting due to 6 previous errors For more information about this error, try `rustc --explain E0268`. diff --git a/tests/ui/inline-const/cross-const-control-flow-125846.stderr b/tests/ui/inline-const/cross-const-control-flow-125846.stderr index 0a910e70d09e..5ea571fe98a7 100644 --- a/tests/ui/inline-const/cross-const-control-flow-125846.stderr +++ b/tests/ui/inline-const/cross-const-control-flow-125846.stderr @@ -39,6 +39,16 @@ LL | const { async {}.await } | | only allowed inside `async` functions and blocks | this is not `async` +error[E0572]: return statement outside of function body + --> $DIR/cross-const-control-flow-125846.rs:4:13 + | +LL | / fn foo() { +LL | | const { return } + | | --^^^^^^-- the return is part of this body... +LL | | +LL | | } + | |_- ...not the enclosing function body + error[E0268]: `break` outside of a loop or labeled block --> $DIR/cross-const-control-flow-125846.rs:9:19 | @@ -63,16 +73,6 @@ error[E0268]: `continue` outside of a loop LL | const { continue } | ^^^^^^^^ cannot `continue` outside of a loop -error[E0572]: return statement outside of function body - --> $DIR/cross-const-control-flow-125846.rs:4:13 - | -LL | / fn foo() { -LL | | const { return } - | | --^^^^^^-- the return is part of this body... -LL | | -LL | | } - | |_- ...not the enclosing function body - error: aborting due to 9 previous errors Some errors have detailed explanations: E0268, E0435, E0572, E0728, E0767. diff --git a/tests/ui/intrinsics/intrinsic-alignment.rs b/tests/ui/intrinsics/intrinsic-alignment.rs index 30a523f364c7..904da71c306b 100644 --- a/tests/ui/intrinsics/intrinsic-alignment.rs +++ b/tests/ui/intrinsics/intrinsic-alignment.rs @@ -23,12 +23,12 @@ use std::intrinsics as rusti; mod m { #[cfg(target_arch = "x86")] pub fn main() { - assert_eq!(crate::rusti::min_align_of::(), 4); + assert_eq!(crate::rusti::align_of::(), 4); } #[cfg(not(target_arch = "x86"))] pub fn main() { - assert_eq!(crate::rusti::min_align_of::(), 8); + assert_eq!(crate::rusti::align_of::(), 8); } } @@ -36,21 +36,21 @@ mod m { mod m { #[cfg(target_arch = "x86_64")] pub fn main() { - assert_eq!(crate::rusti::min_align_of::(), 8); + assert_eq!(crate::rusti::align_of::(), 8); } } #[cfg(target_os = "windows")] mod m { pub fn main() { - assert_eq!(crate::rusti::min_align_of::(), 8); + assert_eq!(crate::rusti::align_of::(), 8); } } #[cfg(target_family = "wasm")] mod m { pub fn main() { - assert_eq!(crate::rusti::min_align_of::(), 8); + assert_eq!(crate::rusti::align_of::(), 8); } } diff --git a/tests/ui/invalid/invalid-rustc_legacy_const_generics-issue-123077.stderr b/tests/ui/invalid/invalid-rustc_legacy_const_generics-issue-123077.stderr index d92836aa063b..8d120ae98d90 100644 --- a/tests/ui/invalid/invalid-rustc_legacy_const_generics-issue-123077.stderr +++ b/tests/ui/invalid/invalid-rustc_legacy_const_generics-issue-123077.stderr @@ -19,7 +19,7 @@ LL | std::arch::x86_64::_mm_blend_ps(loop {}, loop {}, 5 + || ()); help: try using a const generic argument instead | LL - std::arch::x86_64::_mm_blend_ps(loop {}, loop {}, 5 + || ()); -LL + std::arch::x86_64::_mm_blend_ps::<{ 5 + (|| ()) }>(loop {}, loop {}); +LL + std::arch::x86_64::_mm_blend_ps::<{ 5 + || () }>(loop {}, loop {}); | error: invalid argument to a legacy const generic: cannot have const blocks, closures, async blocks or items @@ -81,7 +81,7 @@ LL | std::arch::x86_64::_mm_inserti_si64(loop {}, loop {}, || (), 1 + || ()) help: try using a const generic argument instead | LL - std::arch::x86_64::_mm_inserti_si64(loop {}, loop {}, || (), 1 + || ()); -LL + std::arch::x86_64::_mm_inserti_si64::<{ || () }, { 1 + (|| ()) }>(loop {}, loop {}); +LL + std::arch::x86_64::_mm_inserti_si64::<{ || () }, { 1 + || () }>(loop {}, loop {}); | error: aborting due to 7 previous errors diff --git a/tests/ui/issues/issue-13058.stderr b/tests/ui/issues/issue-13058.stderr index 7cc2860eb508..4f4108fa1825 100644 --- a/tests/ui/issues/issue-13058.stderr +++ b/tests/ui/issues/issue-13058.stderr @@ -1,11 +1,13 @@ error[E0621]: explicit lifetime required in the type of `cont` --> $DIR/issue-13058.rs:14:21 | -LL | fn check<'r, I: Iterator, T: Itble<'r, usize, I>>(cont: &T) -> bool - | -- help: add explicit lifetime `'r` to the type of `cont`: `&'r T` -LL | { LL | let cont_iter = cont.iter(); | ^^^^^^^^^^^ lifetime `'r` required + | +help: add explicit lifetime `'r` to the type of `cont` + | +LL | fn check<'r, I: Iterator, T: Itble<'r, usize, I>>(cont: &'r T) -> bool + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/issues/issue-14285.stderr b/tests/ui/issues/issue-14285.stderr index 4f89ae51157b..edd139eecba4 100644 --- a/tests/ui/issues/issue-14285.stderr +++ b/tests/ui/issues/issue-14285.stderr @@ -1,10 +1,14 @@ error[E0621]: explicit lifetime required in the type of `a` --> $DIR/issue-14285.rs:12:5 | -LL | fn foo<'a>(a: &dyn Foo) -> B<'a> { - | -------- help: add explicit lifetime `'a` to the type of `a`: `&'a (dyn Foo + 'a)` LL | B(a) | ^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `a` + | +LL - fn foo<'a>(a: &dyn Foo) -> B<'a> { +LL + fn foo<'a>(a: &'a (dyn Foo + 'a)) -> B<'a> { + | error: aborting due to 1 previous error diff --git a/tests/ui/issues/issue-15034.stderr b/tests/ui/issues/issue-15034.stderr index 587a5c85e924..7db8ade2e482 100644 --- a/tests/ui/issues/issue-15034.stderr +++ b/tests/ui/issues/issue-15034.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `lexer` --> $DIR/issue-15034.rs:17:9 | -LL | pub fn new(lexer: &'a mut Lexer) -> Parser<'a> { - | ------------- help: add explicit lifetime `'a` to the type of `lexer`: `&'a mut Lexer<'a>` LL | Parser { lexer: lexer } | ^^^^^^^^^^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `lexer` + | +LL | pub fn new(lexer: &'a mut Lexer<'a>) -> Parser<'a> { + | ++++ error: aborting due to 1 previous error diff --git a/tests/ui/issues/issue-28561.rs b/tests/ui/issues/issue-28561.rs index f9b0ceb22fc6..642b2193a4f9 100644 --- a/tests/ui/issues/issue-28561.rs +++ b/tests/ui/issues/issue-28561.rs @@ -37,6 +37,7 @@ struct Array { } #[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +#[allow(unpredictable_function_pointer_comparisons)] struct Fn { f00: fn(), f01: fn(A), diff --git a/tests/ui/issues/issue-3154.stderr b/tests/ui/issues/issue-3154.stderr index 3106aaddc4a1..c17e59f7fc3d 100644 --- a/tests/ui/issues/issue-3154.stderr +++ b/tests/ui/issues/issue-3154.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/issue-3154.rs:6:5 | -LL | fn thing<'a,Q>(x: &Q) -> Thing<'a,Q> { - | -- help: add explicit lifetime `'a` to the type of `x`: `&'a Q` LL | Thing { x: x } | ^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn thing<'a,Q>(x: &'a Q) -> Thing<'a,Q> { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/issues/issue-40288-2.stderr b/tests/ui/issues/issue-40288-2.stderr index 2c64856b08f8..81cb7cdd51ff 100644 --- a/tests/ui/issues/issue-40288-2.stderr +++ b/tests/ui/issues/issue-40288-2.stderr @@ -1,20 +1,24 @@ error[E0621]: explicit lifetime required in the type of `y` --> $DIR/issue-40288-2.rs:9:5 | -LL | fn lifetime_transmute_slice<'a, T: ?Sized>(x: &'a T, y: &T) -> &'a T { - | -- help: add explicit lifetime `'a` to the type of `y`: `&'a T` -... LL | out[0] | ^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `y` + | +LL | fn lifetime_transmute_slice<'a, T: ?Sized>(x: &'a T, y: &'a T) -> &'a T { + | ++ error[E0621]: explicit lifetime required in the type of `y` --> $DIR/issue-40288-2.rs:24:5 | -LL | fn lifetime_transmute_struct<'a, T: ?Sized>(x: &'a T, y: &T) -> &'a T { - | -- help: add explicit lifetime `'a` to the type of `y`: `&'a T` -... LL | out.head | ^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `y` + | +LL | fn lifetime_transmute_struct<'a, T: ?Sized>(x: &'a T, y: &'a T) -> &'a T { + | ++ error: aborting due to 2 previous errors diff --git a/tests/ui/layout/invalid-unsized-in-always-sized-tail.stderr b/tests/ui/layout/invalid-unsized-in-always-sized-tail.stderr index 1a43fd4ad181..5f6a6099ba23 100644 --- a/tests/ui/layout/invalid-unsized-in-always-sized-tail.stderr +++ b/tests/ui/layout/invalid-unsized-in-always-sized-tail.stderr @@ -24,7 +24,7 @@ error[E0080]: the type `MySlice<[bool]>` has an unknown layout LL | static CHECK: () = assert!(align_of::() == 1); | ^^^^^^^^^^^^^^^^ evaluation of `CHECK` failed inside this call | -note: inside `align_of::` +note: inside `std::mem::align_of::` --> $SRC_DIR/core/src/mem/mod.rs:LL:COL error: aborting due to 2 previous errors diff --git a/tests/ui/lifetimes/lifetime-errors/42701_one_named_and_one_anonymous.stderr b/tests/ui/lifetimes/lifetime-errors/42701_one_named_and_one_anonymous.stderr index af22078aff59..c524aabfacb8 100644 --- a/tests/ui/lifetimes/lifetime-errors/42701_one_named_and_one_anonymous.stderr +++ b/tests/ui/lifetimes/lifetime-errors/42701_one_named_and_one_anonymous.stderr @@ -1,11 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/42701_one_named_and_one_anonymous.rs:10:9 | -LL | fn foo2<'a>(a: &'a Foo, x: &i32) -> &'a i32 { - | ---- help: add explicit lifetime `'a` to the type of `x`: `&'a i32` -... LL | &*x | ^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo2<'a>(a: &'a Foo, x: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-early-bound-in-struct.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-early-bound-in-struct.stderr index e202c31214d3..44a542eeeeb6 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-early-bound-in-struct.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-early-bound-in-struct.stderr @@ -1,11 +1,13 @@ error[E0621]: explicit lifetime required in the type of `other` --> $DIR/ex1-return-one-existing-name-early-bound-in-struct.rs:11:21 | -LL | fn bar(&self, other: Foo) -> Foo<'a> { - | --- help: add explicit lifetime `'a` to the type of `other`: `Foo<'a>` -... LL | other | ^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `other` + | +LL | fn bar(&self, other: Foo<'a>) -> Foo<'a> { + | ++++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-2.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-2.stderr index 5518ded0106d..52cf8595448d 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-2.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-2.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/ex1-return-one-existing-name-if-else-2.rs:2:16 | -LL | fn foo<'a>(x: &i32, y: &'a i32) -> &'a i32 { - | ---- help: add explicit lifetime `'a` to the type of `x`: `&'a i32` LL | if x > y { x } else { y } | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo<'a>(x: &'a i32, y: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-3.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-3.stderr index c689fa9884a7..fbd9695e85fa 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-3.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-3.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in parameter type --> $DIR/ex1-return-one-existing-name-if-else-3.rs:2:27 | -LL | fn foo<'a>((x, y): (&'a i32, &i32)) -> &'a i32 { - | --------------- help: add explicit lifetime `'a` to type: `(&'a i32, &'a i32)` LL | if x > y { x } else { y } | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to type + | +LL | fn foo<'a>((x, y): (&'a i32, &'a i32)) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-2.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-2.stderr index 3da50cfbb1d0..c875381c615f 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-2.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-2.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/ex1-return-one-existing-name-if-else-using-impl-2.rs:4:15 | -LL | fn foo<'a>(x: &i32, y: &'a i32) -> &'a i32 { - | ---- help: add explicit lifetime `'a` to the type of `x`: `&'a i32` LL | if x > y { x } else { y } | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo<'a>(x: &'a i32, y: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-3.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-3.stderr index 071bda24ef8d..83cd11baf391 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-3.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else-using-impl-3.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/ex1-return-one-existing-name-if-else-using-impl-3.rs:7:36 | -LL | fn foo<'a>(&'a self, x: &i32) -> &i32 { - | ---- help: add explicit lifetime `'a` to the type of `x`: `&'a i32` LL | if true { &self.field } else { x } | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo<'a>(&'a self, x: &'a i32) -> &i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else.stderr b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else.stderr index 1df0776a51b5..bf09bd26359c 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex1-return-one-existing-name-if-else.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `y` --> $DIR/ex1-return-one-existing-name-if-else.rs:2:27 | -LL | fn foo<'a>(x: &'a i32, y: &i32) -> &'a i32 { - | ---- help: add explicit lifetime `'a` to the type of `y`: `&'a i32` LL | if x > y { x } else { y } | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `y` + | +LL | fn foo<'a>(x: &'a i32, y: &'a i32) -> &'a i32 { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-2.stderr b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-2.stderr index 25a2f4b96f40..f37e1ba00e7e 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-2.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-2.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `x` --> $DIR/ex2a-push-one-existing-name-2.rs:6:5 | -LL | fn foo<'a>(x: Ref, y: &mut Vec>) { - | -------- help: add explicit lifetime `'a` to the type of `x`: `Ref<'a, i32>` LL | y.push(x); | ^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `x` + | +LL | fn foo<'a>(x: Ref<'a, i32>, y: &mut Vec>) { + | +++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-early-bound.stderr b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-early-bound.stderr index e2725977d837..c25b4c9921f8 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-early-bound.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name-early-bound.stderr @@ -1,11 +1,13 @@ error[E0621]: explicit lifetime required in the type of `y` --> $DIR/ex2a-push-one-existing-name-early-bound.rs:8:5 | -LL | fn baz<'a, 'b, T>(x: &mut Vec<&'a T>, y: &T) - | -- help: add explicit lifetime `'a` to the type of `y`: `&'a T` -... LL | x.push(y); | ^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `y` + | +LL | fn baz<'a, 'b, T>(x: &mut Vec<&'a T>, y: &'a T) + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name.stderr b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name.stderr index 1025581d5acf..8c7bee4bfc40 100644 --- a/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name.stderr +++ b/tests/ui/lifetimes/lifetime-errors/ex2a-push-one-existing-name.stderr @@ -1,10 +1,13 @@ error[E0621]: explicit lifetime required in the type of `y` --> $DIR/ex2a-push-one-existing-name.rs:6:5 | -LL | fn foo<'a>(x: &mut Vec>, y: Ref) { - | -------- help: add explicit lifetime `'a` to the type of `y`: `Ref<'a, i32>` LL | x.push(y); | ^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `y` + | +LL | fn foo<'a>(x: &mut Vec>, y: Ref<'a, i32>) { + | +++ error: aborting due to 1 previous error diff --git a/tests/ui/lifetimes/noisy-follow-up-erro.stderr b/tests/ui/lifetimes/noisy-follow-up-erro.stderr index 04863badbd1e..eb52147dba4b 100644 --- a/tests/ui/lifetimes/noisy-follow-up-erro.stderr +++ b/tests/ui/lifetimes/noisy-follow-up-erro.stderr @@ -15,11 +15,14 @@ LL | struct Foo<'c, 'd>(&'c (), &'d ()); error[E0621]: explicit lifetime required in the type of `foo` --> $DIR/noisy-follow-up-erro.rs:14:9 | -LL | fn boom(&self, foo: &mut Foo<'_, '_, 'a>) -> Result<(), &'a ()> { - | -------------------- help: add explicit lifetime `'a` to the type of `foo`: `&mut Foo<'_, 'a>` -LL | LL | self.bar().map_err(|()| foo.acc(self))?; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `foo` + | +LL - fn boom(&self, foo: &mut Foo<'_, '_, 'a>) -> Result<(), &'a ()> { +LL + fn boom(&self, foo: &mut Foo<'_, 'a>) -> Result<(), &'a ()> { + | error: aborting due to 2 previous errors diff --git a/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.rs b/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.rs index df69782e154d..9babc20d1a15 100644 --- a/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.rs +++ b/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.rs @@ -1,6 +1,14 @@ -//@ only-x86_64 -//@ only-windows +//@ add-core-stubs +//@ compile-flags: --target x86_64-pc-windows-msvc //@ compile-flags: --crate-type lib --emit link +//@ needs-llvm-components: x86 +#![no_core] +#![feature(no_core)] +extern crate minicore; + +// It may seem weird this is a cross-platform-testable thing, since doesn't it test linkage? +// However the main thing we are testing is an *error*, so it works fine! + #[link(name = "foo", kind = "raw-dylib")] extern "stdcall" { //~^ WARN: calling convention not supported on this target diff --git a/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.stderr b/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.stderr index e7a32f4c84b5..95ea90804867 100644 --- a/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.stderr +++ b/tests/ui/linkage-attr/raw-dylib/windows/unsupported-abi.stderr @@ -1,5 +1,5 @@ warning: use of calling convention not supported on this target - --> $DIR/unsupported-abi.rs:5:1 + --> $DIR/unsupported-abi.rs:13:1 | LL | / extern "stdcall" { LL | | @@ -15,27 +15,10 @@ LL | | } = note: `#[warn(unsupported_calling_conventions)]` on by default error: ABI not supported by `#[link(kind = "raw-dylib")]` on this architecture - --> $DIR/unsupported-abi.rs:8:5 + --> $DIR/unsupported-abi.rs:16:5 | LL | fn f(x: i32); | ^^^^^^^^^^^^^ error: aborting due to 1 previous error; 1 warning emitted -Future incompatibility report: Future breakage diagnostic: -warning: use of calling convention not supported on this target - --> $DIR/unsupported-abi.rs:5:1 - | -LL | / extern "stdcall" { -LL | | -LL | | -LL | | fn f(x: i32); -LL | | -LL | | } - | |_^ - | - = 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 #137018 - = help: if you need `extern "stdcall"` on win32 and `extern "C"` everywhere else, use `extern "system"` - = note: `#[warn(unsupported_calling_conventions)]` on by default - diff --git a/tests/ui/lint/expansion-time.rs b/tests/ui/lint/expansion-time.rs index 5ffb0c7881e3..2c59bf000651 100644 --- a/tests/ui/lint/expansion-time.rs +++ b/tests/ui/lint/expansion-time.rs @@ -5,10 +5,6 @@ macro_rules! foo { ( $($i:ident)* ) => { $($i)+ }; //~ WARN meta-variable repeats with different Kleene operator } -#[warn(missing_fragment_specifier)] -macro_rules! m { ($i) => {} } //~ WARN missing fragment specifier - //~| WARN this was previously accepted - #[deprecated = "reason"] macro_rules! deprecated { () => {} diff --git a/tests/ui/lint/expansion-time.stderr b/tests/ui/lint/expansion-time.stderr index f24d1b68a8da..b1154d1a54c0 100644 --- a/tests/ui/lint/expansion-time.stderr +++ b/tests/ui/lint/expansion-time.stderr @@ -12,20 +12,6 @@ note: the lint level is defined here LL | #[warn(meta_variable_misuse)] | ^^^^^^^^^^^^^^^^^^^^ -warning: missing fragment specifier - --> $DIR/expansion-time.rs:9:19 - | -LL | macro_rules! m { ($i) => {} } - | ^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/expansion-time.rs:8:8 - | -LL | #[warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - warning: include macro expected single expression in source --> $DIR/expansion-time-include.rs:4:1 | @@ -33,25 +19,10 @@ LL | 2 | ^ | note: the lint level is defined here - --> $DIR/expansion-time.rs:22:8 + --> $DIR/expansion-time.rs:18:8 | LL | #[warn(incomplete_include)] | ^^^^^^^^^^^^^^^^^^ -warning: 3 warnings emitted - -Future incompatibility report: Future breakage diagnostic: -warning: missing fragment specifier - --> $DIR/expansion-time.rs:9:19 - | -LL | macro_rules! m { ($i) => {} } - | ^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/expansion-time.rs:8:8 - | -LL | #[warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ +warning: 2 warnings emitted diff --git a/tests/ui/lint/fn-ptr-comparisons-some.rs b/tests/ui/lint/fn-ptr-comparisons-some.rs index 152e16b9884b..c6ddd759baa3 100644 --- a/tests/ui/lint/fn-ptr-comparisons-some.rs +++ b/tests/ui/lint/fn-ptr-comparisons-some.rs @@ -12,6 +12,6 @@ fn main() { let _ = Some::(func) == Some(func as unsafe extern "C" fn()); //~^ WARN function pointer comparisons - // Undecided as of https://github.com/rust-lang/rust/pull/134536 assert_eq!(Some::(func), Some(func as unsafe extern "C" fn())); + //~^ WARN function pointer comparisons } diff --git a/tests/ui/lint/fn-ptr-comparisons-some.stderr b/tests/ui/lint/fn-ptr-comparisons-some.stderr index eefad05b676d..522c4399bce1 100644 --- a/tests/ui/lint/fn-ptr-comparisons-some.stderr +++ b/tests/ui/lint/fn-ptr-comparisons-some.stderr @@ -9,5 +9,16 @@ LL | let _ = Some::(func) == Some(func as unsafe extern "C" fn()); = note: for more information visit = note: `#[warn(unpredictable_function_pointer_comparisons)]` on by default -warning: 1 warning emitted +warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique + --> $DIR/fn-ptr-comparisons-some.rs:15:5 + | +LL | assert_eq!(Some::(func), Some(func as unsafe extern "C" fn())); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: the address of the same function can vary between different codegen units + = note: furthermore, different functions could have the same address after being merged together + = note: for more information visit + = note: this warning originates in the macro `assert_eq` (in Nightly builds, run with -Z macro-backtrace for more info) + +warning: 2 warnings emitted diff --git a/tests/ui/lint/fn-ptr-comparisons-weird.rs b/tests/ui/lint/fn-ptr-comparisons-weird.rs index 171fbfb87279..4d756cb49df0 100644 --- a/tests/ui/lint/fn-ptr-comparisons-weird.rs +++ b/tests/ui/lint/fn-ptr-comparisons-weird.rs @@ -1,5 +1,23 @@ //@ check-pass +#[derive(PartialEq, Eq)] +struct A { + f: fn(), + //~^ WARN function pointer comparisons +} + +#[allow(unpredictable_function_pointer_comparisons)] +#[derive(PartialEq, Eq)] +struct AllowedAbove { + f: fn(), +} + +#[derive(PartialEq, Eq)] +#[allow(unpredictable_function_pointer_comparisons)] +struct AllowedBelow { + f: fn(), +} + fn main() { let f: fn() = main; let g: fn() = main; @@ -12,4 +30,8 @@ fn main() { //~^ WARN function pointer comparisons let _ = f < g; //~^ WARN function pointer comparisons + let _ = assert_eq!(g, g); + //~^ WARN function pointer comparisons + let _ = assert_ne!(g, g); + //~^ WARN function pointer comparisons } diff --git a/tests/ui/lint/fn-ptr-comparisons-weird.stderr b/tests/ui/lint/fn-ptr-comparisons-weird.stderr index f23716639223..2014e519c253 100644 --- a/tests/ui/lint/fn-ptr-comparisons-weird.stderr +++ b/tests/ui/lint/fn-ptr-comparisons-weird.stderr @@ -1,8 +1,11 @@ warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons-weird.rs:7:13 + --> $DIR/fn-ptr-comparisons-weird.rs:5:5 | -LL | let _ = f > g; - | ^^^^^ +LL | #[derive(PartialEq, Eq)] + | --------- in this derive macro expansion +LL | struct A { +LL | f: fn(), + | ^^^^^^^ | = note: the address of the same function can vary between different codegen units = note: furthermore, different functions could have the same address after being merged together @@ -10,7 +13,17 @@ LL | let _ = f > g; = note: `#[warn(unpredictable_function_pointer_comparisons)]` on by default warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons-weird.rs:9:13 + --> $DIR/fn-ptr-comparisons-weird.rs:25:13 + | +LL | let _ = f > g; + | ^^^^^ + | + = note: the address of the same function can vary between different codegen units + = note: furthermore, different functions could have the same address after being merged together + = note: for more information visit + +warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique + --> $DIR/fn-ptr-comparisons-weird.rs:27:13 | LL | let _ = f >= g; | ^^^^^^ @@ -20,7 +33,7 @@ LL | let _ = f >= g; = note: for more information visit warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons-weird.rs:11:13 + --> $DIR/fn-ptr-comparisons-weird.rs:29:13 | LL | let _ = f <= g; | ^^^^^^ @@ -30,7 +43,7 @@ LL | let _ = f <= g; = note: for more information visit warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons-weird.rs:13:13 + --> $DIR/fn-ptr-comparisons-weird.rs:31:13 | LL | let _ = f < g; | ^^^^^ @@ -39,5 +52,27 @@ LL | let _ = f < g; = note: furthermore, different functions could have the same address after being merged together = note: for more information visit -warning: 4 warnings emitted +warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique + --> $DIR/fn-ptr-comparisons-weird.rs:33:13 + | +LL | let _ = assert_eq!(g, g); + | ^^^^^^^^^^^^^^^^ + | + = note: the address of the same function can vary between different codegen units + = note: furthermore, different functions could have the same address after being merged together + = note: for more information visit + = note: this warning originates in the macro `assert_eq` (in Nightly builds, run with -Z macro-backtrace for more info) + +warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique + --> $DIR/fn-ptr-comparisons-weird.rs:35:13 + | +LL | let _ = assert_ne!(g, g); + | ^^^^^^^^^^^^^^^^ + | + = note: the address of the same function can vary between different codegen units + = note: furthermore, different functions could have the same address after being merged together + = note: for more information visit + = note: this warning originates in the macro `assert_ne` (in Nightly builds, run with -Z macro-backtrace for more info) + +warning: 7 warnings emitted diff --git a/tests/ui/lint/fn-ptr-comparisons.fixed b/tests/ui/lint/fn-ptr-comparisons.fixed index 22f16177a044..41cdb7bf6aea 100644 --- a/tests/ui/lint/fn-ptr-comparisons.fixed +++ b/tests/ui/lint/fn-ptr-comparisons.fixed @@ -11,7 +11,6 @@ extern "C" fn c() {} extern "C" fn args(_a: i32) -> i32 { 0 } -#[derive(PartialEq, Eq)] struct A { f: fn(), } @@ -52,7 +51,6 @@ fn main() { let _ = std::ptr::fn_addr_eq(t, test as unsafe extern "C" fn()); //~^ WARN function pointer comparisons - let _ = a1 == a2; // should not warn let _ = std::ptr::fn_addr_eq(a1.f, a2.f); //~^ WARN function pointer comparisons } diff --git a/tests/ui/lint/fn-ptr-comparisons.rs b/tests/ui/lint/fn-ptr-comparisons.rs index 90a8ab5c926b..c2601d6adfba 100644 --- a/tests/ui/lint/fn-ptr-comparisons.rs +++ b/tests/ui/lint/fn-ptr-comparisons.rs @@ -11,7 +11,6 @@ extern "C" fn c() {} extern "C" fn args(_a: i32) -> i32 { 0 } -#[derive(PartialEq, Eq)] struct A { f: fn(), } @@ -52,7 +51,6 @@ fn main() { let _ = t == test; //~^ WARN function pointer comparisons - let _ = a1 == a2; // should not warn let _ = a1.f == a2.f; //~^ WARN function pointer comparisons } diff --git a/tests/ui/lint/fn-ptr-comparisons.stderr b/tests/ui/lint/fn-ptr-comparisons.stderr index e69933238986..5913acca16bb 100644 --- a/tests/ui/lint/fn-ptr-comparisons.stderr +++ b/tests/ui/lint/fn-ptr-comparisons.stderr @@ -1,5 +1,5 @@ warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:26:13 + --> $DIR/fn-ptr-comparisons.rs:25:13 | LL | let _ = f == a; | ^^^^^^ @@ -15,7 +15,7 @@ LL + let _ = std::ptr::fn_addr_eq(f, a as fn()); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:28:13 + --> $DIR/fn-ptr-comparisons.rs:27:13 | LL | let _ = f != a; | ^^^^^^ @@ -30,7 +30,7 @@ LL + let _ = !std::ptr::fn_addr_eq(f, a as fn()); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:30:13 + --> $DIR/fn-ptr-comparisons.rs:29:13 | LL | let _ = f == g; | ^^^^^^ @@ -45,7 +45,7 @@ LL + let _ = std::ptr::fn_addr_eq(f, g); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:32:13 + --> $DIR/fn-ptr-comparisons.rs:31:13 | LL | let _ = f == f; | ^^^^^^ @@ -60,7 +60,7 @@ LL + let _ = std::ptr::fn_addr_eq(f, f); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:34:13 + --> $DIR/fn-ptr-comparisons.rs:33:13 | LL | let _ = g == g; | ^^^^^^ @@ -75,7 +75,7 @@ LL + let _ = std::ptr::fn_addr_eq(g, g); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:36:13 + --> $DIR/fn-ptr-comparisons.rs:35:13 | LL | let _ = g == g; | ^^^^^^ @@ -90,7 +90,7 @@ LL + let _ = std::ptr::fn_addr_eq(g, g); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:38:13 + --> $DIR/fn-ptr-comparisons.rs:37:13 | LL | let _ = &g == &g; | ^^^^^^^^ @@ -105,7 +105,7 @@ LL + let _ = std::ptr::fn_addr_eq(g, g); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:40:13 + --> $DIR/fn-ptr-comparisons.rs:39:13 | LL | let _ = a as fn() == g; | ^^^^^^^^^^^^^^ @@ -120,7 +120,7 @@ LL + let _ = std::ptr::fn_addr_eq(a as fn(), g); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:44:13 + --> $DIR/fn-ptr-comparisons.rs:43:13 | LL | let _ = cfn == c; | ^^^^^^^^ @@ -135,7 +135,7 @@ LL + let _ = std::ptr::fn_addr_eq(cfn, c as extern "C" fn()); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:48:13 + --> $DIR/fn-ptr-comparisons.rs:47:13 | LL | let _ = argsfn == args; | ^^^^^^^^^^^^^^ @@ -150,7 +150,7 @@ LL + let _ = std::ptr::fn_addr_eq(argsfn, args as extern "C" fn(i32) -> i32) | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:52:13 + --> $DIR/fn-ptr-comparisons.rs:51:13 | LL | let _ = t == test; | ^^^^^^^^^ @@ -165,7 +165,7 @@ LL + let _ = std::ptr::fn_addr_eq(t, test as unsafe extern "C" fn()); | warning: function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique - --> $DIR/fn-ptr-comparisons.rs:56:13 + --> $DIR/fn-ptr-comparisons.rs:54:13 | LL | let _ = a1.f == a2.f; | ^^^^^^^^^^^^ diff --git a/tests/ui/lint/future-incompatible-lint-group.rs b/tests/ui/lint/future-incompatible-lint-group.rs new file mode 100644 index 000000000000..22a7ccb463b6 --- /dev/null +++ b/tests/ui/lint/future-incompatible-lint-group.rs @@ -0,0 +1,30 @@ +//! Test that future_incompatible lint group only includes edition-independent lints + +// Ensure that the future_incompatible lint group only includes +// lints for changes that are not tied to an edition +#![deny(future_incompatible)] + +enum E { V } + +trait Tr1 { + type V; + fn foo() -> Self::V; +} + +impl Tr1 for E { + type V = u8; + + // Error since this is a `future_incompatible` lint + fn foo() -> Self::V { 0 } + //~^ ERROR ambiguous associated item + //~| WARN this was previously accepted +} + +trait Tr2 { + // Warn only since this is not a `future_incompatible` lint + fn f(u8) {} + //~^ WARN anonymous parameters are deprecated + //~| WARN this is accepted in the current edition +} + +fn main() {} diff --git a/tests/ui/lint/future-incompatible-lint-group.stderr b/tests/ui/lint/future-incompatible-lint-group.stderr new file mode 100644 index 000000000000..87b9ebec08b3 --- /dev/null +++ b/tests/ui/lint/future-incompatible-lint-group.stderr @@ -0,0 +1,37 @@ +warning: anonymous parameters are deprecated and will be removed in the next edition + --> $DIR/future-incompatible-lint-group.rs:25:10 + | +LL | fn f(u8) {} + | ^^ help: try naming the parameter or explicitly ignoring it: `_: u8` + | + = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! + = note: for more information, see issue #41686 + = note: `#[warn(anonymous_parameters)]` on by default + +error: ambiguous associated item + --> $DIR/future-incompatible-lint-group.rs:18:17 + | +LL | fn foo() -> Self::V { 0 } + | ^^^^^^^ help: use fully-qualified syntax: `::V` + | + = 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 #57644 +note: `V` could refer to the variant defined here + --> $DIR/future-incompatible-lint-group.rs:7:10 + | +LL | enum E { V } + | ^ +note: `V` could also refer to the associated type defined here + --> $DIR/future-incompatible-lint-group.rs:10:5 + | +LL | type V; + | ^^^^^^ +note: the lint level is defined here + --> $DIR/future-incompatible-lint-group.rs:5:9 + | +LL | #![deny(future_incompatible)] + | ^^^^^^^^^^^^^^^^^^^ + = note: `#[deny(ambiguous_associated_items)]` implied by `#[deny(future_incompatible)]` + +error: aborting due to 1 previous error; 1 warning emitted + diff --git a/tests/ui/loops/issue-43162.stderr b/tests/ui/loops/issue-43162.stderr index 40d9200058ed..f6b6bf2621c2 100644 --- a/tests/ui/loops/issue-43162.stderr +++ b/tests/ui/loops/issue-43162.stderr @@ -4,12 +4,6 @@ error[E0268]: `break` outside of a loop or labeled block LL | break true; | ^^^^^^^^^^ cannot `break` outside of a loop or labeled block -error[E0268]: `break` outside of a loop or labeled block - --> $DIR/issue-43162.rs:7:5 - | -LL | break {}; - | ^^^^^^^^ cannot `break` outside of a loop or labeled block - error[E0308]: mismatched types --> $DIR/issue-43162.rs:1:13 | @@ -18,6 +12,12 @@ LL | fn foo() -> bool { | | | implicitly returns `()` as its body has no tail or `return` expression +error[E0268]: `break` outside of a loop or labeled block + --> $DIR/issue-43162.rs:7:5 + | +LL | break {}; + | ^^^^^^^^ cannot `break` outside of a loop or labeled block + error: aborting due to 3 previous errors Some errors have detailed explanations: E0268, E0308. diff --git a/tests/ui/macros/auxiliary/serde.rs b/tests/ui/macros/auxiliary/serde.rs new file mode 100644 index 000000000000..355b650bcf39 --- /dev/null +++ b/tests/ui/macros/auxiliary/serde.rs @@ -0,0 +1,19 @@ +//@ force-host +//@ no-prefer-dynamic + +#![crate_type = "proc-macro"] +#![feature(proc_macro_quote)] + +extern crate proc_macro; + +use proc_macro::*; + +#[proc_macro_derive(Serialize, attributes(serde))] +pub fn serialize(ts: TokenStream) -> TokenStream { + quote!{} +} + +#[proc_macro_derive(Deserialize, attributes(serde))] +pub fn deserialize(ts: TokenStream) -> TokenStream { + quote!{} +} diff --git a/tests/ui/macros/issue-39404.rs b/tests/ui/macros/issue-39404.rs index 2229f2c3900c..ceeb6231bc8c 100644 --- a/tests/ui/macros/issue-39404.rs +++ b/tests/ui/macros/issue-39404.rs @@ -1,7 +1,7 @@ #![allow(unused)] -macro_rules! m { ($i) => {} } -//~^ ERROR missing fragment specifier -//~| WARN previously accepted +macro_rules! m { + ($i) => {}; //~ ERROR missing fragment specifier +} fn main() {} diff --git a/tests/ui/macros/issue-39404.stderr b/tests/ui/macros/issue-39404.stderr index 176c8e9f073c..62d0bc1018c5 100644 --- a/tests/ui/macros/issue-39404.stderr +++ b/tests/ui/macros/issue-39404.stderr @@ -1,23 +1,15 @@ error: missing fragment specifier - --> $DIR/issue-39404.rs:3:19 + --> $DIR/issue-39404.rs:4:6 | -LL | macro_rules! m { ($i) => {} } - | ^^ +LL | ($i) => {}; + | ^^ | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default + = note: fragment specifiers must be provided + = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility +help: try adding a specifier here + | +LL | ($i:spec) => {}; + | +++++ error: aborting due to 1 previous error -Future incompatibility report: Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/issue-39404.rs:3:19 - | -LL | macro_rules! m { ($i) => {} } - | ^^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default - diff --git a/tests/ui/macros/macro-match-nonterminal.rs b/tests/ui/macros/macro-match-nonterminal.rs index 5d9eb55fee03..fa2af945a1f1 100644 --- a/tests/ui/macros/macro-match-nonterminal.rs +++ b/tests/ui/macros/macro-match-nonterminal.rs @@ -3,8 +3,6 @@ macro_rules! test { //~^ ERROR missing fragment //~| ERROR missing fragment //~| ERROR missing fragment - //~| WARN this was previously accepted - //~| WARN this was previously accepted () }; } diff --git a/tests/ui/macros/macro-match-nonterminal.stderr b/tests/ui/macros/macro-match-nonterminal.stderr index f221f92c3cda..8196d795c4c8 100644 --- a/tests/ui/macros/macro-match-nonterminal.stderr +++ b/tests/ui/macros/macro-match-nonterminal.stderr @@ -1,18 +1,15 @@ -error: missing fragment specifier - --> $DIR/macro-match-nonterminal.rs:2:6 - | -LL | ($a, $b) => { - | ^^ - error: missing fragment specifier --> $DIR/macro-match-nonterminal.rs:2:6 | LL | ($a, $b) => { | ^^ | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default + = note: fragment specifiers must be provided + = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility +help: try adding a specifier here + | +LL | ($a:spec, $b) => { + | +++++ error: missing fragment specifier --> $DIR/macro-match-nonterminal.rs:2:10 @@ -20,30 +17,18 @@ error: missing fragment specifier LL | ($a, $b) => { | ^^ | - = 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 #40107 + = note: fragment specifiers must be provided + = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility +help: try adding a specifier here + | +LL | ($a, $b:spec) => { + | +++++ + +error: missing fragment specifier + --> $DIR/macro-match-nonterminal.rs:2:6 + | +LL | ($a, $b) => { + | ^^ error: aborting due to 3 previous errors -Future incompatibility report: Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/macro-match-nonterminal.rs:2:6 - | -LL | ($a, $b) => { - | ^^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default - -Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/macro-match-nonterminal.rs:2:10 - | -LL | ($a, $b) => { - | ^^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default - diff --git a/tests/ui/macros/macro-missing-fragment-deduplication.rs b/tests/ui/macros/macro-missing-fragment-deduplication.rs index b77c51e055bf..481f08fa1119 100644 --- a/tests/ui/macros/macro-missing-fragment-deduplication.rs +++ b/tests/ui/macros/macro-missing-fragment-deduplication.rs @@ -1,10 +1,8 @@ //@ compile-flags: -Zdeduplicate-diagnostics=yes macro_rules! m { - ($name) => {} - //~^ ERROR missing fragment - //~| ERROR missing fragment - //~| WARN this was previously accepted + ($name) => {}; //~ ERROR missing fragment + //~| ERROR missing fragment } fn main() { diff --git a/tests/ui/macros/macro-missing-fragment-deduplication.stderr b/tests/ui/macros/macro-missing-fragment-deduplication.stderr index c46712f70fd5..820f7eb3cf7f 100644 --- a/tests/ui/macros/macro-missing-fragment-deduplication.stderr +++ b/tests/ui/macros/macro-missing-fragment-deduplication.stderr @@ -1,29 +1,21 @@ error: missing fragment specifier --> $DIR/macro-missing-fragment-deduplication.rs:4:6 | -LL | ($name) => {} +LL | ($name) => {}; | ^^^^^ + | + = note: fragment specifiers must be provided + = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility +help: try adding a specifier here + | +LL | ($name:spec) => {}; + | +++++ error: missing fragment specifier --> $DIR/macro-missing-fragment-deduplication.rs:4:6 | -LL | ($name) => {} +LL | ($name) => {}; | ^^^^^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default error: aborting due to 2 previous errors -Future incompatibility report: Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/macro-missing-fragment-deduplication.rs:4:6 - | -LL | ($name) => {} - | ^^^^^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default - diff --git a/tests/ui/macros/macro-missing-fragment.e2015.stderr b/tests/ui/macros/macro-missing-fragment.e2015.stderr deleted file mode 100644 index 3d32f203d4a2..000000000000 --- a/tests/ui/macros/macro-missing-fragment.e2015.stderr +++ /dev/null @@ -1,85 +0,0 @@ -error: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:8:20 - | -LL | ( $( any_token $field_rust_type )* ) => {}; - | ^^^^^^^^^^^^^^^^ - -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:8:20 - | -LL | ( $( any_token $field_rust_type )* ) => {}; - | ^^^^^^^^^^^^^^^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/macro-missing-fragment.rs:5:9 - | -LL | #![warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:18:7 - | -LL | ( $name ) => {}; - | ^^^^^ - | - = 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 #40107 - -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:25:7 - | -LL | ( $name ) => {}; - | ^^^^^ - | - = 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 #40107 - -error: aborting due to 1 previous error; 3 warnings emitted - -Future incompatibility report: Future breakage diagnostic: -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:8:20 - | -LL | ( $( any_token $field_rust_type )* ) => {}; - | ^^^^^^^^^^^^^^^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/macro-missing-fragment.rs:5:9 - | -LL | #![warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - -Future breakage diagnostic: -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:18:7 - | -LL | ( $name ) => {}; - | ^^^^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/macro-missing-fragment.rs:5:9 - | -LL | #![warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - -Future breakage diagnostic: -warning: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:25:7 - | -LL | ( $name ) => {}; - | ^^^^^ - | - = 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 #40107 -note: the lint level is defined here - --> $DIR/macro-missing-fragment.rs:5:9 - | -LL | #![warn(missing_fragment_specifier)] - | ^^^^^^^^^^^^^^^^^^^^^^^^^^ - diff --git a/tests/ui/macros/macro-missing-fragment.rs b/tests/ui/macros/macro-missing-fragment.rs index 42387e8dbbf4..533aa147bcbf 100644 --- a/tests/ui/macros/macro-missing-fragment.rs +++ b/tests/ui/macros/macro-missing-fragment.rs @@ -1,31 +1,17 @@ -//@ revisions: e2015 e2024 -//@[e2015] edition:2015 -//@[e2024] edition:2024 - -#![warn(missing_fragment_specifier)] +//! Ensure that macros produce an error if fragment specifiers are missing. macro_rules! used_arm { - ( $( any_token $field_rust_type )* ) => {}; - //[e2015]~^ ERROR missing fragment - //[e2015]~| WARN missing fragment - //[e2015]~| WARN this was previously accepted - //[e2024]~^^^^ ERROR missing fragment - //[e2024]~| ERROR missing fragment + ( $( any_token $field_rust_type )* ) => {}; //~ ERROR missing fragment + //~| ERROR missing fragment } macro_rules! used_macro_unused_arm { () => {}; - ( $name ) => {}; - //[e2015]~^ WARN missing fragment - //[e2015]~| WARN this was previously accepted - //[e2024]~^^^ ERROR missing fragment + ( $name ) => {}; //~ ERROR missing fragment } macro_rules! unused_macro { - ( $name ) => {}; - //[e2015]~^ WARN missing fragment - //[e2015]~| WARN this was previously accepted - //[e2024]~^^^ ERROR missing fragment + ( $name ) => {}; //~ ERROR missing fragment } fn main() { diff --git a/tests/ui/macros/macro-missing-fragment.e2024.stderr b/tests/ui/macros/macro-missing-fragment.stderr similarity index 79% rename from tests/ui/macros/macro-missing-fragment.e2024.stderr rename to tests/ui/macros/macro-missing-fragment.stderr index a9195063a5b9..4a99d7d949cf 100644 --- a/tests/ui/macros/macro-missing-fragment.e2024.stderr +++ b/tests/ui/macros/macro-missing-fragment.stderr @@ -1,10 +1,10 @@ error: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:8:20 + --> $DIR/macro-missing-fragment.rs:4:20 | LL | ( $( any_token $field_rust_type )* ) => {}; | ^^^^^^^^^^^^^^^^ | - = note: fragment specifiers must be specified in the 2024 edition + = note: fragment specifiers must be provided = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility help: try adding a specifier here | @@ -12,12 +12,12 @@ LL | ( $( any_token $field_rust_type:spec )* ) => {}; | +++++ error: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:18:7 + --> $DIR/macro-missing-fragment.rs:10:7 | LL | ( $name ) => {}; | ^^^^^ | - = note: fragment specifiers must be specified in the 2024 edition + = note: fragment specifiers must be provided = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility help: try adding a specifier here | @@ -25,12 +25,12 @@ LL | ( $name:spec ) => {}; | +++++ error: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:25:7 + --> $DIR/macro-missing-fragment.rs:14:7 | LL | ( $name ) => {}; | ^^^^^ | - = note: fragment specifiers must be specified in the 2024 edition + = note: fragment specifiers must be provided = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility help: try adding a specifier here | @@ -38,7 +38,7 @@ LL | ( $name:spec ) => {}; | +++++ error: missing fragment specifier - --> $DIR/macro-missing-fragment.rs:8:20 + --> $DIR/macro-missing-fragment.rs:4:20 | LL | ( $( any_token $field_rust_type )* ) => {}; | ^^^^^^^^^^^^^^^^ diff --git a/tests/ui/macros/macro-reexport-removed.rs b/tests/ui/macros/macro-reexport-removed.rs index 4a054686d776..c1267f14cd86 100644 --- a/tests/ui/macros/macro-reexport-removed.rs +++ b/tests/ui/macros/macro-reexport-removed.rs @@ -1,4 +1,5 @@ //@ aux-build:two_macros.rs +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" #![feature(macro_reexport)] //~ ERROR feature has been removed diff --git a/tests/ui/macros/macro-reexport-removed.stderr b/tests/ui/macros/macro-reexport-removed.stderr index 475a586ddc08..d4940eeb7755 100644 --- a/tests/ui/macros/macro-reexport-removed.stderr +++ b/tests/ui/macros/macro-reexport-removed.stderr @@ -1,13 +1,14 @@ error[E0557]: feature has been removed - --> $DIR/macro-reexport-removed.rs:3:12 + --> $DIR/macro-reexport-removed.rs:4:12 | LL | #![feature(macro_reexport)] | ^^^^^^^^^^^^^^ feature has been removed | + = note: removed in 1.0.0 (you are using $RUSTC_VERSION); see for more information = note: subsumed by `pub use` error: cannot find attribute `macro_reexport` in this scope - --> $DIR/macro-reexport-removed.rs:5:3 + --> $DIR/macro-reexport-removed.rs:6:3 | LL | #[macro_reexport(macro_one)] | ^^^^^^^^^^^^^^ help: a built-in attribute with a similar name exists: `macro_export` diff --git a/tests/ui/macros/missing-derive-1.rs b/tests/ui/macros/missing-derive-1.rs new file mode 100644 index 000000000000..e23ef7bf07ba --- /dev/null +++ b/tests/ui/macros/missing-derive-1.rs @@ -0,0 +1,33 @@ +//@aux-build:serde.rs + +// derive macros imported and used + +extern crate serde; +use serde::{Serialize, Deserialize}; + +#[serde(untagged)] //~ ERROR cannot find attribute `serde` +enum A { //~ HELP `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize` + A, + B, +} + +enum B { //~ HELP `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize` + A, + #[serde(untagged)] //~ ERROR cannot find attribute `serde` + B, +} + +enum C { + A, + #[sede(untagged)] //~ ERROR cannot find attribute `sede` + B, //~^ HELP the derive macros `Deserialize` and `Serialize` accept the similarly named `serde` attribute +} + +#[derive(Serialize, Deserialize)] +#[serde(untagged)] +enum D { + A, + B, +} + +fn main() {} diff --git a/tests/ui/macros/missing-derive-1.stderr b/tests/ui/macros/missing-derive-1.stderr new file mode 100644 index 000000000000..15584100ffaf --- /dev/null +++ b/tests/ui/macros/missing-derive-1.stderr @@ -0,0 +1,47 @@ +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-1.rs:8:3 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-1.rs:5:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ +help: `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize`, you might be missing a `derive` attribute + | +LL + #[derive(Deserialize, Serialize)] +LL | enum A { + | + +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-1.rs:16:7 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-1.rs:5:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ +help: `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize`, you might be missing a `derive` attribute + | +LL + #[derive(Deserialize, Serialize)] +LL | enum B { + | + +error: cannot find attribute `sede` in this scope + --> $DIR/missing-derive-1.rs:22:7 + | +LL | #[sede(untagged)] + | ^^^^ + | +help: the derive macros `Deserialize` and `Serialize` accept the similarly named `serde` attribute + | +LL | #[serde(untagged)] + | + + +error: aborting due to 3 previous errors + diff --git a/tests/ui/macros/missing-derive-2.rs b/tests/ui/macros/missing-derive-2.rs new file mode 100644 index 000000000000..027d465d8b37 --- /dev/null +++ b/tests/ui/macros/missing-derive-2.rs @@ -0,0 +1,26 @@ +//@aux-build:serde.rs + +// derive macros imported but unused + +extern crate serde; +use serde::{Serialize, Deserialize}; + +#[serde(untagged)] //~ ERROR cannot find attribute `serde` +enum A { //~ HELP `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize` + A, + B, +} + +enum B { //~ HELP `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize` + A, + #[serde(untagged)] //~ ERROR cannot find attribute `serde` + B, +} + +enum C { + A, + #[sede(untagged)] //~ ERROR cannot find attribute `sede` + B, //~^ HELP the derive macros `Deserialize` and `Serialize` accept the similarly named `serde` attribute +} + +fn main() {} diff --git a/tests/ui/macros/missing-derive-2.stderr b/tests/ui/macros/missing-derive-2.stderr new file mode 100644 index 000000000000..6c8e9e120190 --- /dev/null +++ b/tests/ui/macros/missing-derive-2.stderr @@ -0,0 +1,47 @@ +error: cannot find attribute `sede` in this scope + --> $DIR/missing-derive-2.rs:22:7 + | +LL | #[sede(untagged)] + | ^^^^ + | +help: the derive macros `Deserialize` and `Serialize` accept the similarly named `serde` attribute + | +LL | #[serde(untagged)] + | + + +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-2.rs:16:7 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-2.rs:5:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ +help: `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize`, you might be missing a `derive` attribute + | +LL + #[derive(Deserialize, Serialize)] +LL | enum B { + | + +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-2.rs:8:3 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-2.rs:5:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ +help: `serde` is an attribute that can be used by the derive macros `Deserialize` and `Serialize`, you might be missing a `derive` attribute + | +LL + #[derive(Deserialize, Serialize)] +LL | enum A { + | + +error: aborting due to 3 previous errors + diff --git a/tests/ui/macros/missing-derive-3.rs b/tests/ui/macros/missing-derive-3.rs new file mode 100644 index 000000000000..8add81988901 --- /dev/null +++ b/tests/ui/macros/missing-derive-3.rs @@ -0,0 +1,24 @@ +//@aux-build:serde.rs + +// derive macros not imported, but namespace imported. Not yet handled. +extern crate serde; + +#[serde(untagged)] //~ ERROR cannot find attribute `serde` +enum A { + A, + B, +} + +enum B { + A, + #[serde(untagged)] //~ ERROR cannot find attribute `serde` + B, +} + +enum C { + A, + #[sede(untagged)] //~ ERROR cannot find attribute `sede` + B, +} + +fn main() {} diff --git a/tests/ui/macros/missing-derive-3.stderr b/tests/ui/macros/missing-derive-3.stderr new file mode 100644 index 000000000000..0a7ed8d08763 --- /dev/null +++ b/tests/ui/macros/missing-derive-3.stderr @@ -0,0 +1,32 @@ +error: cannot find attribute `sede` in this scope + --> $DIR/missing-derive-3.rs:20:7 + | +LL | #[sede(untagged)] + | ^^^^ + +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-3.rs:14:7 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-3.rs:4:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ + +error: cannot find attribute `serde` in this scope + --> $DIR/missing-derive-3.rs:6:3 + | +LL | #[serde(untagged)] + | ^^^^^ + | +note: `serde` is imported here, but it is a crate, not an attribute + --> $DIR/missing-derive-3.rs:4:1 + | +LL | extern crate serde; + | ^^^^^^^^^^^^^^^^^^^ + +error: aborting due to 3 previous errors + diff --git a/tests/ui/ext-expand-inner-exprs.rs b/tests/ui/macros/nested-macro-expansion.rs similarity index 71% rename from tests/ui/ext-expand-inner-exprs.rs rename to tests/ui/macros/nested-macro-expansion.rs index 94610d0a328f..3b94b1051c9b 100644 --- a/tests/ui/ext-expand-inner-exprs.rs +++ b/tests/ui/macros/nested-macro-expansion.rs @@ -1,3 +1,5 @@ +//! Test nested macro expansion with concat! macros + //@ run-pass static FOO : &'static str = concat!(concat!("hel", "lo"), "world"); diff --git a/tests/ui/impl-inherent-non-conflict.rs b/tests/ui/methods/inherent-methods-same-name.rs similarity index 68% rename from tests/ui/impl-inherent-non-conflict.rs rename to tests/ui/methods/inherent-methods-same-name.rs index 41ab865892a1..d7d19bc33256 100644 --- a/tests/ui/impl-inherent-non-conflict.rs +++ b/tests/ui/methods/inherent-methods-same-name.rs @@ -1,17 +1,22 @@ +//! Test multiple inherent methods with same name on different type parameters + //@ run-pass // Ensure that a user-defined type admits multiple inherent methods // with the same name, which can be called on values that have a // precise enough type to allow distinguishing between the methods. - struct Foo(T); impl Foo { - fn bar(&self) -> i32 { self.0 as i32 } + fn bar(&self) -> i32 { + self.0 as i32 + } } impl Foo { - fn bar(&self) -> i32 { -(self.0 as i32) } + fn bar(&self) -> i32 { + -(self.0 as i32) + } } fn main() { diff --git a/tests/ui/methods/missing-bound-on-tuple.rs b/tests/ui/methods/missing-bound-on-tuple.rs new file mode 100644 index 000000000000..25deabf59267 --- /dev/null +++ b/tests/ui/methods/missing-bound-on-tuple.rs @@ -0,0 +1,39 @@ +trait WorksOnDefault { + fn do_something() {} +} + +impl WorksOnDefault for T {} +//~^ NOTE the following trait bounds were not satisfied +//~| NOTE unsatisfied trait bound introduced here + +trait Foo {} + +trait WorksOnFoo { + fn do_be_do() {} +} + +impl WorksOnFoo for T {} +//~^ NOTE the following trait bounds were not satisfied +//~| NOTE unsatisfied trait bound introduced here + +impl Foo for (A, B, C) {} +//~^ NOTE `Foo` is implemented for `(i32, u32, String)` +impl Foo for i32 {} +impl Foo for &i32 {} +impl Foo for u32 {} +impl Foo for String {} + +fn main() { + let _success = <(i32, u32, String)>::do_something(); + let _failure = <(i32, &u32, String)>::do_something(); //~ ERROR E0599 + //~^ NOTE `Default` is implemented for `(i32, u32, String)` + //~| NOTE function or associated item cannot be called on + let _success = <(i32, u32, String)>::do_be_do(); + let _failure = <(i32, &u32, String)>::do_be_do(); //~ ERROR E0599 + //~^ NOTE function or associated item cannot be called on + let _success = <(i32, u32, String)>::default(); + let _failure = <(i32, &u32, String)>::default(); //~ ERROR E0599 + //~^ NOTE `Default` is implemented for `(i32, u32, String)` + //~| NOTE function or associated item cannot be called on + //~| NOTE the following trait bounds were not satisfied +} diff --git a/tests/ui/methods/missing-bound-on-tuple.stderr b/tests/ui/methods/missing-bound-on-tuple.stderr new file mode 100644 index 000000000000..f3e0897e5e64 --- /dev/null +++ b/tests/ui/methods/missing-bound-on-tuple.stderr @@ -0,0 +1,58 @@ +error[E0599]: the function or associated item `do_something` exists for tuple `(i32, &u32, String)`, but its trait bounds were not satisfied + --> $DIR/missing-bound-on-tuple.rs:28:43 + | +LL | let _failure = <(i32, &u32, String)>::do_something(); + | ^^^^^^^^^^^^ function or associated item cannot be called on `(i32, &u32, String)` due to unsatisfied trait bounds + | +note: the following trait bounds were not satisfied: + `&(i32, &u32, String): Default` + `&mut (i32, &u32, String): Default` + `(i32, &u32, String): Default` + --> $DIR/missing-bound-on-tuple.rs:5:9 + | +LL | impl WorksOnDefault for T {} + | ^^^^^^^ -------------- - + | | + | unsatisfied trait bound introduced here +note: `Default` is implemented for `(i32, u32, String)` but not for `(i32, &u32, String)` + --> $SRC_DIR/core/src/tuple.rs:LL:COL + = note: this error originates in the macro `tuple_impls` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: the function or associated item `do_be_do` exists for tuple `(i32, &u32, String)`, but its trait bounds were not satisfied + --> $DIR/missing-bound-on-tuple.rs:32:43 + | +LL | let _failure = <(i32, &u32, String)>::do_be_do(); + | ^^^^^^^^ function or associated item cannot be called on `(i32, &u32, String)` due to unsatisfied trait bounds + | +note: the following trait bounds were not satisfied: + `&(i32, &u32, String): Foo` + `&mut (i32, &u32, String): Foo` + `(i32, &u32, String): Foo` + --> $DIR/missing-bound-on-tuple.rs:15:9 + | +LL | impl WorksOnFoo for T {} + | ^^^ ---------- - + | | + | unsatisfied trait bound introduced here +note: `Foo` is implemented for `(i32, u32, String)` but not for `(i32, &u32, String)` + --> $DIR/missing-bound-on-tuple.rs:19:1 + | +LL | impl Foo for (A, B, C) {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error[E0599]: the function or associated item `default` exists for tuple `(i32, &u32, String)`, but its trait bounds were not satisfied + --> $DIR/missing-bound-on-tuple.rs:35:43 + | +LL | let _failure = <(i32, &u32, String)>::default(); + | ^^^^^^^ function or associated item cannot be called on `(i32, &u32, String)` due to unsatisfied trait bounds + | + = note: the following trait bounds were not satisfied: + `&u32: Default` + which is required by `(i32, &u32, String): Default` +note: `Default` is implemented for `(i32, u32, String)` but not for `(i32, &u32, String)` + --> $SRC_DIR/core/src/tuple.rs:LL:COL + = note: this error originates in the macro `tuple_impls` (in Nightly builds, run with -Z macro-backtrace for more info) + +error: aborting due to 3 previous errors + +For more information about this error, try `rustc --explain E0599`. diff --git a/tests/ui/mir/mir_refs_correct.rs b/tests/ui/mir/mir_refs_correct.rs index fc23c8c3631e..f1832d90a0f5 100644 --- a/tests/ui/mir/mir_refs_correct.rs +++ b/tests/ui/mir/mir_refs_correct.rs @@ -1,6 +1,8 @@ //@ run-pass //@ aux-build:mir_external_refs.rs +#![allow(unpredictable_function_pointer_comparisons)] + extern crate mir_external_refs as ext; struct S(#[allow(dead_code)] u8); diff --git a/tests/ui/impl-not-adjacent-to-type.rs b/tests/ui/modules/impl-cross-module.rs similarity index 78% rename from tests/ui/impl-not-adjacent-to-type.rs rename to tests/ui/modules/impl-cross-module.rs index ccf59ed43932..3ed8c18ff3cd 100644 --- a/tests/ui/impl-not-adjacent-to-type.rs +++ b/tests/ui/modules/impl-cross-module.rs @@ -1,3 +1,5 @@ +//! Test implementing methods for types defined in other modules + //@ run-pass mod foo { diff --git a/tests/ui/nll/sugg-mut-for-binding-issue-137486.fixed b/tests/ui/nll/sugg-mut-for-binding-issue-137486.fixed new file mode 100644 index 000000000000..ee9d9a373de0 --- /dev/null +++ b/tests/ui/nll/sugg-mut-for-binding-issue-137486.fixed @@ -0,0 +1,23 @@ +//@ run-rustfix +#![allow(unused_assignments)] + +use std::pin::Pin; +fn main() { + let mut s = String::from("hello"); + let mut ref_s = &mut s; + + let mut binding = String::from("world"); + ref_s = &mut binding; //~ ERROR temporary value dropped while borrowed [E0716] + + print!("r1 = {}", ref_s); + + let mut val: u8 = 5; + let mut s = Pin::new(&mut val); + let mut ref_s = &mut s; + + let mut val2: u8 = 10; + let mut binding = Pin::new(&mut val2); + ref_s = &mut binding; //~ ERROR temporary value dropped while borrowed [E0716] + + print!("r1 = {}", ref_s); +} diff --git a/tests/ui/nll/sugg-mut-for-binding-issue-137486.rs b/tests/ui/nll/sugg-mut-for-binding-issue-137486.rs new file mode 100644 index 000000000000..8f7ea7561077 --- /dev/null +++ b/tests/ui/nll/sugg-mut-for-binding-issue-137486.rs @@ -0,0 +1,21 @@ +//@ run-rustfix +#![allow(unused_assignments)] + +use std::pin::Pin; +fn main() { + let mut s = String::from("hello"); + let mut ref_s = &mut s; + + ref_s = &mut String::from("world"); //~ ERROR temporary value dropped while borrowed [E0716] + + print!("r1 = {}", ref_s); + + let mut val: u8 = 5; + let mut s = Pin::new(&mut val); + let mut ref_s = &mut s; + + let mut val2: u8 = 10; + ref_s = &mut Pin::new(&mut val2); //~ ERROR temporary value dropped while borrowed [E0716] + + print!("r1 = {}", ref_s); +} diff --git a/tests/ui/nll/sugg-mut-for-binding-issue-137486.stderr b/tests/ui/nll/sugg-mut-for-binding-issue-137486.stderr new file mode 100644 index 000000000000..8432725f60ad --- /dev/null +++ b/tests/ui/nll/sugg-mut-for-binding-issue-137486.stderr @@ -0,0 +1,37 @@ +error[E0716]: temporary value dropped while borrowed + --> $DIR/sugg-mut-for-binding-issue-137486.rs:9:18 + | +LL | ref_s = &mut String::from("world"); + | ^^^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement + | | + | creates a temporary value which is freed while still in use +LL | +LL | print!("r1 = {}", ref_s); + | ----- borrow later used here + | +help: consider using a `let` binding to create a longer lived value + | +LL ~ let mut binding = String::from("world"); +LL ~ ref_s = &mut binding; + | + +error[E0716]: temporary value dropped while borrowed + --> $DIR/sugg-mut-for-binding-issue-137486.rs:18:18 + | +LL | ref_s = &mut Pin::new(&mut val2); + | ^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement + | | + | creates a temporary value which is freed while still in use +LL | +LL | print!("r1 = {}", ref_s); + | ----- borrow later used here + | +help: consider using a `let` binding to create a longer lived value + | +LL ~ let mut binding = Pin::new(&mut val2); +LL ~ ref_s = &mut binding; + | + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0716`. diff --git a/tests/ui/nullable-pointer-iotareduction.rs b/tests/ui/nullable-pointer-iotareduction.rs index fa837dab51b6..1b73164c9fc7 100644 --- a/tests/ui/nullable-pointer-iotareduction.rs +++ b/tests/ui/nullable-pointer-iotareduction.rs @@ -8,6 +8,8 @@ // trying to get assert failure messages that at least identify which case // failed. +#![allow(unpredictable_function_pointer_comparisons)] + enum E { Thing(isize, T), #[allow(dead_code)] Nothing((), ((), ()), [i8; 0]) } impl E { fn is_none(&self) -> bool { diff --git a/tests/ui/object-lifetime/object-lifetime-default-from-box-error.stderr b/tests/ui/object-lifetime/object-lifetime-default-from-box-error.stderr index 15b36925c47b..05eb611081a4 100644 --- a/tests/ui/object-lifetime/object-lifetime-default-from-box-error.stderr +++ b/tests/ui/object-lifetime/object-lifetime-default-from-box-error.stderr @@ -21,11 +21,13 @@ LL | ss.r error[E0621]: explicit lifetime required in the type of `ss` --> $DIR/object-lifetime-default-from-box-error.rs:33:5 | -LL | fn store1<'b>(ss: &mut SomeStruct, b: Box) { - | --------------- help: add explicit lifetime `'b` to the type of `ss`: `&mut SomeStruct<'b>` -... LL | ss.r = b; | ^^^^ lifetime `'b` required + | +help: add explicit lifetime `'b` to the type of `ss` + | +LL | fn store1<'b>(ss: &mut SomeStruct<'b>, b: Box) { + | ++++ error: aborting due to 3 previous errors diff --git a/tests/ui/on-unimplemented/feature-gate-on-unimplemented.rs b/tests/ui/on-unimplemented/feature-gate-on-unimplemented.rs index 3cc50e3499a0..436caab5d64a 100644 --- a/tests/ui/on-unimplemented/feature-gate-on-unimplemented.rs +++ b/tests/ui/on-unimplemented/feature-gate-on-unimplemented.rs @@ -1,8 +1,9 @@ // Test that `#[rustc_on_unimplemented]` is gated by `rustc_attrs` feature gate. #[rustc_on_unimplemented = "test error `{Self}` with `{Bar}`"] -//~^ ERROR this is an internal attribute that will never be stable -trait Foo -{} +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_on_unimplemented]` attribute is an internal implementation detail that will never be stable +//~| NOTE see `#[diagnostic::on_unimplemented]` for the stable equivalent of this attribute +trait Foo {} fn main() {} diff --git a/tests/ui/on-unimplemented/feature-gate-on-unimplemented.stderr b/tests/ui/on-unimplemented/feature-gate-on-unimplemented.stderr index 2733f7478f0a..d1983088af85 100644 --- a/tests/ui/on-unimplemented/feature-gate-on-unimplemented.stderr +++ b/tests/ui/on-unimplemented/feature-gate-on-unimplemented.stderr @@ -1,11 +1,12 @@ -error[E0658]: this is an internal attribute that will never be stable +error[E0658]: use of an internal attribute --> $DIR/feature-gate-on-unimplemented.rs:3:1 | LL | #[rustc_on_unimplemented = "test error `{Self}` with `{Bar}`"] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_on_unimplemented]` attribute is an internal implementation detail that will never be stable + = note: see `#[diagnostic::on_unimplemented]` for the stable equivalent of this attribute error: aborting due to 1 previous error diff --git a/tests/ui/parser/block-no-opening-brace.rs b/tests/ui/parser/block-no-opening-brace.rs index b08c830bfc76..ea5a98ff6fc1 100644 --- a/tests/ui/parser/block-no-opening-brace.rs +++ b/tests/ui/parser/block-no-opening-brace.rs @@ -27,10 +27,10 @@ fn in_try() { let x = 0; } -// FIXME(#80931) fn in_async() { async - let x = 0; //~ ERROR expected one of `move`, `use`, `|`, or `||`, found keyword `let` + let x = 0; + //~^ ERROR expected one of `move`, `use`, `{`, `|`, or `||`, found keyword `let` } // FIXME(#78168) diff --git a/tests/ui/parser/block-no-opening-brace.stderr b/tests/ui/parser/block-no-opening-brace.stderr index f51ee92626f5..cf9eeba573dc 100644 --- a/tests/ui/parser/block-no-opening-brace.stderr +++ b/tests/ui/parser/block-no-opening-brace.stderr @@ -43,11 +43,11 @@ error: expected expression, found reserved keyword `try` LL | try | ^^^ expected expression -error: expected one of `move`, `use`, `|`, or `||`, found keyword `let` - --> $DIR/block-no-opening-brace.rs:33:9 +error: expected one of `move`, `use`, `{`, `|`, or `||`, found keyword `let` + --> $DIR/block-no-opening-brace.rs:32:9 | LL | async - | - expected one of `move`, `use`, `|`, or `||` + | - expected one of `move`, `use`, `{`, `|`, or `||` LL | let x = 0; | ^^^ unexpected token diff --git a/tests/ui/parser/macro/issue-33569.rs b/tests/ui/parser/macro/issue-33569.rs index 069d181e9626..e0a5352ab06d 100644 --- a/tests/ui/parser/macro/issue-33569.rs +++ b/tests/ui/parser/macro/issue-33569.rs @@ -2,7 +2,6 @@ macro_rules! foo { { $+ } => { //~ ERROR expected identifier, found `+` //~^ ERROR missing fragment specifier //~| ERROR missing fragment specifier - //~| WARN this was previously accepted $(x)(y) //~ ERROR expected one of: `*`, `+`, or `?` } } diff --git a/tests/ui/parser/macro/issue-33569.stderr b/tests/ui/parser/macro/issue-33569.stderr index d1b6abfeeebf..0d53c04c1c9f 100644 --- a/tests/ui/parser/macro/issue-33569.stderr +++ b/tests/ui/parser/macro/issue-33569.stderr @@ -5,7 +5,7 @@ LL | { $+ } => { | ^ error: expected one of: `*`, `+`, or `?` - --> $DIR/issue-33569.rs:6:13 + --> $DIR/issue-33569.rs:5:13 | LL | $(x)(y) | ^^^ @@ -15,27 +15,19 @@ error: missing fragment specifier | LL | { $+ } => { | ^ + | + = note: fragment specifiers must be provided + = help: valid fragment specifiers are `ident`, `block`, `stmt`, `expr`, `pat`, `ty`, `lifetime`, `literal`, `path`, `meta`, `tt`, `item` and `vis`, along with `expr_2021` and `pat_param` for edition compatibility +help: try adding a specifier here + | +LL | { $+:spec } => { + | +++++ error: missing fragment specifier --> $DIR/issue-33569.rs:2:8 | LL | { $+ } => { | ^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default error: aborting due to 4 previous errors -Future incompatibility report: Future breakage diagnostic: -error: missing fragment specifier - --> $DIR/issue-33569.rs:2:8 - | -LL | { $+ } => { - | ^ - | - = 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 #40107 - = note: `#[deny(missing_fragment_specifier)]` on by default - diff --git a/tests/ui/parser/misspelled-keywords/async-move.stderr b/tests/ui/parser/misspelled-keywords/async-move.stderr index 2507326fb285..26449a17f784 100644 --- a/tests/ui/parser/misspelled-keywords/async-move.stderr +++ b/tests/ui/parser/misspelled-keywords/async-move.stderr @@ -1,8 +1,8 @@ -error: expected one of `move`, `use`, `|`, or `||`, found `Move` +error: expected one of `move`, `use`, `{`, `|`, or `||`, found `Move` --> $DIR/async-move.rs:4:11 | LL | async Move {} - | ^^^^ expected one of `move`, `use`, `|`, or `||` + | ^^^^ expected one of `move`, `use`, `{`, `|`, or `||` | help: write keyword `move` in lowercase | diff --git a/tests/ui/print-calling-conventions.stdout b/tests/ui/print-calling-conventions.stdout index feee8cc3aa9c..7b5ae4956606 100644 --- a/tests/ui/print-calling-conventions.stdout +++ b/tests/ui/print-calling-conventions.stdout @@ -9,6 +9,7 @@ avr-interrupt avr-non-blocking-interrupt cdecl cdecl-unwind +custom efiapi fastcall fastcall-unwind diff --git a/tests/ui/proc-macro/derive-helper-legacy-limits.stderr b/tests/ui/proc-macro/derive-helper-legacy-limits.stderr index f5cd455435d4..df3c5c47ddb2 100644 --- a/tests/ui/proc-macro/derive-helper-legacy-limits.stderr +++ b/tests/ui/proc-macro/derive-helper-legacy-limits.stderr @@ -3,6 +3,12 @@ error: cannot find attribute `empty_helper` in this scope | LL | #[empty_helper] | ^^^^^^^^^^^^ + | +help: `empty_helper` is an attribute that can be used by the derive macro `Empty`, you might be missing a `derive` attribute + | +LL + #[derive(Empty)] +LL | struct S2; + | error: aborting due to 1 previous error diff --git a/tests/ui/proc-macro/derive-helper-shadowing.stderr b/tests/ui/proc-macro/derive-helper-shadowing.stderr index f284b1c54dd6..1206778bb235 100644 --- a/tests/ui/proc-macro/derive-helper-shadowing.stderr +++ b/tests/ui/proc-macro/derive-helper-shadowing.stderr @@ -16,6 +16,7 @@ error: cannot find attribute `empty_helper` in this scope LL | #[derive(GenHelperUse)] | ^^^^^^^^^^^^ | + = note: `empty_helper` is an attribute that can be used by the derive macro `Empty`, you might be missing a `derive` attribute = note: this error originates in the derive macro `GenHelperUse` (in Nightly builds, run with -Z macro-backtrace for more info) help: consider importing this attribute macro through its public re-export | @@ -31,6 +32,7 @@ LL | #[empty_helper] LL | gen_helper_use!(); | ----------------- in this macro invocation | + = note: `empty_helper` is an attribute that can be used by the derive macro `Empty`, you might be missing a `derive` attribute = note: this error originates in the macro `gen_helper_use` (in Nightly builds, run with -Z macro-backtrace for more info) help: consider importing this attribute macro through its public re-export | diff --git a/tests/ui/proc-macro/disappearing-resolution.stderr b/tests/ui/proc-macro/disappearing-resolution.stderr index 734e0cd2ab6d..6c0f1a52915f 100644 --- a/tests/ui/proc-macro/disappearing-resolution.stderr +++ b/tests/ui/proc-macro/disappearing-resolution.stderr @@ -3,6 +3,12 @@ error: cannot find attribute `empty_helper` in this scope | LL | #[empty_helper] | ^^^^^^^^^^^^ + | +help: `empty_helper` is an attribute that can be used by the derive macro `Empty`, you might be missing a `derive` attribute + | +LL + #[derive(Empty)] +LL | struct S; + | error[E0603]: derive macro import `Empty` is private --> $DIR/disappearing-resolution.rs:11:8 diff --git a/tests/ui/regions/regions-glb-free-free.stderr b/tests/ui/regions/regions-glb-free-free.stderr index 727669f26835..6ea09e3e1d76 100644 --- a/tests/ui/regions/regions-glb-free-free.stderr +++ b/tests/ui/regions/regions-glb-free-free.stderr @@ -1,8 +1,6 @@ error[E0621]: explicit lifetime required in the type of `s` --> $DIR/regions-glb-free-free.rs:15:13 | -LL | pub fn set_desc(self, s: &str) -> Flag<'a> { - | ---- help: add explicit lifetime `'a` to the type of `s`: `&'a str` LL | / Flag { LL | | name: self.name, LL | | desc: s, @@ -10,6 +8,11 @@ LL | | max_count: self.max_count, LL | | value: self.value LL | | } | |_____________^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `s` + | +LL | pub fn set_desc(self, s: &'a str) -> Flag<'a> { + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/regions/regions-infer-at-fn-not-param.stderr b/tests/ui/regions/regions-infer-at-fn-not-param.stderr index 4c7660276f2d..58ff2586a82c 100644 --- a/tests/ui/regions/regions-infer-at-fn-not-param.stderr +++ b/tests/ui/regions/regions-infer-at-fn-not-param.stderr @@ -2,9 +2,12 @@ error[E0621]: explicit lifetime required in the type of `p` --> $DIR/regions-infer-at-fn-not-param.rs:13:57 | LL | fn take1<'a>(p: Parameterized1) -> Parameterized1<'a> { p } - | -------------- ^ lifetime `'a` required - | | - | help: add explicit lifetime `'a` to the type of `p`: `Parameterized1<'a>` + | ^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `p` + | +LL | fn take1<'a>(p: Parameterized1<'a>) -> Parameterized1<'a> { p } + | ++++ error: aborting due to 1 previous error diff --git a/tests/ui/resolve/auxiliary/issue-80079.rs b/tests/ui/resolve/auxiliary/issue-80079.rs index 190ca75aba86..bfae5c5a24ee 100644 --- a/tests/ui/resolve/auxiliary/issue-80079.rs +++ b/tests/ui/resolve/auxiliary/issue-80079.rs @@ -1,7 +1,7 @@ #![crate_type = "lib"] pub mod public { - use private_import; + use crate::private_import; // should not be suggested since it is private struct Foo; diff --git a/tests/ui/resolve/auxiliary/privacy-struct-ctor.rs b/tests/ui/resolve/auxiliary/privacy-struct-ctor.rs index 6d0bc728524b..ac157a82e179 100644 --- a/tests/ui/resolve/auxiliary/privacy-struct-ctor.rs +++ b/tests/ui/resolve/auxiliary/privacy-struct-ctor.rs @@ -2,7 +2,7 @@ pub mod m { pub struct S(u8); pub mod n { - pub(in m) struct Z(pub(in m::n) u8); + pub(in crate::m) struct Z(pub(in crate::m::n) u8); } } diff --git a/tests/ui/resolve/extern-prelude-fail.rs b/tests/ui/resolve/extern-prelude-fail.rs index c0716f1ebf56..7d0df03e57bb 100644 --- a/tests/ui/resolve/extern-prelude-fail.rs +++ b/tests/ui/resolve/extern-prelude-fail.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ compile-flags:--extern extern_prelude //@ aux-build:extern-prelude.rs diff --git a/tests/ui/resolve/extern-prelude-fail.stderr b/tests/ui/resolve/extern-prelude-fail.stderr index 199a31244c06..b9668154f446 100644 --- a/tests/ui/resolve/extern-prelude-fail.stderr +++ b/tests/ui/resolve/extern-prelude-fail.stderr @@ -1,5 +1,5 @@ error[E0432]: unresolved import `extern_prelude` - --> $DIR/extern-prelude-fail.rs:7:9 + --> $DIR/extern-prelude-fail.rs:8:9 | LL | use extern_prelude::S; | ^^^^^^^^^^^^^^ use of unresolved module or unlinked crate `extern_prelude` @@ -10,7 +10,7 @@ LL + extern crate extern_prelude; | error[E0433]: failed to resolve: use of unresolved module or unlinked crate `extern_prelude` - --> $DIR/extern-prelude-fail.rs:8:15 + --> $DIR/extern-prelude-fail.rs:9:15 | LL | let s = ::extern_prelude::S; | ^^^^^^^^^^^^^^ use of unresolved module or unlinked crate `extern_prelude` diff --git a/tests/ui/resolve/global-scope-resolution.rs b/tests/ui/resolve/global-scope-resolution.rs new file mode 100644 index 000000000000..176bab36da7c --- /dev/null +++ b/tests/ui/resolve/global-scope-resolution.rs @@ -0,0 +1,21 @@ +//! Test global scope resolution with :: operator + +//@ run-pass + +pub fn f() -> isize { + return 1; +} + +pub mod foo { + pub fn f() -> isize { + return 2; + } + pub fn g() { + assert_eq!(f(), 2); + assert_eq!(::f(), 1); + } +} + +pub fn main() { + return foo::g(); +} diff --git a/tests/ui/resolve/issue-42944.rs b/tests/ui/resolve/issue-42944.rs index 7e439c10b7b8..24aa110329b2 100644 --- a/tests/ui/resolve/issue-42944.rs +++ b/tests/ui/resolve/issue-42944.rs @@ -3,7 +3,7 @@ mod foo { } mod bar { - use foo::Bx; + use crate::foo::Bx; fn foo() { Bx(()); diff --git a/tests/ui/resolve/issue-5035.rs b/tests/ui/resolve/issue-5035.rs index 82c4bc0d5ef9..a9e2509dde99 100644 --- a/tests/ui/resolve/issue-5035.rs +++ b/tests/ui/resolve/issue-5035.rs @@ -4,7 +4,7 @@ trait I {} type K = dyn I; impl K for isize {} //~ ERROR expected trait, found type alias `K` -use ImportError; //~ ERROR unresolved import `ImportError` [E0432] +use crate::ImportError; //~ ERROR unresolved import `crate::ImportError` [E0432] //~^ NOTE no `ImportError` in the root impl ImportError for () {} // check that this is not an additional error (cf. issue #35142) diff --git a/tests/ui/resolve/issue-5035.stderr b/tests/ui/resolve/issue-5035.stderr index f5717438fc8c..b26c962c9bb0 100644 --- a/tests/ui/resolve/issue-5035.stderr +++ b/tests/ui/resolve/issue-5035.stderr @@ -1,8 +1,8 @@ -error[E0432]: unresolved import `ImportError` +error[E0432]: unresolved import `crate::ImportError` --> $DIR/issue-5035.rs:7:5 | -LL | use ImportError; - | ^^^^^^^^^^^ no `ImportError` in the root +LL | use crate::ImportError; + | ^^^^^^^^^^^^^^^^^^ no `ImportError` in the root error[E0404]: expected trait, found type alias `K` --> $DIR/issue-5035.rs:5:6 diff --git a/tests/ui/resolve/nonexistent-macro.rs b/tests/ui/resolve/nonexistent-macro.rs new file mode 100644 index 000000000000..663075473a1c --- /dev/null +++ b/tests/ui/resolve/nonexistent-macro.rs @@ -0,0 +1,6 @@ +//! Test error handling for undefined macro calls + +fn main() { + iamnotanextensionthatexists!(""); + //~^ ERROR cannot find macro `iamnotanextensionthatexists` in this scope +} diff --git a/tests/ui/resolve/nonexistent-macro.stderr b/tests/ui/resolve/nonexistent-macro.stderr new file mode 100644 index 000000000000..7e89e07bf30b --- /dev/null +++ b/tests/ui/resolve/nonexistent-macro.stderr @@ -0,0 +1,8 @@ +error: cannot find macro `iamnotanextensionthatexists` in this scope + --> $DIR/nonexistent-macro.rs:4:5 + | +LL | iamnotanextensionthatexists!(""); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to 1 previous error + diff --git a/tests/ui/resolve/privacy-enum-ctor.rs b/tests/ui/resolve/privacy-enum-ctor.rs index f0d2cf8c04e9..3f79b12a267b 100644 --- a/tests/ui/resolve/privacy-enum-ctor.rs +++ b/tests/ui/resolve/privacy-enum-ctor.rs @@ -8,7 +8,7 @@ mod m { } pub mod n { - pub(in m) enum Z { + pub(in crate::m) enum Z { Fn(u8), Struct { s: u8, @@ -17,7 +17,7 @@ mod m { } } - use m::n::Z; // OK, only the type is imported + use crate::m::n::Z; // OK, only the type is imported fn f() { n::Z; diff --git a/tests/ui/resolve/privacy-enum-ctor.stderr b/tests/ui/resolve/privacy-enum-ctor.stderr index f349b9391d15..4ec1b6b97bd3 100644 --- a/tests/ui/resolve/privacy-enum-ctor.stderr +++ b/tests/ui/resolve/privacy-enum-ctor.stderr @@ -7,7 +7,7 @@ LL | n::Z; note: the enum is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | / pub(in m) enum Z { +LL | / pub(in crate::m) enum Z { LL | | Fn(u8), LL | | Struct { LL | | s: u8, @@ -35,7 +35,7 @@ LL | Z; note: the enum is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | / pub(in m) enum Z { +LL | / pub(in crate::m) enum Z { LL | | Fn(u8), LL | | Struct { LL | | s: u8, @@ -154,8 +154,8 @@ LL | let _: Z = m::n::Z; note: enum `m::Z` exists but is inaccessible --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ not accessible +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ not accessible error[E0423]: expected value, found enum `m::n::Z` --> $DIR/privacy-enum-ctor.rs:57:16 @@ -166,7 +166,7 @@ LL | let _: Z = m::n::Z; note: the enum is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | / pub(in m) enum Z { +LL | / pub(in crate::m) enum Z { LL | | Fn(u8), LL | | Struct { LL | | s: u8, @@ -197,8 +197,8 @@ LL | let _: Z = m::n::Z::Fn; note: enum `m::Z` exists but is inaccessible --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ not accessible +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ not accessible error[E0412]: cannot find type `Z` in this scope --> $DIR/privacy-enum-ctor.rs:64:12 @@ -212,8 +212,8 @@ LL | let _: Z = m::n::Z::Struct; note: enum `m::Z` exists but is inaccessible --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ not accessible +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ not accessible error[E0412]: cannot find type `Z` in this scope --> $DIR/privacy-enum-ctor.rs:68:12 @@ -227,8 +227,8 @@ LL | let _: Z = m::n::Z::Unit {}; note: enum `m::Z` exists but is inaccessible --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ not accessible +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ not accessible error[E0603]: enum `Z` is private --> $DIR/privacy-enum-ctor.rs:57:22 @@ -239,8 +239,8 @@ LL | let _: Z = m::n::Z; note: the enum `Z` is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ error[E0603]: enum `Z` is private --> $DIR/privacy-enum-ctor.rs:61:22 @@ -253,8 +253,8 @@ LL | let _: Z = m::n::Z::Fn; note: the enum `Z` is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ error[E0603]: enum `Z` is private --> $DIR/privacy-enum-ctor.rs:64:22 @@ -265,8 +265,8 @@ LL | let _: Z = m::n::Z::Struct; note: the enum `Z` is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ error[E0603]: enum `Z` is private --> $DIR/privacy-enum-ctor.rs:68:22 @@ -279,8 +279,8 @@ LL | let _: Z = m::n::Z::Unit {}; note: the enum `Z` is defined here --> $DIR/privacy-enum-ctor.rs:11:9 | -LL | pub(in m) enum Z { - | ^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) enum Z { + | ^^^^^^^^^^^^^^^^^^^^^^^ error[E0308]: mismatched types --> $DIR/privacy-enum-ctor.rs:27:20 diff --git a/tests/ui/resolve/privacy-struct-ctor.rs b/tests/ui/resolve/privacy-struct-ctor.rs index da0e9f2fc046..70c751999b7d 100644 --- a/tests/ui/resolve/privacy-struct-ctor.rs +++ b/tests/ui/resolve/privacy-struct-ctor.rs @@ -9,10 +9,10 @@ mod m { } pub mod n { - pub(in m) struct Z(pub(in m::n) u8); + pub(in crate::m) struct Z(pub(in crate::m::n) u8); } - use m::n::Z; // OK, only the type is imported + use crate::m::n::Z; // OK, only the type is imported fn f() { n::Z; diff --git a/tests/ui/resolve/privacy-struct-ctor.stderr b/tests/ui/resolve/privacy-struct-ctor.stderr index 1d8c741c964e..0a6b1b46afae 100644 --- a/tests/ui/resolve/privacy-struct-ctor.stderr +++ b/tests/ui/resolve/privacy-struct-ctor.stderr @@ -42,8 +42,8 @@ LL | pub struct S(u8); error[E0603]: tuple struct constructor `Z` is private --> $DIR/privacy-struct-ctor.rs:18:12 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | --------------- a constructor is private if any of the fields is private +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ---------------------- a constructor is private if any of the fields is private ... LL | n::Z; | ^ private tuple struct constructor @@ -51,12 +51,12 @@ LL | n::Z; note: the tuple struct constructor `Z` is defined here --> $DIR/privacy-struct-ctor.rs:12:9 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider making the field publicly accessible | -LL - pub(in m) struct Z(pub(in m::n) u8); -LL + pub(in m) struct Z(pub u8); +LL - pub(in crate::m) struct Z(pub(in crate::m::n) u8); +LL + pub(in crate::m) struct Z(pub u8); | error[E0603]: tuple struct constructor `S` is private @@ -100,8 +100,8 @@ LL | pub struct S(pub u8); error[E0603]: tuple struct constructor `Z` is private --> $DIR/privacy-struct-ctor.rs:35:11 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | --------------- a constructor is private if any of the fields is private +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ---------------------- a constructor is private if any of the fields is private ... LL | m::n::Z; | ^ private tuple struct constructor @@ -109,12 +109,12 @@ LL | m::n::Z; note: the tuple struct constructor `Z` is defined here --> $DIR/privacy-struct-ctor.rs:12:9 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider making the field publicly accessible | -LL - pub(in m) struct Z(pub(in m::n) u8); -LL + pub(in m) struct Z(pub u8); +LL - pub(in crate::m) struct Z(pub(in crate::m::n) u8); +LL + pub(in crate::m) struct Z(pub u8); | error[E0603]: tuple struct constructor `S` is private @@ -140,16 +140,16 @@ error[E0603]: tuple struct constructor `Z` is private LL | xcrate::m::n::Z; | ^ private tuple struct constructor | - ::: $DIR/auxiliary/privacy-struct-ctor.rs:5:28 + ::: $DIR/auxiliary/privacy-struct-ctor.rs:5:35 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | --------------- a constructor is private if any of the fields is private +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ---------------------- a constructor is private if any of the fields is private | note: the tuple struct constructor `Z` is defined here --> $DIR/auxiliary/privacy-struct-ctor.rs:5:9 | -LL | pub(in m) struct Z(pub(in m::n) u8); - | ^^^^^^^^^^^^^^^^^^ +LL | pub(in crate::m) struct Z(pub(in crate::m::n) u8); + | ^^^^^^^^^^^^^^^^^^^^^^^^^ error: aborting due to 10 previous errors diff --git a/tests/ui/resolve/resolve-bad-visibility.rs b/tests/ui/resolve/resolve-bad-visibility.rs index 7d48bb97b106..81635611fca9 100644 --- a/tests/ui/resolve/resolve-bad-visibility.rs +++ b/tests/ui/resolve/resolve-bad-visibility.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 enum E {} trait Tr {} diff --git a/tests/ui/resolve/resolve-bad-visibility.stderr b/tests/ui/resolve/resolve-bad-visibility.stderr index ac7e1c735b1f..c7bbdfbd2495 100644 --- a/tests/ui/resolve/resolve-bad-visibility.stderr +++ b/tests/ui/resolve/resolve-bad-visibility.stderr @@ -1,23 +1,23 @@ error[E0577]: expected module, found enum `E` - --> $DIR/resolve-bad-visibility.rs:4:8 + --> $DIR/resolve-bad-visibility.rs:5:8 | LL | pub(in E) struct S; | ^ not a module error[E0577]: expected module, found trait `Tr` - --> $DIR/resolve-bad-visibility.rs:5:8 + --> $DIR/resolve-bad-visibility.rs:6:8 | LL | pub(in Tr) struct Z; | ^^ not a module error[E0742]: visibilities can only be restricted to ancestor modules - --> $DIR/resolve-bad-visibility.rs:6:8 + --> $DIR/resolve-bad-visibility.rs:7:8 | LL | pub(in std::vec) struct F; | ^^^^^^^^ error[E0433]: failed to resolve: use of unresolved module or unlinked crate `nonexistent` - --> $DIR/resolve-bad-visibility.rs:7:8 + --> $DIR/resolve-bad-visibility.rs:8:8 | LL | pub(in nonexistent) struct G; | ^^^^^^^^^^^ use of unresolved module or unlinked crate `nonexistent` @@ -28,7 +28,7 @@ LL + extern crate nonexistent; | error[E0433]: failed to resolve: use of unresolved module or unlinked crate `too_soon` - --> $DIR/resolve-bad-visibility.rs:8:8 + --> $DIR/resolve-bad-visibility.rs:9:8 | LL | pub(in too_soon) struct H; | ^^^^^^^^ use of unresolved module or unlinked crate `too_soon` diff --git a/tests/ui/resolve/suggest-builder-fn.rs b/tests/ui/resolve/suggest-builder-fn.rs index 0d9b35549a47..959675ef2c99 100644 --- a/tests/ui/resolve/suggest-builder-fn.rs +++ b/tests/ui/resolve/suggest-builder-fn.rs @@ -32,7 +32,7 @@ impl Bar { } mod SomeMod { - use Bar; + use crate::Bar; impl Bar { // Public method. Should be suggested diff --git a/tests/ui/resolve/unresolved-segments-visibility.rs b/tests/ui/resolve/unresolved-segments-visibility.rs index c26171f75d2c..fc86b31adfc2 100644 --- a/tests/ui/resolve/unresolved-segments-visibility.rs +++ b/tests/ui/resolve/unresolved-segments-visibility.rs @@ -5,7 +5,7 @@ extern crate alloc as b; mod foo { mod bar { - pub(in b::string::String::newy) extern crate alloc as e; + pub(in crate::b::string::String::newy) extern crate alloc as e; //~^ ERROR failed to resolve: `String` is a struct, not a module [E0433] } } diff --git a/tests/ui/resolve/unresolved-segments-visibility.stderr b/tests/ui/resolve/unresolved-segments-visibility.stderr index 09f3c50258d9..082579c9fa11 100644 --- a/tests/ui/resolve/unresolved-segments-visibility.stderr +++ b/tests/ui/resolve/unresolved-segments-visibility.stderr @@ -1,8 +1,8 @@ error[E0433]: failed to resolve: `String` is a struct, not a module - --> $DIR/unresolved-segments-visibility.rs:8:27 + --> $DIR/unresolved-segments-visibility.rs:8:34 | -LL | pub(in b::string::String::newy) extern crate alloc as e; - | ^^^^^^ `String` is a struct, not a module +LL | pub(in crate::b::string::String::newy) extern crate alloc as e; + | ^^^^^^ `String` is a struct, not a module error: aborting due to 1 previous error diff --git a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.fixed b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.fixed index fbe415e2e10c..d685c4944baf 100644 --- a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.fixed +++ b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.rs b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.rs index 72a212453cdb..7a5ecf2720a5 100644 --- a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.rs +++ b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.stderr b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.stderr index 036b9ccab4f3..c0a322edcd64 100644 --- a/tests/ui/rust-2018/edition-lint-fully-qualified-paths.stderr +++ b/tests/ui/rust-2018/edition-lint-fully-qualified-paths.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-fully-qualified-paths.rs:18:25 + --> $DIR/edition-lint-fully-qualified-paths.rs:19:25 | LL | let _: ::Bar = (); | ^^^^^^^^^^ help: use `crate`: `crate::foo::Foo` @@ -7,13 +7,13 @@ LL | let _: ::Bar = (); = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/edition-lint-fully-qualified-paths.rs:3:9 + --> $DIR/edition-lint-fully-qualified-paths.rs:4:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-fully-qualified-paths.rs:18:25 + --> $DIR/edition-lint-fully-qualified-paths.rs:19:25 | LL | let _: ::Bar = (); | ^^^^^^^^^^ help: use `crate`: `crate::foo::Foo` @@ -23,7 +23,7 @@ LL | let _: ::Bar = (); = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-fully-qualified-paths.rs:24:13 + --> $DIR/edition-lint-fully-qualified-paths.rs:25:13 | LL | let _: <::foo::Baz as foo::Foo>::Bar = (); | ^^^^^^^^^^ help: use `crate`: `crate::foo::Baz` diff --git a/tests/ui/rust-2018/edition-lint-nested-empty-paths.fixed b/tests/ui/rust-2018/edition-lint-nested-empty-paths.fixed index 7ec421099c7a..4a584a55e648 100644 --- a/tests/ui/rust-2018/edition-lint-nested-empty-paths.fixed +++ b/tests/ui/rust-2018/edition-lint-nested-empty-paths.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-nested-empty-paths.rs b/tests/ui/rust-2018/edition-lint-nested-empty-paths.rs index 135908c8aef9..2baafbd9704e 100644 --- a/tests/ui/rust-2018/edition-lint-nested-empty-paths.rs +++ b/tests/ui/rust-2018/edition-lint-nested-empty-paths.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-nested-empty-paths.stderr b/tests/ui/rust-2018/edition-lint-nested-empty-paths.stderr index 4174c2fa9adf..041572be8441 100644 --- a/tests/ui/rust-2018/edition-lint-nested-empty-paths.stderr +++ b/tests/ui/rust-2018/edition-lint-nested-empty-paths.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-empty-paths.rs:16:5 + --> $DIR/edition-lint-nested-empty-paths.rs:17:5 | LL | use foo::{bar::{baz::{}}}; | ^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{bar::{baz::{}}}` @@ -7,13 +7,13 @@ LL | use foo::{bar::{baz::{}}}; = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/edition-lint-nested-empty-paths.rs:3:9 + --> $DIR/edition-lint-nested-empty-paths.rs:4:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-empty-paths.rs:20:5 + --> $DIR/edition-lint-nested-empty-paths.rs:21:5 | LL | use foo::{bar::{XX, baz::{}}}; | ^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{bar::{XX, baz::{}}}` @@ -22,7 +22,7 @@ LL | use foo::{bar::{XX, baz::{}}}; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-empty-paths.rs:20:5 + --> $DIR/edition-lint-nested-empty-paths.rs:21:5 | LL | use foo::{bar::{XX, baz::{}}}; | ^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{bar::{XX, baz::{}}}` @@ -32,7 +32,7 @@ LL | use foo::{bar::{XX, baz::{}}}; = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-empty-paths.rs:26:5 + --> $DIR/edition-lint-nested-empty-paths.rs:27:5 | LL | use foo::{bar::{baz::{}, baz1::{}}}; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{bar::{baz::{}, baz1::{}}}` @@ -41,7 +41,7 @@ LL | use foo::{bar::{baz::{}, baz1::{}}}; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-empty-paths.rs:26:5 + --> $DIR/edition-lint-nested-empty-paths.rs:27:5 | LL | use foo::{bar::{baz::{}, baz1::{}}}; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{bar::{baz::{}, baz1::{}}}` diff --git a/tests/ui/rust-2018/edition-lint-nested-paths.fixed b/tests/ui/rust-2018/edition-lint-nested-paths.fixed index 93ccb2fe6af2..bf0038c3be45 100644 --- a/tests/ui/rust-2018/edition-lint-nested-paths.fixed +++ b/tests/ui/rust-2018/edition-lint-nested-paths.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-nested-paths.rs b/tests/ui/rust-2018/edition-lint-nested-paths.rs index 1c1d21dbab91..87dc51a3745e 100644 --- a/tests/ui/rust-2018/edition-lint-nested-paths.rs +++ b/tests/ui/rust-2018/edition-lint-nested-paths.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![deny(absolute_paths_not_starting_with_crate)] diff --git a/tests/ui/rust-2018/edition-lint-nested-paths.stderr b/tests/ui/rust-2018/edition-lint-nested-paths.stderr index d059a2533a90..4a70bb7e5c87 100644 --- a/tests/ui/rust-2018/edition-lint-nested-paths.stderr +++ b/tests/ui/rust-2018/edition-lint-nested-paths.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-paths.rs:5:5 + --> $DIR/edition-lint-nested-paths.rs:6:5 | LL | use foo::{a, b}; | ^^^^^^^^^^^ help: use `crate`: `crate::foo::{a, b}` @@ -7,13 +7,13 @@ LL | use foo::{a, b}; = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/edition-lint-nested-paths.rs:3:9 + --> $DIR/edition-lint-nested-paths.rs:4:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-paths.rs:5:5 + --> $DIR/edition-lint-nested-paths.rs:6:5 | LL | use foo::{a, b}; | ^^^^^^^^^^^ help: use `crate`: `crate::foo::{a, b}` @@ -23,7 +23,7 @@ LL | use foo::{a, b}; = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-paths.rs:22:13 + --> $DIR/edition-lint-nested-paths.rs:23:13 | LL | use foo::{self as x, c}; | ^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{self as x, c}` @@ -32,7 +32,7 @@ LL | use foo::{self as x, c}; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-nested-paths.rs:22:13 + --> $DIR/edition-lint-nested-paths.rs:23:13 | LL | use foo::{self as x, c}; | ^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::{self as x, c}` diff --git a/tests/ui/rust-2018/edition-lint-paths.fixed b/tests/ui/rust-2018/edition-lint-paths.fixed index 014bf91886f7..9664b461161a 100644 --- a/tests/ui/rust-2018/edition-lint-paths.fixed +++ b/tests/ui/rust-2018/edition-lint-paths.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/edition-lint-paths.rs b/tests/ui/rust-2018/edition-lint-paths.rs index 0ecd090c1dff..39cdad3ab98b 100644 --- a/tests/ui/rust-2018/edition-lint-paths.rs +++ b/tests/ui/rust-2018/edition-lint-paths.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/edition-lint-paths.stderr b/tests/ui/rust-2018/edition-lint-paths.stderr index 553a3bfdaa8c..fde17338d98a 100644 --- a/tests/ui/rust-2018/edition-lint-paths.stderr +++ b/tests/ui/rust-2018/edition-lint-paths.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:11:9 + --> $DIR/edition-lint-paths.rs:12:9 | LL | use bar::Bar; | ^^^^^^^^ help: use `crate`: `crate::bar::Bar` @@ -7,13 +7,13 @@ LL | use bar::Bar; = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/edition-lint-paths.rs:4:9 + --> $DIR/edition-lint-paths.rs:5:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:18:9 + --> $DIR/edition-lint-paths.rs:19:9 | LL | use bar; | ^^^ help: use `crate`: `crate::bar` @@ -22,7 +22,7 @@ LL | use bar; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:24:9 + --> $DIR/edition-lint-paths.rs:25:9 | LL | use {main, Bar as SomethingElse}; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::{main, Bar as SomethingElse}` @@ -31,7 +31,7 @@ LL | use {main, Bar as SomethingElse}; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:24:9 + --> $DIR/edition-lint-paths.rs:25:9 | LL | use {main, Bar as SomethingElse}; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::{main, Bar as SomethingElse}` @@ -41,7 +41,7 @@ LL | use {main, Bar as SomethingElse}; = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:24:9 + --> $DIR/edition-lint-paths.rs:25:9 | LL | use {main, Bar as SomethingElse}; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::{main, Bar as SomethingElse}` @@ -51,7 +51,7 @@ LL | use {main, Bar as SomethingElse}; = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no` error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:39:5 + --> $DIR/edition-lint-paths.rs:40:5 | LL | use bar::Bar; | ^^^^^^^^ help: use `crate`: `crate::bar::Bar` @@ -60,7 +60,7 @@ LL | use bar::Bar; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:51:9 + --> $DIR/edition-lint-paths.rs:52:9 | LL | use *; | ^ help: use `crate`: `crate::*` @@ -69,7 +69,7 @@ LL | use *; = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:56:6 + --> $DIR/edition-lint-paths.rs:57:6 | LL | impl ::foo::SomeTrait for u32 {} | ^^^^^^^^^^^^^^^^ help: use `crate`: `crate::foo::SomeTrait` @@ -78,7 +78,7 @@ LL | impl ::foo::SomeTrait for u32 {} = note: for more information, see issue #53130 error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/edition-lint-paths.rs:61:13 + --> $DIR/edition-lint-paths.rs:62:13 | LL | let x = ::bar::Bar; | ^^^^^^^^^^ help: use `crate`: `crate::bar::Bar` diff --git a/tests/ui/rust-2018/extern-crate-rename.fixed b/tests/ui/rust-2018/extern-crate-rename.fixed index 36b528029903..b6b665f537e3 100644 --- a/tests/ui/rust-2018/extern-crate-rename.fixed +++ b/tests/ui/rust-2018/extern-crate-rename.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/extern-crate-rename.rs b/tests/ui/rust-2018/extern-crate-rename.rs index 725e3aaa0726..3257ab876e1e 100644 --- a/tests/ui/rust-2018/extern-crate-rename.rs +++ b/tests/ui/rust-2018/extern-crate-rename.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/extern-crate-rename.stderr b/tests/ui/rust-2018/extern-crate-rename.stderr index 6b2512080309..36986c89c62b 100644 --- a/tests/ui/rust-2018/extern-crate-rename.stderr +++ b/tests/ui/rust-2018/extern-crate-rename.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/extern-crate-rename.rs:11:5 + --> $DIR/extern-crate-rename.rs:12:5 | LL | use my_crate::foo; | ^^^^^^^^^^^^^ help: use `crate`: `crate::my_crate::foo` @@ -7,7 +7,7 @@ LL | use my_crate::foo; = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/extern-crate-rename.rs:7:9 + --> $DIR/extern-crate-rename.rs:8:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/tests/ui/rust-2018/extern-crate-submod.fixed b/tests/ui/rust-2018/extern-crate-submod.fixed index dc864d870392..8657960e9725 100644 --- a/tests/ui/rust-2018/extern-crate-submod.fixed +++ b/tests/ui/rust-2018/extern-crate-submod.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/extern-crate-submod.rs b/tests/ui/rust-2018/extern-crate-submod.rs index f15bc6bced8c..bf0a38d2b34e 100644 --- a/tests/ui/rust-2018/extern-crate-submod.rs +++ b/tests/ui/rust-2018/extern-crate-submod.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ aux-build:edition-lint-paths.rs //@ run-rustfix diff --git a/tests/ui/rust-2018/extern-crate-submod.stderr b/tests/ui/rust-2018/extern-crate-submod.stderr index 0d45d32d568b..85e26d72a673 100644 --- a/tests/ui/rust-2018/extern-crate-submod.stderr +++ b/tests/ui/rust-2018/extern-crate-submod.stderr @@ -1,5 +1,5 @@ error: absolute paths must start with `self`, `super`, `crate`, or an external crate name in the 2018 edition - --> $DIR/extern-crate-submod.rs:18:5 + --> $DIR/extern-crate-submod.rs:19:5 | LL | use m::edition_lint_paths::foo; | ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use `crate`: `crate::m::edition_lint_paths::foo` @@ -7,7 +7,7 @@ LL | use m::edition_lint_paths::foo; = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #53130 note: the lint level is defined here - --> $DIR/extern-crate-submod.rs:8:9 + --> $DIR/extern-crate-submod.rs:9:9 | LL | #![deny(absolute_paths_not_starting_with_crate)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/tests/ui/rust-2018/try-ident.fixed b/tests/ui/rust-2018/try-ident.fixed index b1c446e10226..b514c6d07565 100644 --- a/tests/ui/rust-2018/try-ident.fixed +++ b/tests/ui/rust-2018/try-ident.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix //@ check-pass diff --git a/tests/ui/rust-2018/try-ident.rs b/tests/ui/rust-2018/try-ident.rs index 8e62f698e252..2b8bb9234e55 100644 --- a/tests/ui/rust-2018/try-ident.rs +++ b/tests/ui/rust-2018/try-ident.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix //@ check-pass diff --git a/tests/ui/rust-2018/try-ident.stderr b/tests/ui/rust-2018/try-ident.stderr index eaf4c235697c..aca623d7d482 100644 --- a/tests/ui/rust-2018/try-ident.stderr +++ b/tests/ui/rust-2018/try-ident.stderr @@ -1,5 +1,5 @@ warning: `try` is a keyword in the 2018 edition - --> $DIR/try-ident.rs:7:5 + --> $DIR/try-ident.rs:8:5 | LL | try(); | ^^^ help: you can use a raw identifier to stay compatible: `r#try` @@ -7,14 +7,14 @@ LL | try(); = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #49716 note: the lint level is defined here - --> $DIR/try-ident.rs:4:9 + --> $DIR/try-ident.rs:5:9 | LL | #![warn(rust_2018_compatibility)] | ^^^^^^^^^^^^^^^^^^^^^^^ = note: `#[warn(keyword_idents_2018)]` implied by `#[warn(rust_2018_compatibility)]` warning: `try` is a keyword in the 2018 edition - --> $DIR/try-ident.rs:12:4 + --> $DIR/try-ident.rs:13:4 | LL | fn try() { | ^^^ help: you can use a raw identifier to stay compatible: `r#try` diff --git a/tests/ui/rust-2018/try-macro.fixed b/tests/ui/rust-2018/try-macro.fixed index 98c48d6b96f6..f2d8cf2bd9a5 100644 --- a/tests/ui/rust-2018/try-macro.fixed +++ b/tests/ui/rust-2018/try-macro.fixed @@ -1,5 +1,6 @@ // Test that `try!` macros are rewritten. +//@ edition: 2015 //@ run-rustfix //@ check-pass diff --git a/tests/ui/rust-2018/try-macro.rs b/tests/ui/rust-2018/try-macro.rs index 99480b2a3ec1..fec8eaa1786b 100644 --- a/tests/ui/rust-2018/try-macro.rs +++ b/tests/ui/rust-2018/try-macro.rs @@ -1,5 +1,6 @@ // Test that `try!` macros are rewritten. +//@ edition: 2015 //@ run-rustfix //@ check-pass diff --git a/tests/ui/rust-2018/try-macro.stderr b/tests/ui/rust-2018/try-macro.stderr index 095c755539db..20105e1868f2 100644 --- a/tests/ui/rust-2018/try-macro.stderr +++ b/tests/ui/rust-2018/try-macro.stderr @@ -1,5 +1,5 @@ warning: `try` is a keyword in the 2018 edition - --> $DIR/try-macro.rs:12:5 + --> $DIR/try-macro.rs:13:5 | LL | try!(x); | ^^^ help: you can use a raw identifier to stay compatible: `r#try` @@ -7,7 +7,7 @@ LL | try!(x); = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018! = note: for more information, see issue #49716 note: the lint level is defined here - --> $DIR/try-macro.rs:6:9 + --> $DIR/try-macro.rs:7:9 | LL | #![warn(rust_2018_compatibility)] | ^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/tests/ui/rustdoc/feature-gate-doc_primitive.rs b/tests/ui/rustdoc/feature-gate-doc_primitive.rs index 78fcd90752e4..dbf92f19378a 100644 --- a/tests/ui/rustdoc/feature-gate-doc_primitive.rs +++ b/tests/ui/rustdoc/feature-gate-doc_primitive.rs @@ -1,5 +1,7 @@ #[rustc_doc_primitive = "usize"] -//~^ ERROR `rustc_doc_primitive` is a rustc internal attribute +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_doc_primitive]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_doc_primitive]` attribute is used by the standard library to provide a way to generate documentation for primitive types /// Some docs mod usize {} diff --git a/tests/ui/rustdoc/feature-gate-doc_primitive.stderr b/tests/ui/rustdoc/feature-gate-doc_primitive.stderr index e74b1322b259..0b1af78b5041 100644 --- a/tests/ui/rustdoc/feature-gate-doc_primitive.stderr +++ b/tests/ui/rustdoc/feature-gate-doc_primitive.stderr @@ -1,11 +1,12 @@ -error[E0658]: `rustc_doc_primitive` is a rustc internal attribute +error[E0658]: use of an internal attribute --> $DIR/feature-gate-doc_primitive.rs:1:1 | LL | #[rustc_doc_primitive = "usize"] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_doc_primitive]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_doc_primitive]` attribute is used by the standard library to provide a way to generate documentation for primitive types error: aborting due to 1 previous error diff --git a/tests/ui/rustdoc/renamed-features-rustdoc_internals.rs b/tests/ui/rustdoc/renamed-features-rustdoc_internals.rs index 739c624d0c6f..2257130280dc 100644 --- a/tests/ui/rustdoc/renamed-features-rustdoc_internals.rs +++ b/tests/ui/rustdoc/renamed-features-rustdoc_internals.rs @@ -1,3 +1,5 @@ +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" + #![feature(doc_keyword)] //~ ERROR #![feature(doc_primitive)] //~ ERROR #![crate_type = "lib"] diff --git a/tests/ui/rustdoc/renamed-features-rustdoc_internals.stderr b/tests/ui/rustdoc/renamed-features-rustdoc_internals.stderr index d0979ce97ac8..9c664da8ee6c 100644 --- a/tests/ui/rustdoc/renamed-features-rustdoc_internals.stderr +++ b/tests/ui/rustdoc/renamed-features-rustdoc_internals.stderr @@ -1,17 +1,19 @@ error[E0557]: feature has been removed - --> $DIR/renamed-features-rustdoc_internals.rs:1:12 + --> $DIR/renamed-features-rustdoc_internals.rs:3:12 | LL | #![feature(doc_keyword)] | ^^^^^^^^^^^ feature has been removed | + = note: removed in 1.58.0 (you are using $RUSTC_VERSION); see for more information = note: merged into `#![feature(rustdoc_internals)]` error[E0557]: feature has been removed - --> $DIR/renamed-features-rustdoc_internals.rs:2:12 + --> $DIR/renamed-features-rustdoc_internals.rs:4:12 | LL | #![feature(doc_primitive)] | ^^^^^^^^^^^^^ feature has been removed | + = note: removed in 1.58.0 (you are using $RUSTC_VERSION); see for more information = note: merged into `#![feature(rustdoc_internals)]` error: aborting due to 2 previous errors diff --git a/tests/ui/self/self-shadowing-import.rs b/tests/ui/self/self-shadowing-import.rs index 85574daad5fd..78d04e0713aa 100644 --- a/tests/ui/self/self-shadowing-import.rs +++ b/tests/ui/self/self-shadowing-import.rs @@ -9,7 +9,7 @@ mod a { } mod c { - use a::b::a; + use crate::a::b::a; pub fn bar() { assert_eq!(a::foo(), 1); } } diff --git a/tests/ui/sepcomp/auxiliary/sepcomp_lib.rs b/tests/ui/sepcomp/auxiliary/sepcomp_lib.rs index 59efb3f790b8..a0d91c5dc87c 100644 --- a/tests/ui/sepcomp/auxiliary/sepcomp_lib.rs +++ b/tests/ui/sepcomp/auxiliary/sepcomp_lib.rs @@ -13,8 +13,8 @@ pub mod b { } pub mod c { - use a::one; - use b::two; + use crate::a::one; + use crate::b::two; pub fn three() -> usize { one() + two() } diff --git a/tests/ui/sepcomp/sepcomp-extern.rs b/tests/ui/sepcomp/sepcomp-extern.rs index 6acd3a1eede3..d0756c5f19a7 100644 --- a/tests/ui/sepcomp/sepcomp-extern.rs +++ b/tests/ui/sepcomp/sepcomp-extern.rs @@ -16,13 +16,13 @@ fn call1() -> usize { mod a { pub fn call2() -> usize { - unsafe { ::foo() } + unsafe { crate::foo() } } } mod b { pub fn call3() -> usize { - unsafe { ::foo() } + unsafe { crate::foo() } } } diff --git a/tests/ui/sepcomp/sepcomp-fns-backwards.rs b/tests/ui/sepcomp/sepcomp-fns-backwards.rs index 35326d19d6e3..c671771babb2 100644 --- a/tests/ui/sepcomp/sepcomp-fns-backwards.rs +++ b/tests/ui/sepcomp/sepcomp-fns-backwards.rs @@ -12,13 +12,13 @@ fn pad() -> usize { 0 } mod b { pub fn three() -> usize { - ::one() + ::a::two() + crate::one() + crate::a::two() } } mod a { pub fn two() -> usize { - ::one() + ::one() + crate::one() + crate::one() } } diff --git a/tests/ui/sepcomp/sepcomp-fns.rs b/tests/ui/sepcomp/sepcomp-fns.rs index 399193e69b65..1486a2471b85 100644 --- a/tests/ui/sepcomp/sepcomp-fns.rs +++ b/tests/ui/sepcomp/sepcomp-fns.rs @@ -13,13 +13,13 @@ fn one() -> usize { 1 } mod a { pub fn two() -> usize { - ::one() + ::one() + crate::one() + crate::one() } } mod b { pub fn three() -> usize { - ::one() + ::a::two() + crate::one() + crate::a::two() } } diff --git a/tests/ui/sepcomp/sepcomp-statics.rs b/tests/ui/sepcomp/sepcomp-statics.rs index 580bb628da68..3fe897f3c30b 100644 --- a/tests/ui/sepcomp/sepcomp-statics.rs +++ b/tests/ui/sepcomp/sepcomp-statics.rs @@ -15,13 +15,13 @@ mod b { // that `a` and `b` don't go into the same compilation unit. fn pad() -> usize { 0 } - pub static THREE: usize = ::ONE + ::a::TWO; + pub static THREE: usize = crate::ONE + crate::a::TWO; } mod a { fn pad() -> usize { 0 } - pub const TWO: usize = ::ONE + ::ONE; + pub const TWO: usize = crate::ONE + crate::ONE; } fn main() { diff --git a/tests/ui/sepcomp/sepcomp-unwind.rs b/tests/ui/sepcomp/sepcomp-unwind.rs index 8c25278bb7ec..95591676b5ee 100644 --- a/tests/ui/sepcomp/sepcomp-unwind.rs +++ b/tests/ui/sepcomp/sepcomp-unwind.rs @@ -26,10 +26,10 @@ mod a { mod b { pub fn g() { - ::a::f(); + crate::a::f(); } } fn main() { - thread::spawn(move|| { ::b::g() }).join().unwrap_err(); + thread::spawn(move|| { b::g() }).join().unwrap_err(); } diff --git a/tests/ui/shadowed-use-visibility.rs b/tests/ui/shadowed-use-visibility.rs index 66181267f98a..5ce4103b5597 100644 --- a/tests/ui/shadowed-use-visibility.rs +++ b/tests/ui/shadowed-use-visibility.rs @@ -5,7 +5,7 @@ mod foo { pub fn f() {} pub use self::f as bar; - use foo as bar; + use crate::foo as bar; } fn main() { diff --git a/tests/ui/shadowed/shadowed-trait-methods.rs b/tests/ui/shadowed/shadowed-trait-methods.rs index f9c25d979131..6cc5159fd089 100644 --- a/tests/ui/shadowed/shadowed-trait-methods.rs +++ b/tests/ui/shadowed/shadowed-trait-methods.rs @@ -5,7 +5,7 @@ mod foo { impl T for () {} } -mod bar { pub use foo::T; } +mod bar { pub use crate::foo::T; } fn main() { pub use bar::*; diff --git a/tests/ui/shadowed/shadowed-use-visibility.rs b/tests/ui/shadowed/shadowed-use-visibility.rs index 6b801972f417..070aeaf14670 100644 --- a/tests/ui/shadowed/shadowed-use-visibility.rs +++ b/tests/ui/shadowed/shadowed-use-visibility.rs @@ -1,15 +1,15 @@ mod foo { pub fn f() {} - use foo as bar; + use crate::foo as bar; pub use self::f as bar; } mod bar { - use foo::bar::f as g; //~ ERROR module import `bar` is private + use crate::foo::bar::f as g; //~ ERROR module import `bar` is private - use foo as f; - pub use foo::*; + use crate::foo as f; + pub use crate::foo::*; } use bar::f::f; //~ ERROR module import `f` is private diff --git a/tests/ui/shadowed/shadowed-use-visibility.stderr b/tests/ui/shadowed/shadowed-use-visibility.stderr index 1a642ae6e8ed..b062341dc8be 100644 --- a/tests/ui/shadowed/shadowed-use-visibility.stderr +++ b/tests/ui/shadowed/shadowed-use-visibility.stderr @@ -1,14 +1,14 @@ error[E0603]: module import `bar` is private - --> $DIR/shadowed-use-visibility.rs:9:14 + --> $DIR/shadowed-use-visibility.rs:9:21 | -LL | use foo::bar::f as g; - | ^^^ private module import +LL | use crate::foo::bar::f as g; + | ^^^ private module import | note: the module import `bar` is defined here... --> $DIR/shadowed-use-visibility.rs:4:9 | -LL | use foo as bar; - | ^^^^^^^^^^ +LL | use crate::foo as bar; + | ^^^^^^^^^^^^^^^^^ note: ...and refers to the module `foo` which is defined here --> $DIR/shadowed-use-visibility.rs:1:1 | @@ -24,8 +24,8 @@ LL | use bar::f::f; note: the module import `f` is defined here... --> $DIR/shadowed-use-visibility.rs:11:9 | -LL | use foo as f; - | ^^^^^^^^ +LL | use crate::foo as f; + | ^^^^^^^^^^^^^^^ note: ...and refers to the module `foo` which is defined here --> $DIR/shadowed-use-visibility.rs:1:1 | diff --git a/tests/ui/simd/size-align.rs b/tests/ui/simd/size-align.rs index ff23ea5980ba..53acb686fb84 100644 --- a/tests/ui/simd/size-align.rs +++ b/tests/ui/simd/size-align.rs @@ -7,12 +7,12 @@ use std::mem; -/// `T` should satisfy `size_of T (mod min_align_of T) === 0` to be stored at `Vec` properly +/// `T` should satisfy `size_of T (mod align_of T) === 0` to be stored at `Vec` properly /// Please consult the issue #20460 fn check() { - assert_eq!(mem::size_of::() % mem::min_align_of::(), 0); - assert_eq!(mem::size_of::() % mem::min_align_of::(), 0); - assert_eq!(mem::size_of::() % mem::min_align_of::(), 0); + assert_eq!(mem::size_of::() % mem::align_of::(), 0); + assert_eq!(mem::size_of::() % mem::align_of::(), 0); + assert_eq!(mem::size_of::() % mem::align_of::(), 0); } #[repr(simd)] diff --git a/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs b/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs index 66a432be3573..baa664d59339 100644 --- a/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs +++ b/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs @@ -1,3 +1,5 @@ +//@ edition: 2015 + #![warn(rust_2021_incompatible_closure_captures)] fn main() {} diff --git a/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.stderr b/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.stderr index 5ecbedf18678..00b9a81b27d9 100644 --- a/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.stderr +++ b/tests/ui/span/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.stderr @@ -1,5 +1,5 @@ error[E0670]: `async fn` is not permitted in Rust 2015 - --> $DIR/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs:8:16 + --> $DIR/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs:10:16 | LL | pub(crate) async fn new( | ^^^^^ to use `async fn`, switch to Rust 2018 or later @@ -8,7 +8,7 @@ LL | pub(crate) async fn new( = note: for more on editions, read https://doc.rust-lang.org/edition-guide error[E0412]: cannot find type `Duration` in this scope - --> $DIR/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs:10:19 + --> $DIR/drop-location-span-error-rust-2021-incompatible-closure-captures-96258.rs:12:19 | LL | interval: Duration, | ^^^^^^^^ not found in this scope diff --git a/tests/ui/span/dropck_arr_cycle_checked.rs b/tests/ui/span/dropck_arr_cycle_checked.rs index a14db5ff0896..adecb3f59424 100644 --- a/tests/ui/span/dropck_arr_cycle_checked.rs +++ b/tests/ui/span/dropck_arr_cycle_checked.rs @@ -19,7 +19,7 @@ mod s { } mod id { - use s; + use crate::s; #[derive(Debug)] pub struct Id { orig_count: usize, diff --git a/tests/ui/span/dropck_vec_cycle_checked.rs b/tests/ui/span/dropck_vec_cycle_checked.rs index c5d21507d76c..b015131caf16 100644 --- a/tests/ui/span/dropck_vec_cycle_checked.rs +++ b/tests/ui/span/dropck_vec_cycle_checked.rs @@ -16,7 +16,7 @@ mod s { } mod id { - use s; + use crate::s; #[derive(Debug)] pub struct Id { orig_count: usize, diff --git a/tests/ui/span/vec-must-not-hide-type-from-dropck.rs b/tests/ui/span/vec-must-not-hide-type-from-dropck.rs index 9bfbfab06a0a..972ffef2e3c8 100644 --- a/tests/ui/span/vec-must-not-hide-type-from-dropck.rs +++ b/tests/ui/span/vec-must-not-hide-type-from-dropck.rs @@ -31,7 +31,7 @@ mod s { } mod id { - use s; + use crate::s; /// Id represents a globally unique identifier (global across the /// current process, that is). When dropped, it automatically diff --git a/tests/ui/span/visibility-ty-params.rs b/tests/ui/span/visibility-ty-params.rs index 11c2cf44cb45..05d93e546360 100644 --- a/tests/ui/span/visibility-ty-params.rs +++ b/tests/ui/span/visibility-ty-params.rs @@ -3,11 +3,11 @@ macro_rules! m { } struct S(T); -m!{ S } //~ ERROR unexpected generic arguments in path - //~| ERROR failed to resolve: `S` is a struct, not a module [E0433] +m!{ crate::S } //~ ERROR unexpected generic arguments in path + //~| ERROR failed to resolve: `S` is a struct, not a module [E0433] mod m { - m!{ m<> } //~ ERROR unexpected generic arguments in path + m!{ crate::m<> } //~ ERROR unexpected generic arguments in path } fn main() {} diff --git a/tests/ui/span/visibility-ty-params.stderr b/tests/ui/span/visibility-ty-params.stderr index 97d05c4644e8..7b02d79a1bc2 100644 --- a/tests/ui/span/visibility-ty-params.stderr +++ b/tests/ui/span/visibility-ty-params.stderr @@ -1,20 +1,20 @@ error: unexpected generic arguments in path - --> $DIR/visibility-ty-params.rs:6:6 + --> $DIR/visibility-ty-params.rs:6:13 | -LL | m!{ S } - | ^^^^ +LL | m!{ crate::S } + | ^^^^ error[E0433]: failed to resolve: `S` is a struct, not a module - --> $DIR/visibility-ty-params.rs:6:5 + --> $DIR/visibility-ty-params.rs:6:12 | -LL | m!{ S } - | ^ `S` is a struct, not a module +LL | m!{ crate::S } + | ^ `S` is a struct, not a module error: unexpected generic arguments in path - --> $DIR/visibility-ty-params.rs:10:10 + --> $DIR/visibility-ty-params.rs:10:17 | -LL | m!{ m<> } - | ^^ +LL | m!{ crate::m<> } + | ^^ error: aborting due to 3 previous errors diff --git a/tests/ui/auxiliary/pub-and-stability.rs b/tests/ui/stability-attribute/auxiliary/pub-and-stability.rs similarity index 100% rename from tests/ui/auxiliary/pub-and-stability.rs rename to tests/ui/stability-attribute/auxiliary/pub-and-stability.rs diff --git a/tests/ui/stability-attribute/renamed_feature.rs b/tests/ui/stability-attribute/renamed_feature.rs new file mode 100644 index 000000000000..249c2abecff0 --- /dev/null +++ b/tests/ui/stability-attribute/renamed_feature.rs @@ -0,0 +1,3 @@ +#![feature(try_trait)] //~ ERROR feature `try_trait` has been renamed to `try_trait_v2` [E0635] + +fn main() {} diff --git a/tests/ui/stability-attribute/renamed_feature.stderr b/tests/ui/stability-attribute/renamed_feature.stderr new file mode 100644 index 000000000000..293a2feffb22 --- /dev/null +++ b/tests/ui/stability-attribute/renamed_feature.stderr @@ -0,0 +1,9 @@ +error[E0635]: feature `try_trait` has been renamed to `try_trait_v2` + --> $DIR/renamed_feature.rs:1:12 + | +LL | #![feature(try_trait)] + | ^^^^^^^^^ + +error: aborting due to 1 previous error + +For more information about this error, try `rustc --explain E0635`. diff --git a/tests/ui/explore-issue-38412.rs b/tests/ui/stability-attribute/stability-privacy-interaction.rs similarity index 64% rename from tests/ui/explore-issue-38412.rs rename to tests/ui/stability-attribute/stability-privacy-interaction.rs index 2008b120faae..e02816ae1e73 100644 --- a/tests/ui/explore-issue-38412.rs +++ b/tests/ui/stability-attribute/stability-privacy-interaction.rs @@ -1,28 +1,39 @@ +//! Regression test for issue #38412: interaction between stability attributes and privacy +//! +//! Tests that the compiler correctly handles the interaction between feature gates +//! and privacy/visibility rules. Specifically verifies that enabled unstable features +//! are accessible while disabled ones are properly rejected. + //@ aux-build:pub-and-stability.rs -// A big point of this test is that we *enable* `unstable_declared`, -// but do *not* enable `unstable_undeclared`. This way we can check -// that the compiler is letting in uses of enabled feature-gated -// stuff but still rejecting uses of disabled feature-gated stuff. +// Enable `unstable_declared` but not `unstable_undeclared` to test +// that the compiler allows enabled features but rejects disabled ones #![feature(unstable_declared)] extern crate pub_and_stability; use pub_and_stability::{Record, Trait, Tuple}; fn main() { - // Okay + // Test struct field access patterns let Record { .. } = Record::new(); - // Okay - let Record { a_stable_pub: _, a_unstable_declared_pub: _, .. } = Record::new(); + let Record { + a_stable_pub: _, + a_unstable_declared_pub: _, + .. + } = Record::new(); - let Record { a_stable_pub: _, a_unstable_declared_pub: _, a_unstable_undeclared_pub: _, .. } = - Record::new(); - //~^^ ERROR use of unstable library feature `unstable_undeclared` + let Record { + a_stable_pub: _, + a_unstable_declared_pub: _, + a_unstable_undeclared_pub: _, //~ ERROR use of unstable library feature `unstable_undeclared` + .. + } = Record::new(); let r = Record::new(); let t = Tuple::new(); + // Test field access with different stability/privacy combinations r.a_stable_pub; r.a_unstable_declared_pub; r.a_unstable_undeclared_pub; //~ ERROR use of unstable library feature @@ -37,10 +48,12 @@ fn main() { t.4; //~ ERROR is private t.5; //~ ERROR is private + // Test trait method access r.stable_trait_method(); r.unstable_declared_trait_method(); r.unstable_undeclared_trait_method(); //~ ERROR use of unstable library feature + // Test inherent method access r.stable(); r.unstable_declared(); r.unstable_undeclared(); //~ ERROR use of unstable library feature @@ -49,6 +62,7 @@ fn main() { r.pub_mod(); //~ ERROR `pub_mod` is private r.private(); //~ ERROR `private` is private + // Repeat tests for tuple struct let t = Tuple::new(); t.stable_trait_method(); t.unstable_declared_trait_method(); diff --git a/tests/ui/explore-issue-38412.stderr b/tests/ui/stability-attribute/stability-privacy-interaction.stderr similarity index 84% rename from tests/ui/explore-issue-38412.stderr rename to tests/ui/stability-attribute/stability-privacy-interaction.stderr index fca5c738d276..991b3dbe0191 100644 --- a/tests/ui/explore-issue-38412.stderr +++ b/tests/ui/stability-attribute/stability-privacy-interaction.stderr @@ -1,15 +1,15 @@ error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:19:63 + --> $DIR/stability-privacy-interaction.rs:29:9 | -LL | let Record { a_stable_pub: _, a_unstable_declared_pub: _, a_unstable_undeclared_pub: _, .. } = - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | a_unstable_undeclared_pub: _, + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = note: see issue #38412 for more information = help: add `#![feature(unstable_undeclared)]` to the crate attributes to enable = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:28:5 + --> $DIR/stability-privacy-interaction.rs:39:5 | LL | r.a_unstable_undeclared_pub; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -19,25 +19,25 @@ LL | r.a_unstable_undeclared_pub; = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0616]: field `b_crate` of struct `Record` is private - --> $DIR/explore-issue-38412.rs:29:7 + --> $DIR/stability-privacy-interaction.rs:40:7 | LL | r.b_crate; | ^^^^^^^ private field error[E0616]: field `c_mod` of struct `Record` is private - --> $DIR/explore-issue-38412.rs:30:7 + --> $DIR/stability-privacy-interaction.rs:41:7 | LL | r.c_mod; | ^^^^^ private field error[E0616]: field `d_priv` of struct `Record` is private - --> $DIR/explore-issue-38412.rs:31:7 + --> $DIR/stability-privacy-interaction.rs:42:7 | LL | r.d_priv; | ^^^^^^ private field error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:35:5 + --> $DIR/stability-privacy-interaction.rs:46:5 | LL | t.2; | ^^^ @@ -47,25 +47,25 @@ LL | t.2; = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0616]: field `3` of struct `pub_and_stability::Tuple` is private - --> $DIR/explore-issue-38412.rs:36:7 + --> $DIR/stability-privacy-interaction.rs:47:7 | LL | t.3; | ^ private field error[E0616]: field `4` of struct `pub_and_stability::Tuple` is private - --> $DIR/explore-issue-38412.rs:37:7 + --> $DIR/stability-privacy-interaction.rs:48:7 | LL | t.4; | ^ private field error[E0616]: field `5` of struct `pub_and_stability::Tuple` is private - --> $DIR/explore-issue-38412.rs:38:7 + --> $DIR/stability-privacy-interaction.rs:49:7 | LL | t.5; | ^ private field error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:42:7 + --> $DIR/stability-privacy-interaction.rs:54:7 | LL | r.unstable_undeclared_trait_method(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -75,7 +75,7 @@ LL | r.unstable_undeclared_trait_method(); = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:46:7 + --> $DIR/stability-privacy-interaction.rs:59:7 | LL | r.unstable_undeclared(); | ^^^^^^^^^^^^^^^^^^^ @@ -85,7 +85,7 @@ LL | r.unstable_undeclared(); = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0624]: method `pub_crate` is private - --> $DIR/explore-issue-38412.rs:48:7 + --> $DIR/stability-privacy-interaction.rs:61:7 | LL | r.pub_crate(); | ^^^^^^^^^ private method @@ -96,7 +96,7 @@ LL | pub(crate) fn pub_crate(&self) -> i32 { self.d_priv } | ------------------------------------- private method defined here error[E0624]: method `pub_mod` is private - --> $DIR/explore-issue-38412.rs:49:7 + --> $DIR/stability-privacy-interaction.rs:62:7 | LL | r.pub_mod(); | ^^^^^^^ private method @@ -107,7 +107,7 @@ LL | pub(in crate::m) fn pub_mod(&self) -> i32 { self.d_priv } | ----------------------------------------- private method defined here error[E0624]: method `private` is private - --> $DIR/explore-issue-38412.rs:50:7 + --> $DIR/stability-privacy-interaction.rs:63:7 | LL | r.private(); | ^^^^^^^ private method @@ -118,7 +118,7 @@ LL | fn private(&self) -> i32 { self.d_priv } | ------------------------ private method defined here error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:55:7 + --> $DIR/stability-privacy-interaction.rs:69:7 | LL | t.unstable_undeclared_trait_method(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -128,7 +128,7 @@ LL | t.unstable_undeclared_trait_method(); = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0658]: use of unstable library feature `unstable_undeclared` - --> $DIR/explore-issue-38412.rs:59:7 + --> $DIR/stability-privacy-interaction.rs:73:7 | LL | t.unstable_undeclared(); | ^^^^^^^^^^^^^^^^^^^ @@ -138,7 +138,7 @@ LL | t.unstable_undeclared(); = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date error[E0624]: method `pub_crate` is private - --> $DIR/explore-issue-38412.rs:61:7 + --> $DIR/stability-privacy-interaction.rs:75:7 | LL | t.pub_crate(); | ^^^^^^^^^ private method @@ -149,7 +149,7 @@ LL | pub(crate) fn pub_crate(&self) -> i32 { self.0 } | ------------------------------------- private method defined here error[E0624]: method `pub_mod` is private - --> $DIR/explore-issue-38412.rs:62:7 + --> $DIR/stability-privacy-interaction.rs:76:7 | LL | t.pub_mod(); | ^^^^^^^ private method @@ -160,7 +160,7 @@ LL | pub(in crate::m) fn pub_mod(&self) -> i32 { self.0 } | ----------------------------------------- private method defined here error[E0624]: method `private` is private - --> $DIR/explore-issue-38412.rs:63:7 + --> $DIR/stability-privacy-interaction.rs:77:7 | LL | t.private(); | ^^^^^^^ private method diff --git a/tests/ui/static/auxiliary/static_priv_by_default.rs b/tests/ui/static/auxiliary/static_priv_by_default.rs index 39f912066ece..fe9aef42feb2 100644 --- a/tests/ui/static/auxiliary/static_priv_by_default.rs +++ b/tests/ui/static/auxiliary/static_priv_by_default.rs @@ -31,11 +31,11 @@ mod foo { } pub mod bar { - pub use foo::reexported_a as e; - pub use foo::reexported_b as f; - pub use foo::reexported_c as g; - pub use foo::reexported_d as h; - pub use foo::reexported_e as i; + pub use crate::foo::reexported_a as e; + pub use crate::foo::reexported_b as f; + pub use crate::foo::reexported_c as g; + pub use crate::foo::reexported_d as h; + pub use crate::foo::reexported_e as i; } pub static a: isize = 0; diff --git a/tests/ui/static/static-extern-type.rs b/tests/ui/static/static-extern-type.rs index 8b022a5c31c3..2597c22ed7e8 100644 --- a/tests/ui/static/static-extern-type.rs +++ b/tests/ui/static/static-extern-type.rs @@ -10,7 +10,7 @@ pub mod a { pub mod b { #[repr(transparent)] - pub struct TransparentType(::a::StartFn); + pub struct TransparentType(crate::a::StartFn); extern "C" { pub static start: TransparentType; } @@ -18,7 +18,7 @@ pub mod b { pub mod c { #[repr(C)] - pub struct CType(u32, ::b::TransparentType); + pub struct CType(u32, crate::b::TransparentType); extern "C" { pub static start: CType; } diff --git a/tests/ui/statics/auxiliary/static_fn_inline_xc_aux.rs b/tests/ui/statics/auxiliary/static_fn_inline_xc_aux.rs index 8d0f7f61ced1..a739e8f2dbe6 100644 --- a/tests/ui/statics/auxiliary/static_fn_inline_xc_aux.rs +++ b/tests/ui/statics/auxiliary/static_fn_inline_xc_aux.rs @@ -5,7 +5,7 @@ pub mod num { } pub mod f64 { - impl ::num::Num2 for f64 { + impl crate::num::Num2 for f64 { #[inline] fn from_int2(n: isize) -> f64 { return n as f64; } } diff --git a/tests/ui/statics/auxiliary/static_fn_trait_xc_aux.rs b/tests/ui/statics/auxiliary/static_fn_trait_xc_aux.rs index b8aed2c5f54d..ab73bac3bf81 100644 --- a/tests/ui/statics/auxiliary/static_fn_trait_xc_aux.rs +++ b/tests/ui/statics/auxiliary/static_fn_trait_xc_aux.rs @@ -5,7 +5,7 @@ pub mod num { } pub mod f64 { - impl ::num::Num2 for f64 { + impl crate::num::Num2 for f64 { fn from_int2(n: isize) -> f64 { return n as f64; } } } diff --git a/tests/ui/statics/static-impl.rs b/tests/ui/statics/static-impl.rs index 37f3cd131333..5c8d20da0c68 100644 --- a/tests/ui/statics/static-impl.rs +++ b/tests/ui/statics/static-impl.rs @@ -9,12 +9,12 @@ pub trait plus { } mod a { - use plus; + use crate::plus; impl plus for usize { fn plus(&self) -> isize { *self as isize + 20 } } } mod b { - use plus; + use crate::plus; impl plus for String { fn plus(&self) -> isize { 200 } } } diff --git a/tests/ui/stats/auxiliary/include.rs b/tests/ui/stats/auxiliary/include.rs new file mode 100644 index 000000000000..7fb7c7811376 --- /dev/null +++ b/tests/ui/stats/auxiliary/include.rs @@ -0,0 +1,3 @@ +fn zzz(x: u32) -> u32 { + x +} diff --git a/tests/ui/stats/input-stats.stderr b/tests/ui/stats/input-stats.stderr index f2598bd7eaf8..88f91bef30b1 100644 --- a/tests/ui/stats/input-stats.stderr +++ b/tests/ui/stats/input-stats.stderr @@ -82,10 +82,10 @@ hir-stats - Expr 32 (NN.N%) 1 hir-stats - Let 32 (NN.N%) 1 hir-stats - Semi 32 (NN.N%) 1 hir-stats FnDecl 120 (NN.N%) 3 40 -hir-stats Attribute 128 (NN.N%) 4 32 hir-stats FieldDef 128 (NN.N%) 2 64 hir-stats GenericArgs 144 (NN.N%) 3 48 hir-stats Variant 144 (NN.N%) 2 72 +hir-stats Attribute 160 (NN.N%) 4 40 hir-stats GenericBound 256 (NN.N%) 4 64 hir-stats - Trait 256 (NN.N%) 4 hir-stats Block 288 (NN.N%) 6 48 @@ -117,5 +117,5 @@ hir-stats - Use 352 (NN.N%) 4 hir-stats Path 1_040 (NN.N%) 26 40 hir-stats PathSegment 1_776 (NN.N%) 37 48 hir-stats ---------------------------------------------------------------- -hir-stats Total 8_644 172 +hir-stats Total 8_676 172 hir-stats diff --git a/tests/ui/stats/macro-stats.rs b/tests/ui/stats/macro-stats.rs new file mode 100644 index 000000000000..ee265d682fd6 --- /dev/null +++ b/tests/ui/stats/macro-stats.rs @@ -0,0 +1,130 @@ +//@ check-pass +//@ compile-flags: -Zmacro-stats + +#[test] +fn test_foo() { + let what = "this"; + let how = "completely"; + let when = "immediately"; + println!("{what} disappears {how} and {when}"); +} + +#[rustfmt::skip] // non-macro attr, ignored by `-Zmacro-stats` +fn rustfmt_skip() { + // Nothing to see here. +} + +#[derive(Default, Clone, Copy, Hash)] +enum E1 { + #[default] // non-macro attr, ignored by `-Zmacro-stats` + A, + B, +} + +#[derive(Clone, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)] +struct E2 { + a: u32, + b: String, + c: Vec, +} + +#[derive(Clone)] struct S0; +#[derive(Clone)] struct S1(u32); +#[derive(Clone)] struct S2(u32, u32); +#[derive(Clone)] struct S3(u32, u32, u32); +#[derive(Clone)] struct S4(u32, u32, u32, u32); +#[derive(Clone)] struct S5(u32, u32, u32, u32, u32); + +macro_rules! u32 { + () => { u32 } +} + +macro_rules! none { + () => { None } +} +fn opt(x: Option) { + match x { + Some(_) => {} + none!() => {} // AstFragmentKind::Pat + } +} + +macro_rules! this_is_a_really_really_long_macro_name { + ($t:ty) => { + fn f(_: $t) {} + } +} +this_is_a_really_really_long_macro_name!(u32!()); // AstFragmentKind::{Items,Ty} + +macro_rules! trait_tys { + () => { + type A; + type B; + } +} +trait Tr { + trait_tys!(); // AstFragmentKind::TraitItems +} + +macro_rules! impl_const { () => { const X: u32 = 0; } } +struct U; +impl U { + impl_const!(); // AstFragmentKind::ImplItems +} + +macro_rules! trait_impl_tys { + () => { + type A = u32; + type B = bool; + } +} +struct Tr1; +impl Tr for Tr1 { + trait_impl_tys!(); // AstFragment::TraitImplItems +} + +macro_rules! foreign_item { + () => { fn fc(a: u32) -> u32; } +} +extern "C" { + foreign_item!(); // AstFragment::ForeignItems +} + +// Include macros are ignored by `-Zmacro-stats`. +mod includes { + mod z1 { + include!("auxiliary/include.rs"); + } + mod z2 { + std::include!("auxiliary/include.rs"); + } + + const B1: &[u8] = include_bytes!("auxiliary/include.rs"); + const B2: &[u8] = std::include_bytes!("auxiliary/include.rs"); + + const S1: &str = include_str!("auxiliary/include.rs"); + const S2: &str = std::include_str!("auxiliary/include.rs"); +} + +fn main() { + macro_rules! n99 { + () => { 99 } + } + let x = n99!() + n99!(); // AstFragmentKind::Expr + + macro_rules! p { + () => { + // blah + let x = 1; + let y = x; + let _ = y; + } + } + p!(); // AstFragmentKind::Stmts + + macro_rules! q { + () => {}; + ($($x:ident),*) => { $( let $x: u32 = 12345; )* }; + } + q!(a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z); +} diff --git a/tests/ui/stats/macro-stats.stderr b/tests/ui/stats/macro-stats.stderr new file mode 100644 index 000000000000..f87e34622b92 --- /dev/null +++ b/tests/ui/stats/macro-stats.stderr @@ -0,0 +1,26 @@ +macro-stats =================================================================================== +macro-stats MACRO EXPANSION STATS: macro_stats +macro-stats Macro Name Uses Lines Avg Lines Bytes Avg Bytes +macro-stats ----------------------------------------------------------------------------------- +macro-stats #[derive(Clone)] 8 56 7.0 1_660 207.5 +macro-stats #[derive(PartialOrd)] 1 16 16.0 654 654.0 +macro-stats #[derive(Hash)] 2 15 7.5 547 273.5 +macro-stats #[derive(Ord)] 1 14 14.0 489 489.0 +macro-stats q! 1 24 24.0 435 435.0 +macro-stats #[derive(Default)] 2 14 7.0 367 183.5 +macro-stats #[derive(Eq)] 1 10 10.0 312 312.0 +macro-stats #[derive(Debug)] 1 7 7.0 261 261.0 +macro-stats #[derive(PartialEq)] 1 8 8.0 247 247.0 +macro-stats #[derive(Copy)] 1 1 1.0 46 46.0 +macro-stats p! 1 2 2.0 28 28.0 +macro-stats trait_impl_tys! 1 1 1.0 11 11.0 +macro-stats foreign_item! 1 0 0.0 6 6.0 +macro-stats impl_const! 1 0 0.0 4 4.0 +macro-stats trait_tys! 1 1 1.0 3 3.0 +macro-stats u32! 1 0 0.0 -3 -3.0 +macro-stats none! 1 0 0.0 -3 -3.0 +macro-stats n99! 2 0 0.0 -8 -4.0 +macro-stats this_is_a_really_really_long_macro_name! +macro-stats 1 0 0.0 -30 -30.0 +macro-stats #[test] 1 -6 -6.0 -158 -158.0 +macro-stats =================================================================================== diff --git a/tests/ui/structs-enums/enum-alignment.rs b/tests/ui/structs-enums/enum-alignment.rs index bb779b1e0cdd..95f14e521b57 100644 --- a/tests/ui/structs-enums/enum-alignment.rs +++ b/tests/ui/structs-enums/enum-alignment.rs @@ -11,7 +11,7 @@ fn addr_of(ptr: &T) -> usize { fn is_aligned(ptr: &T) -> bool { unsafe { let addr: usize = mem::transmute(ptr); - (addr % mem::min_align_of::()) == 0 + (addr % mem::align_of::()) == 0 } } diff --git a/tests/ui/structs-enums/issue-2718-a.rs b/tests/ui/structs-enums/issue-2718-a.rs index 6c4915845405..f799a82447fe 100644 --- a/tests/ui/structs-enums/issue-2718-a.rs +++ b/tests/ui/structs-enums/issue-2718-a.rs @@ -3,7 +3,7 @@ pub struct SendPacket { } mod pingpong { - use SendPacket; + use crate::SendPacket; pub type Ping = SendPacket; pub struct Pong(SendPacket); //~^ ERROR recursive type `Pong` has infinite size diff --git a/tests/ui/structs-enums/namespaced-enum-glob-import.rs b/tests/ui/structs-enums/namespaced-enum-glob-import.rs index e8a709d5bd0c..82742a934c41 100644 --- a/tests/ui/structs-enums/namespaced-enum-glob-import.rs +++ b/tests/ui/structs-enums/namespaced-enum-glob-import.rs @@ -14,7 +14,7 @@ mod m2 { } mod m { - pub use m2::Foo::*; + pub use crate::m2::Foo::*; } fn _f(f: m2::Foo) { diff --git a/tests/ui/structs-enums/rec-align-u32.rs b/tests/ui/structs-enums/rec-align-u32.rs index 448791897398..b18cd11198e8 100644 --- a/tests/ui/structs-enums/rec-align-u32.rs +++ b/tests/ui/structs-enums/rec-align-u32.rs @@ -34,12 +34,12 @@ pub fn main() { // Send it through the shape code let y = format!("{:?}", x); - println!("align inner = {:?}", intrinsics::min_align_of::()); + println!("align inner = {:?}", intrinsics::align_of::()); println!("size outer = {:?}", mem::size_of::()); println!("y = {:?}", y); // per clang/gcc the alignment of `inner` is 4 on x86. - assert_eq!(intrinsics::min_align_of::(), m::align()); + assert_eq!(intrinsics::align_of::(), m::align()); // per clang/gcc the size of `outer` should be 12 // because `inner`s alignment was 4. diff --git a/tests/ui/structs-enums/rec-align-u64.rs b/tests/ui/structs-enums/rec-align-u64.rs index 0f7bb6b35057..df219892d737 100644 --- a/tests/ui/structs-enums/rec-align-u64.rs +++ b/tests/ui/structs-enums/rec-align-u64.rs @@ -84,12 +84,12 @@ pub fn main() { let y = format!("{:?}", x); - println!("align inner = {:?}", intrinsics::min_align_of::()); + println!("align inner = {:?}", intrinsics::align_of::()); println!("size outer = {:?}", mem::size_of::()); println!("y = {:?}", y); // per clang/gcc the alignment of `Inner` is 4 on x86. - assert_eq!(intrinsics::min_align_of::(), m::m::align()); + assert_eq!(intrinsics::align_of::(), m::m::align()); // per clang/gcc the size of `Outer` should be 12 // because `Inner`s alignment was 4. diff --git a/tests/ui/structs-enums/tag-align-dyn-u64.rs b/tests/ui/structs-enums/tag-align-dyn-u64.rs index 5e7d918b4fbc..5a4f0878c533 100644 --- a/tests/ui/structs-enums/tag-align-dyn-u64.rs +++ b/tests/ui/structs-enums/tag-align-dyn-u64.rs @@ -19,7 +19,7 @@ fn mk_rec() -> Rec { fn is_u64_aligned(u: &Tag) -> bool { let p: usize = unsafe { mem::transmute(u) }; - let u64_align = std::mem::min_align_of::(); + let u64_align = std::mem::align_of::(); return (p & (u64_align - 1)) == 0; } diff --git a/tests/ui/structs-enums/tag-align-dyn-variants.rs b/tests/ui/structs-enums/tag-align-dyn-variants.rs index c0574f3354e6..019f1a82895b 100644 --- a/tests/ui/structs-enums/tag-align-dyn-variants.rs +++ b/tests/ui/structs-enums/tag-align-dyn-variants.rs @@ -34,7 +34,7 @@ fn variant_data_is_aligned(amnt: usize, u: &Tag) -> bool { } pub fn main() { - let u64_align = std::mem::min_align_of::(); + let u64_align = std::mem::align_of::(); let x = mk_rec(22u64, 23u64); assert!(is_aligned(u64_align, &x.tA)); assert!(variant_data_is_aligned(u64_align, &x.tA)); diff --git a/tests/ui/structs-enums/tag-align-u64.rs b/tests/ui/structs-enums/tag-align-u64.rs index 8ab9f242822c..e274cc0e1575 100644 --- a/tests/ui/structs-enums/tag-align-u64.rs +++ b/tests/ui/structs-enums/tag-align-u64.rs @@ -19,7 +19,7 @@ fn mk_rec() -> Rec { fn is_u64_aligned(u: &Tag) -> bool { let p: usize = unsafe { mem::transmute(u) }; - let u64_align = std::mem::min_align_of::(); + let u64_align = std::mem::align_of::(); return (p & (u64_align - 1)) == 0; } diff --git a/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.rs b/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.rs index 2893bbc8b713..63fe5ebaea49 100644 --- a/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.rs +++ b/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.rs @@ -1,16 +1,15 @@ -#![allow(bare_trait_objects)] trait A: Sized { - fn f(a: A) -> A; + fn f(a: dyn A) -> dyn A; //~^ ERROR associated item referring to unboxed trait object for its own trait //~| ERROR the trait `A` is not dyn compatible } trait B { - fn f(a: B) -> B; + fn f(a: dyn B) -> dyn B; //~^ ERROR associated item referring to unboxed trait object for its own trait //~| ERROR the trait `B` is not dyn compatible } trait C { - fn f(&self, a: C) -> C; + fn f(&self, a: dyn C) -> dyn C; } fn main() {} diff --git a/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.stderr b/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.stderr index f4b669d7fcd4..e8384afed7a1 100644 --- a/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.stderr +++ b/tests/ui/suggestions/dyn-incompatible-trait-should-use-self.stderr @@ -1,26 +1,26 @@ error: associated item referring to unboxed trait object for its own trait - --> $DIR/dyn-incompatible-trait-should-use-self.rs:3:13 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:2:13 | LL | trait A: Sized { | - in this trait -LL | fn f(a: A) -> A; - | ^ ^ +LL | fn f(a: dyn A) -> dyn A; + | ^^^^^ ^^^^^ | help: you might have meant to use `Self` to refer to the implementing type | -LL - fn f(a: A) -> A; +LL - fn f(a: dyn A) -> dyn A; LL + fn f(a: Self) -> Self; | error[E0038]: the trait `A` is not dyn compatible - --> $DIR/dyn-incompatible-trait-should-use-self.rs:3:13 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:2:13 | -LL | fn f(a: A) -> A; - | ^ `A` is not dyn compatible +LL | fn f(a: dyn A) -> dyn A; + | ^^^^^ `A` is not dyn compatible | note: for a trait to be dyn compatible it needs to allow building a vtable for more information, visit - --> $DIR/dyn-incompatible-trait-should-use-self.rs:2:10 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:1:10 | LL | trait A: Sized { | - ^^^^^ ...because it requires `Self: Sized` @@ -28,41 +28,41 @@ LL | trait A: Sized { | this trait is not dyn compatible... error: associated item referring to unboxed trait object for its own trait - --> $DIR/dyn-incompatible-trait-should-use-self.rs:8:13 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:7:13 | LL | trait B { | - in this trait -LL | fn f(a: B) -> B; - | ^ ^ +LL | fn f(a: dyn B) -> dyn B; + | ^^^^^ ^^^^^ | help: you might have meant to use `Self` to refer to the implementing type | -LL - fn f(a: B) -> B; +LL - fn f(a: dyn B) -> dyn B; LL + fn f(a: Self) -> Self; | error[E0038]: the trait `B` is not dyn compatible - --> $DIR/dyn-incompatible-trait-should-use-self.rs:8:13 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:7:13 | -LL | fn f(a: B) -> B; - | ^ `B` is not dyn compatible +LL | fn f(a: dyn B) -> dyn B; + | ^^^^^ `B` is not dyn compatible | note: for a trait to be dyn compatible it needs to allow building a vtable for more information, visit - --> $DIR/dyn-incompatible-trait-should-use-self.rs:8:8 + --> $DIR/dyn-incompatible-trait-should-use-self.rs:7:8 | LL | trait B { | - this trait is not dyn compatible... -LL | fn f(a: B) -> B; +LL | fn f(a: dyn B) -> dyn B; | ^ ...because associated function `f` has no `self` parameter help: consider turning `f` into a method by giving it a `&self` argument | -LL | fn f(&self, a: B) -> B; +LL | fn f(&self, a: dyn B) -> dyn B; | ++++++ help: alternatively, consider constraining `f` so it does not apply to trait objects | -LL | fn f(a: B) -> B where Self: Sized; - | +++++++++++++++++ +LL | fn f(a: dyn B) -> dyn B where Self: Sized; + | +++++++++++++++++ error: aborting due to 4 previous errors diff --git a/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.rs b/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.rs index efa296db47cf..d10b3bec543e 100644 --- a/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.rs +++ b/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.rs @@ -1,4 +1,5 @@ // Regression test for ICE #125876 +//@ edition: 2015 fn main() { std::ptr::from_ref(num).cast_mut().as_deref(); diff --git a/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.stderr b/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.stderr index f943688e6578..696151b6ee2c 100644 --- a/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.stderr +++ b/tests/ui/suggestions/ice-unwrap-probe-many-result-125876.stderr @@ -1,11 +1,11 @@ error[E0425]: cannot find value `num` in this scope - --> $DIR/ice-unwrap-probe-many-result-125876.rs:4:24 + --> $DIR/ice-unwrap-probe-many-result-125876.rs:5:24 | LL | std::ptr::from_ref(num).cast_mut().as_deref(); | ^^^ not found in this scope warning: type annotations needed - --> $DIR/ice-unwrap-probe-many-result-125876.rs:4:29 + --> $DIR/ice-unwrap-probe-many-result-125876.rs:5:29 | LL | std::ptr::from_ref(num).cast_mut().as_deref(); | ^^^^^^^^ @@ -15,7 +15,7 @@ LL | std::ptr::from_ref(num).cast_mut().as_deref(); = note: `#[warn(tyvar_behind_raw_pointer)]` on by default warning: type annotations needed - --> $DIR/ice-unwrap-probe-many-result-125876.rs:4:40 + --> $DIR/ice-unwrap-probe-many-result-125876.rs:5:40 | LL | std::ptr::from_ref(num).cast_mut().as_deref(); | ^^^^^^^^ @@ -24,7 +24,7 @@ LL | std::ptr::from_ref(num).cast_mut().as_deref(); = note: for more information, see issue #46906 error[E0599]: no method named `as_deref` found for raw pointer `*mut _` in the current scope - --> $DIR/ice-unwrap-probe-many-result-125876.rs:4:40 + --> $DIR/ice-unwrap-probe-many-result-125876.rs:5:40 | LL | std::ptr::from_ref(num).cast_mut().as_deref(); | ^^^^^^^^ diff --git a/tests/ui/suggestions/issue-116434-2015.rs b/tests/ui/suggestions/issue-116434-2015.rs index 1518765152ff..bad9d02321cf 100644 --- a/tests/ui/suggestions/issue-116434-2015.rs +++ b/tests/ui/suggestions/issue-116434-2015.rs @@ -1,3 +1,5 @@ +//@ edition: 2015 + trait Foo { type Clone; fn foo() -> Clone; diff --git a/tests/ui/suggestions/issue-116434-2015.stderr b/tests/ui/suggestions/issue-116434-2015.stderr index 07a254432a28..a0a99cc560db 100644 --- a/tests/ui/suggestions/issue-116434-2015.stderr +++ b/tests/ui/suggestions/issue-116434-2015.stderr @@ -1,5 +1,5 @@ warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-116434-2015.rs:3:17 + --> $DIR/issue-116434-2015.rs:5:17 | LL | fn foo() -> Clone; | ^^^^^ @@ -13,7 +13,7 @@ LL | fn foo() -> dyn Clone; | +++ warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-116434-2015.rs:3:17 + --> $DIR/issue-116434-2015.rs:5:17 | LL | fn foo() -> Clone; | ^^^^^ @@ -27,7 +27,7 @@ LL | fn foo() -> dyn Clone; | +++ error[E0038]: the trait `Clone` is not dyn compatible - --> $DIR/issue-116434-2015.rs:3:17 + --> $DIR/issue-116434-2015.rs:5:17 | LL | fn foo() -> Clone; | ^^^^^ `Clone` is not dyn compatible @@ -41,7 +41,7 @@ LL | fn foo() -> Self::Clone; | ++++++ warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-116434-2015.rs:18:20 + --> $DIR/issue-116434-2015.rs:20:20 | LL | fn handle() -> DbHandle; | ^^^^^^^^ @@ -54,7 +54,7 @@ LL | fn handle() -> dyn DbHandle; | +++ warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-116434-2015.rs:18:20 + --> $DIR/issue-116434-2015.rs:20:20 | LL | fn handle() -> DbHandle; | ^^^^^^^^ @@ -68,14 +68,14 @@ LL | fn handle() -> dyn DbHandle; | +++ error[E0038]: the trait `DbHandle` is not dyn compatible - --> $DIR/issue-116434-2015.rs:18:20 + --> $DIR/issue-116434-2015.rs:20:20 | LL | fn handle() -> DbHandle; | ^^^^^^^^ `DbHandle` is not dyn compatible | note: for a trait to be dyn compatible it needs to allow building a vtable for more information, visit - --> $DIR/issue-116434-2015.rs:14:17 + --> $DIR/issue-116434-2015.rs:16:17 | LL | trait DbHandle: Sized {} | -------- ^^^^^ ...because it requires `Self: Sized` diff --git a/tests/ui/suggestions/issue-61963.rs b/tests/ui/suggestions/issue-61963.rs index 2fafe629db97..77e4b21f5dbd 100644 --- a/tests/ui/suggestions/issue-61963.rs +++ b/tests/ui/suggestions/issue-61963.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ proc-macro: issue-61963.rs //@ proc-macro: issue-61963-1.rs #![deny(bare_trait_objects)] diff --git a/tests/ui/suggestions/issue-61963.stderr b/tests/ui/suggestions/issue-61963.stderr index 734c88f3fd67..ef11efe5c74d 100644 --- a/tests/ui/suggestions/issue-61963.stderr +++ b/tests/ui/suggestions/issue-61963.stderr @@ -1,5 +1,5 @@ error: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-61963.rs:22:14 + --> $DIR/issue-61963.rs:23:14 | LL | bar: Box, | ^^^ @@ -7,7 +7,7 @@ LL | bar: Box, = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! = note: for more information, see note: the lint level is defined here - --> $DIR/issue-61963.rs:3:9 + --> $DIR/issue-61963.rs:4:9 | LL | #![deny(bare_trait_objects)] | ^^^^^^^^^^^^^^^^^^ @@ -17,7 +17,7 @@ LL | bar: Box, | +++ error: trait objects without an explicit `dyn` are deprecated - --> $DIR/issue-61963.rs:18:1 + --> $DIR/issue-61963.rs:19:1 | LL | pub struct Foo { | ^^^ diff --git a/tests/ui/suggestions/lifetimes/missing-lifetimes-in-signature.stderr b/tests/ui/suggestions/lifetimes/missing-lifetimes-in-signature.stderr index 41cb2ee46bb5..0aa33d3b6fb1 100644 --- a/tests/ui/suggestions/lifetimes/missing-lifetimes-in-signature.stderr +++ b/tests/ui/suggestions/lifetimes/missing-lifetimes-in-signature.stderr @@ -101,15 +101,17 @@ LL + fn bat<'b, 'a, G: 'a + 'b, T>(g: G, dest: &'b mut T) -> impl FnOnce() + 'b error[E0621]: explicit lifetime required in the type of `dest` --> $DIR/missing-lifetimes-in-signature.rs:73:5 | -LL | fn bat<'a, G: 'a, T>(g: G, dest: &mut T) -> impl FnOnce() + '_ + 'a - | ------ help: add explicit lifetime `'a` to the type of `dest`: `&'a mut T` -... LL | / move || { LL | | LL | | LL | | *dest = g.get(); LL | | } | |_____^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `dest` + | +LL | fn bat<'a, G: 'a, T>(g: G, dest: &'a mut T) -> impl FnOnce() + '_ + 'a + | ++ error[E0309]: the parameter type `G` may not live long enough --> $DIR/missing-lifetimes-in-signature.rs:85:5 diff --git a/tests/ui/suggestions/missing-lifetime-specifier.rs b/tests/ui/suggestions/missing-lifetime-specifier.rs index a957477897d5..88d9736a071d 100644 --- a/tests/ui/suggestions/missing-lifetime-specifier.rs +++ b/tests/ui/suggestions/missing-lifetime-specifier.rs @@ -7,7 +7,6 @@ // Different number of duplicated diagnostics on different targets //@ compile-flags: -Zdeduplicate-diagnostics=yes -#![allow(bare_trait_objects)] use std::cell::RefCell; use std::collections::HashMap; @@ -28,7 +27,7 @@ thread_local! { //~^ ERROR missing lifetime specifiers } thread_local! { - static b: RefCell>>> = RefCell::new(HashMap::new()); + static b: RefCell>>> = RefCell::new(HashMap::new()); //~^ ERROR missing lifetime specifiers } thread_local! { @@ -36,7 +35,7 @@ thread_local! { //~^ ERROR missing lifetime specifiers } thread_local! { - static d: RefCell>>>> = RefCell::new(HashMap::new()); + static d: RefCell>>>> = RefCell::new(HashMap::new()); //~^ ERROR missing lifetime specifiers } @@ -45,8 +44,9 @@ thread_local! { //~^ ERROR union takes 2 lifetime arguments but 1 lifetime argument } thread_local! { - static f: RefCell>>>> = RefCell::new(HashMap::new()); - //~^ ERROR trait takes 2 lifetime arguments but 1 lifetime argument was supplied + static f: RefCell>>>> = + RefCell::new(HashMap::new()); + //~^^ ERROR trait takes 2 lifetime arguments but 1 lifetime argument was supplied //~| ERROR missing lifetime specifier } diff --git a/tests/ui/suggestions/missing-lifetime-specifier.stderr b/tests/ui/suggestions/missing-lifetime-specifier.stderr index 1fdbf3b0c79a..b8c58155e636 100644 --- a/tests/ui/suggestions/missing-lifetime-specifier.stderr +++ b/tests/ui/suggestions/missing-lifetime-specifier.stderr @@ -1,5 +1,5 @@ error[E0106]: missing lifetime specifiers - --> $DIR/missing-lifetime-specifier.rs:27:44 + --> $DIR/missing-lifetime-specifier.rs:26:44 | LL | static a: RefCell>>> = RefCell::new(HashMap::new()); | ^^^ expected 2 lifetime parameters @@ -11,21 +11,21 @@ LL | static a: RefCell>>>> = RefC | ++++++++++++++++++ error[E0106]: missing lifetime specifiers - --> $DIR/missing-lifetime-specifier.rs:31:44 + --> $DIR/missing-lifetime-specifier.rs:30:44 | -LL | static b: RefCell>>> = RefCell::new(HashMap::new()); - | ^^^^ expected 2 lifetime parameters +LL | static b: RefCell>>> = RefCell::new(HashMap::new()); + | ^ ^^^ expected 2 lifetime parameters | | | expected named lifetime parameter | = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from help: consider using the `'static` lifetime, but this is uncommon unless you're returning a borrowed value from a `const` or a `static` | -LL | static b: RefCell>>>> = RefCell::new(HashMap::new()); - | +++++++ ++++++++++++++++++ +LL | static b: RefCell>>>> = RefCell::new(HashMap::new()); + | +++++++ ++++++++++++++++++ error[E0106]: missing lifetime specifiers - --> $DIR/missing-lifetime-specifier.rs:35:47 + --> $DIR/missing-lifetime-specifier.rs:34:47 | LL | static c: RefCell>>>> = RefCell::new(HashMap::new()); | ^ expected 2 lifetime parameters @@ -37,33 +37,38 @@ LL | static c: RefCell>>>> = | +++++++++++++++++ error[E0106]: missing lifetime specifiers - --> $DIR/missing-lifetime-specifier.rs:39:44 + --> $DIR/missing-lifetime-specifier.rs:38:44 | -LL | static d: RefCell>>>> = RefCell::new(HashMap::new()); - | ^ ^ expected 2 lifetime parameters +LL | static d: RefCell>>>> = RefCell::new(HashMap::new()); + | ^ ^ expected 2 lifetime parameters | | | expected named lifetime parameter | = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from help: consider using the `'static` lifetime, but this is uncommon unless you're returning a borrowed value from a `const` or a `static` | -LL | static d: RefCell>>>> = RefCell::new(HashMap::new()); - | +++++++ +++++++++++++++++ +LL | static d: RefCell>>>> = RefCell::new(HashMap::new()); + | +++++++ +++++++++++++++++ error[E0106]: missing lifetime specifier - --> $DIR/missing-lifetime-specifier.rs:48:44 + --> $DIR/missing-lifetime-specifier.rs:47:44 | -LL | static f: RefCell>>>> = RefCell::new(HashMap::new()); +LL | static f: RefCell>>>> = | ^ expected named lifetime parameter | = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from help: consider using the `'static` lifetime, but this is uncommon unless you're returning a borrowed value from a `const` or a `static` | -LL | static f: RefCell>>>> = RefCell::new(HashMap::new()); +LL | static f: RefCell>>>> = | +++++++ +help: instead, you are more likely to want to return an owned value + | +LL - static f: RefCell>>>> = +LL + static f: RefCell>>>> = + | error[E0107]: union takes 2 lifetime arguments but 1 lifetime argument was supplied - --> $DIR/missing-lifetime-specifier.rs:44:44 + --> $DIR/missing-lifetime-specifier.rs:43:44 | LL | static e: RefCell>>>> = RefCell::new(HashMap::new()); | ^^^ ------- supplied 1 lifetime argument @@ -71,7 +76,7 @@ LL | static e: RefCell>>>> = RefCell: | expected 2 lifetime arguments | note: union defined here, with 2 lifetime parameters: `'t`, `'k` - --> $DIR/missing-lifetime-specifier.rs:20:11 + --> $DIR/missing-lifetime-specifier.rs:19:11 | LL | pub union Qux<'t, 'k, I> { | ^^^ -- -- @@ -81,22 +86,22 @@ LL | static e: RefCell>>>> = | +++++++++ error[E0107]: trait takes 2 lifetime arguments but 1 lifetime argument was supplied - --> $DIR/missing-lifetime-specifier.rs:48:45 + --> $DIR/missing-lifetime-specifier.rs:47:49 | -LL | static f: RefCell>>>> = RefCell::new(HashMap::new()); - | ^^^ ------- supplied 1 lifetime argument - | | - | expected 2 lifetime arguments +LL | static f: RefCell>>>> = + | ^^^ ------- supplied 1 lifetime argument + | | + | expected 2 lifetime arguments | note: trait defined here, with 2 lifetime parameters: `'t`, `'k` - --> $DIR/missing-lifetime-specifier.rs:24:7 + --> $DIR/missing-lifetime-specifier.rs:23:7 | LL | trait Tar<'t, 'k, I> {} | ^^^ -- -- help: add missing lifetime argument | -LL | static f: RefCell>>>> = RefCell::new(HashMap::new()); - | +++++++++ +LL | static f: RefCell>>>> = + | +++++++++ error: aborting due to 7 previous errors diff --git a/tests/ui/symbol-names/impl1.rs b/tests/ui/symbol-names/impl1.rs index 694cd89bd80f..0fdf56454799 100644 --- a/tests/ui/symbol-names/impl1.rs +++ b/tests/ui/symbol-names/impl1.rs @@ -26,7 +26,7 @@ mod foo { } mod bar { - use foo::Foo; + use crate::foo::Foo; impl Foo { #[rustc_symbol_name] diff --git a/tests/ui/symbol-names/issue-53912.rs b/tests/ui/symbol-names/issue-53912.rs index 194416cdb70c..ba28316b0bf0 100644 --- a/tests/ui/symbol-names/issue-53912.rs +++ b/tests/ui/symbol-names/issue-53912.rs @@ -12,13 +12,13 @@ mod llvm { mod foo { pub(crate) struct Foo(T); - impl Foo<::llvm::Foo> { + impl Foo { pub(crate) fn foo() { for _ in 0..0 { - for _ in &[::dummy()] { - ::dummy(); - ::dummy(); - ::dummy(); + for _ in &[crate::dummy()] { + crate::dummy(); + crate::dummy(); + crate::dummy(); } } } diff --git a/tests/ui/symbol-names/issue-60925.rs b/tests/ui/symbol-names/issue-60925.rs index ca0f21b7a781..24969fc66419 100644 --- a/tests/ui/symbol-names/issue-60925.rs +++ b/tests/ui/symbol-names/issue-60925.rs @@ -17,7 +17,7 @@ mod llvm { mod foo { pub(crate) struct Foo(T); - impl Foo<::llvm::Foo> { + impl Foo { #[rustc_symbol_name] //[legacy]~^ ERROR symbol-name(_ZN11issue_609253foo37Foo$LT$issue_60925..llv$u6d$..Foo$GT$3foo //[legacy]~| ERROR demangling(issue_60925::foo::Foo::foo @@ -27,10 +27,10 @@ mod foo { //[v0]~| ERROR demangling-alt(>::foo) pub(crate) fn foo() { for _ in 0..0 { - for _ in &[::dummy()] { - ::dummy(); - ::dummy(); - ::dummy(); + for _ in &[crate::dummy()] { + crate::dummy(); + crate::dummy(); + crate::dummy(); } } } diff --git a/tests/ui/target-feature/retpoline-target-feature-flag.by_feature.stderr b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature.stderr new file mode 100644 index 000000000000..e2b6078b7a8c --- /dev/null +++ b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature.stderr @@ -0,0 +1,7 @@ +warning: target feature `retpoline-external-thunk` cannot be enabled with `-Ctarget-feature`: use `x86-retpoline` target modifier flag instead + | + = note: 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 #116344 + +warning: 1 warning emitted + diff --git a/tests/ui/target-feature/retpoline-target-feature-flag.by_feature1.stderr b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature1.stderr new file mode 100644 index 000000000000..2a0f5f01aef6 --- /dev/null +++ b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature1.stderr @@ -0,0 +1,7 @@ +warning: target feature `retpoline-external-thunk` cannot be enabled with `-Ctarget-feature`: use `retpoline-external-thunk` target modifier flag instead + | + = note: 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 #116344 + +warning: 1 warning emitted + diff --git a/tests/ui/target-feature/retpoline-target-feature-flag.by_feature2.stderr b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature2.stderr new file mode 100644 index 000000000000..f7b6cb164477 --- /dev/null +++ b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature2.stderr @@ -0,0 +1,7 @@ +warning: target feature `retpoline-indirect-branches` cannot be enabled with `-Ctarget-feature`: use `retpoline` target modifier flag instead + | + = note: 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 #116344 + +warning: 1 warning emitted + diff --git a/tests/ui/target-feature/retpoline-target-feature-flag.by_feature3.stderr b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature3.stderr new file mode 100644 index 000000000000..4f2cd1d1a522 --- /dev/null +++ b/tests/ui/target-feature/retpoline-target-feature-flag.by_feature3.stderr @@ -0,0 +1,7 @@ +warning: target feature `retpoline-indirect-calls` cannot be enabled with `-Ctarget-feature`: use `retpoline` target modifier flag instead + | + = note: 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 #116344 + +warning: 1 warning emitted + diff --git a/tests/ui/target-feature/retpoline-target-feature-flag.rs b/tests/ui/target-feature/retpoline-target-feature-flag.rs new file mode 100644 index 000000000000..3e614a4236c0 --- /dev/null +++ b/tests/ui/target-feature/retpoline-target-feature-flag.rs @@ -0,0 +1,23 @@ +//@ revisions: by_flag by_feature1 by_feature2 by_feature3 +//@ compile-flags: --target=x86_64-unknown-linux-gnu --crate-type=lib +//@ needs-llvm-components: x86 +//@ [by_flag]compile-flags: -Zretpoline + +//@ [by_feature1]compile-flags: -Ctarget-feature=+retpoline-external-thunk +//@ [by_feature2]compile-flags: -Ctarget-feature=+retpoline-indirect-branches +//@ [by_feature3]compile-flags: -Ctarget-feature=+retpoline-indirect-calls +//@ [by_flag]build-pass +// For now this is just a warning. +//@ [by_feature1]build-pass +//@ [by_feature2]build-pass +//@ [by_feature3]build-pass +#![feature(no_core, lang_items)] +#![no_std] +#![no_core] + +#[lang = "sized"] +pub trait Sized {} + +//[by_feature1]~? WARN target feature `retpoline-external-thunk` cannot be enabled with `-Ctarget-feature`: use `retpoline-external-thunk` target modifier flag instead +//[by_feature2]~? WARN target feature `retpoline-indirect-branches` cannot be enabled with `-Ctarget-feature`: use `retpoline` target modifier flag instead +//[by_feature3]~? WARN target feature `retpoline-indirect-calls` cannot be enabled with `-Ctarget-feature`: use `retpoline` target modifier flag instead diff --git a/tests/ui/threads-sendsync/thread-local-syntax.rs b/tests/ui/threads-sendsync/thread-local-syntax.rs index 2cf91f0c1f78..9492e1c93e25 100644 --- a/tests/ui/threads-sendsync/thread-local-syntax.rs +++ b/tests/ui/threads-sendsync/thread-local-syntax.rs @@ -13,7 +13,7 @@ mod foo { // look at these restrictions!! pub(crate) static BAZ: usize = 0; - pub(in foo) static QUUX: usize = 0; + pub(in crate::foo) static QUUX: usize = 0; } thread_local!(static SPLOK: u32 = 0); } diff --git a/tests/ui/tool-attributes/diagnostic_item.rs b/tests/ui/tool-attributes/diagnostic_item.rs index 26a52ce60cfd..806b140feba3 100644 --- a/tests/ui/tool-attributes/diagnostic_item.rs +++ b/tests/ui/tool-attributes/diagnostic_item.rs @@ -1,3 +1,5 @@ -#[rustc_diagnostic_item = "foomp"] //~ ERROR compiler internal support for linting +#[rustc_diagnostic_item = "foomp"] +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_diagnostic_item]` attribute allows the compiler to reference types from the standard library for diagnostic purposes struct Foomp; fn main() {} diff --git a/tests/ui/tool-attributes/diagnostic_item.stderr b/tests/ui/tool-attributes/diagnostic_item.stderr index c6ae5a38594f..d37044281a13 100644 --- a/tests/ui/tool-attributes/diagnostic_item.stderr +++ b/tests/ui/tool-attributes/diagnostic_item.stderr @@ -1,11 +1,11 @@ -error[E0658]: diagnostic items compiler internal support for linting +error[E0658]: use of an internal attribute --> $DIR/diagnostic_item.rs:1:1 | LL | #[rustc_diagnostic_item = "foomp"] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_diagnostic_item]` attribute allows the compiler to reference types from the standard library for diagnostic purposes error: aborting due to 1 previous error diff --git a/tests/ui/track-diagnostics/track.stderr b/tests/ui/track-diagnostics/track.stderr index d2908bb91776..527c0d1b8989 100644 --- a/tests/ui/track-diagnostics/track.stderr +++ b/tests/ui/track-diagnostics/track.stderr @@ -10,7 +10,7 @@ error[E0268]: `break` outside of a loop or labeled block | LL | break rust | ^^^^^^^^^^ cannot `break` outside of a loop or labeled block --Ztrack-diagnostics: created at compiler/rustc_passes/src/loops.rs:LL:CC +-Ztrack-diagnostics: created at compiler/rustc_hir_typeck/src/loops.rs:LL:CC error: internal compiler error: It looks like you're trying to break rust; would you like some ICE? --> $DIR/track.rs:LL:CC diff --git a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.fixed b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.fixed index e6aac1708cef..6354676bb25b 100644 --- a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.fixed +++ b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.fixed @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![allow(non_snake_case)] mod A { diff --git a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.rs b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.rs index d5c557dc9c7d..c3b3a00aa6dd 100644 --- a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.rs +++ b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.rs @@ -1,3 +1,4 @@ +//@ edition: 2015 //@ run-rustfix #![allow(non_snake_case)] mod A { diff --git a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.stderr b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.stderr index e2a72697501f..4fb0dcc79017 100644 --- a/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.stderr +++ b/tests/ui/trait-bounds/shadowed-path-in-trait-bound-suggestion.stderr @@ -1,5 +1,5 @@ error[E0405]: cannot find trait `Trait` in `A` - --> $DIR/shadowed-path-in-trait-bound-suggestion.rs:9:24 + --> $DIR/shadowed-path-in-trait-bound-suggestion.rs:10:24 | LL | pub struct A(pub H); | ^^^^^ not found in `A` diff --git a/tests/ui/traits/auxiliary/traitimpl.rs b/tests/ui/traits/auxiliary/traitimpl.rs index fda5314cdbfa..2544a96048b6 100644 --- a/tests/ui/traits/auxiliary/traitimpl.rs +++ b/tests/ui/traits/auxiliary/traitimpl.rs @@ -2,6 +2,6 @@ pub trait Bar<'a> : 'a {} -impl<'a> Bar<'a> { +impl<'a> dyn Bar<'a> { pub fn bar(&self) {} } diff --git a/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.rs b/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.rs index f90ff91aff4b..b563b78f78a1 100644 --- a/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.rs +++ b/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.rs @@ -6,6 +6,7 @@ // Regression test for issue #125877. //@ compile-flags: -Znext-solver +//@ normalize-stderr: "you are using [0-9]+\.[0-9]+\.[0-9]+(-[a-zA-Z0-9]+)?( \([^)]*\))?" -> "you are using $$RUSTC_VERSION" #![feature(const_trait_impl, effects)] //~^ ERROR feature has been removed diff --git a/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.stderr b/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.stderr index d45c4cba1f8b..a04f98e68a63 100644 --- a/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.stderr +++ b/tests/ui/traits/const-traits/const-trait-impl-parameter-mismatch.stderr @@ -1,13 +1,14 @@ error[E0557]: feature has been removed - --> $DIR/const-trait-impl-parameter-mismatch.rs:10:30 + --> $DIR/const-trait-impl-parameter-mismatch.rs:11:30 | LL | #![feature(const_trait_impl, effects)] | ^^^^^^^ feature has been removed | + = note: removed in 1.84.0 (you are using $RUSTC_VERSION); see for more information = note: removed, redundant with `#![feature(const_trait_impl)]` error[E0049]: associated function `compute` has 0 type parameters but its trait declaration has 1 type parameter - --> $DIR/const-trait-impl-parameter-mismatch.rs:19:16 + --> $DIR/const-trait-impl-parameter-mismatch.rs:20:16 | LL | fn compute() -> u32; | - expected 1 type parameter diff --git a/tests/ui/traits/const-traits/inherent-impl.rs b/tests/ui/traits/const-traits/inherent-impl.rs index afd0d137bb4a..07b23adf9e1f 100644 --- a/tests/ui/traits/const-traits/inherent-impl.rs +++ b/tests/ui/traits/const-traits/inherent-impl.rs @@ -7,7 +7,7 @@ trait T {} impl const S {} //~^ ERROR inherent impls cannot be `const` -impl const T {} +impl const dyn T {} //~^ ERROR inherent impls cannot be `const` fn main() {} diff --git a/tests/ui/traits/const-traits/inherent-impl.stderr b/tests/ui/traits/const-traits/inherent-impl.stderr index 8c55627031d1..e4ec1e807b0e 100644 --- a/tests/ui/traits/const-traits/inherent-impl.stderr +++ b/tests/ui/traits/const-traits/inherent-impl.stderr @@ -11,8 +11,8 @@ LL | impl const S {} error: inherent impls cannot be `const` --> $DIR/inherent-impl.rs:10:12 | -LL | impl const T {} - | ----- ^ inherent impl for this type +LL | impl const dyn T {} + | ----- ^^^^^ inherent impl for this type | | | `const` because of this | diff --git a/tests/ui/traits/const-traits/mbe-dyn-const-2015.rs b/tests/ui/traits/const-traits/mbe-dyn-const-2015.rs index 9d65a2ac3026..fadfbe667887 100644 --- a/tests/ui/traits/const-traits/mbe-dyn-const-2015.rs +++ b/tests/ui/traits/const-traits/mbe-dyn-const-2015.rs @@ -1,6 +1,7 @@ // Ensure that the introduction of const trait bound didn't regress this code in Rust 2015. // See also `mbe-const-trait-bound-theoretical-regression.rs`. +//@ edition: 2015 //@ check-pass macro_rules! check { diff --git a/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.rs b/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.rs index 27e70556b7af..47cc9f5f9605 100644 --- a/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.rs +++ b/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.rs @@ -1,5 +1,7 @@ #[rustc_must_implement_one_of(eq, neq)] -//~^ ERROR the `#[rustc_must_implement_one_of]` attribute is used to change minimal complete definition of a trait, it's currently in experimental form and should be changed before being exposed outside of the std +//~^ ERROR use of an internal attribute [E0658] +//~| NOTE the `#[rustc_must_implement_one_of]` attribute is an internal implementation detail that will never be stable +//~| NOTE the `#[rustc_must_implement_one_of]` attribute is used to change minimal complete definition of a trait. Its syntax and semantics are highly experimental and will be subject to change before stabilization trait Equal { fn eq(&self, other: &Self) -> bool { !self.neq(other) diff --git a/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.stderr b/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.stderr index 162c3d36cb1c..4d44ceff98a4 100644 --- a/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.stderr +++ b/tests/ui/traits/default-method/rustc_must_implement_one_of_gated.stderr @@ -1,11 +1,12 @@ -error[E0658]: the `#[rustc_must_implement_one_of]` attribute is used to change minimal complete definition of a trait, it's currently in experimental form and should be changed before being exposed outside of the std +error[E0658]: use of an internal attribute --> $DIR/rustc_must_implement_one_of_gated.rs:1:1 | LL | #[rustc_must_implement_one_of(eq, neq)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = help: add `#![feature(rustc_attrs)]` to the crate attributes to enable - = note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date + = note: the `#[rustc_must_implement_one_of]` attribute is an internal implementation detail that will never be stable + = note: the `#[rustc_must_implement_one_of]` attribute is used to change minimal complete definition of a trait. Its syntax and semantics are highly experimental and will be subject to change before stabilization error: aborting due to 1 previous error diff --git a/tests/ui/traits/impl-2.rs b/tests/ui/traits/impl-2.rs index c6f60a9081cc..41fa1cd334f4 100644 --- a/tests/ui/traits/impl-2.rs +++ b/tests/ui/traits/impl-2.rs @@ -10,7 +10,7 @@ pub mod Foo { } mod Bar { - impl<'a> dyn (::Foo::Trait) + 'a { + impl<'a> dyn (crate::Foo::Trait) + 'a { fn bar(&self) { self.foo() } } } diff --git a/tests/ui/traits/item-privacy.rs b/tests/ui/traits/item-privacy.rs index 9f75e6e4c123..b8724399e327 100644 --- a/tests/ui/traits/item-privacy.rs +++ b/tests/ui/traits/item-privacy.rs @@ -15,9 +15,9 @@ mod method { fn c(&self) { } } - impl A for ::S {} - impl B for ::S {} - impl C for ::S {} + impl A for crate::S {} + impl B for crate::S {} + impl C for crate::S {} } mod assoc_const { @@ -33,9 +33,9 @@ mod assoc_const { const C: u8 = 0; } - impl A for ::S {} - impl B for ::S {} - impl C for ::S {} + impl A for crate::S {} + impl B for crate::S {} + impl C for crate::S {} } mod assoc_ty { @@ -51,9 +51,9 @@ mod assoc_ty { type C = u8; } - impl A for ::S {} - impl B for ::S {} - impl C for ::S {} + impl A for crate::S {} + impl B for crate::S {} + impl C for crate::S {} } fn check_method() { diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs index ea6df9387047..14f0cbcc8b77 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.rs @@ -13,9 +13,9 @@ fn main() { } fn weird0() -> impl Sized + !Sized {} -//~^ ERROR type mismatch resolving +//~^ ERROR the trait bound `(): !Sized` is not satisfied fn weird1() -> impl !Sized + Sized {} -//~^ ERROR type mismatch resolving +//~^ ERROR the trait bound `(): !Sized` is not satisfied fn weird2() -> impl !Sized {} -//~^ ERROR type mismatch resolving +//~^ ERROR the trait bound `(): !Sized` is not satisfied //~| ERROR the size for values of type diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr index 41d9e74f8076..3ba3d8d8bd59 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-bound.stderr @@ -7,23 +7,23 @@ LL | fn weird2() -> impl !Sized {} = help: the trait `Sized` is not implemented for `impl !Sized` = note: the return type of a function must have a statically known size -error[E0271]: type mismatch resolving `impl !Sized + Sized == ()` +error[E0277]: the trait bound `(): !Sized` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:15:16 | LL | fn weird0() -> impl Sized + !Sized {} - | ^^^^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied -error[E0271]: type mismatch resolving `impl !Sized + Sized == ()` +error[E0277]: the trait bound `(): !Sized` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:17:16 | LL | fn weird1() -> impl !Sized + Sized {} - | ^^^^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied -error[E0271]: type mismatch resolving `impl !Sized == ()` +error[E0277]: the trait bound `(): !Sized` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:19:16 | LL | fn weird2() -> impl !Sized {} - | ^^^^^^^^^^^ types differ + | ^^^^^^^^^^^ the trait bound `(): !Sized` is not satisfied error[E0277]: the trait bound `impl !Trait: Trait` is not satisfied --> $DIR/opaque-type-unsatisfied-bound.rs:12:13 @@ -41,5 +41,4 @@ LL | fn consume(_: impl Trait) {} error: aborting due to 5 previous errors -Some errors have detailed explanations: E0271, E0277. -For more information about an error, try `rustc --explain E0271`. +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs index ce42bce0ad4e..39422914afcd 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.rs @@ -3,6 +3,6 @@ #![feature(negative_bounds, unboxed_closures)] fn produce() -> impl !Fn<(u32,)> {} -//~^ ERROR type mismatch resolving +//~^ ERROR the trait bound `(): !Fn(u32)` is not satisfied fn main() {} diff --git a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr index e1b84e0df7a5..760e5aa62f2c 100644 --- a/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr +++ b/tests/ui/traits/negative-bounds/opaque-type-unsatisfied-fn-bound.stderr @@ -1,9 +1,9 @@ -error[E0271]: type mismatch resolving `impl !Fn<(u32,)> == ()` +error[E0277]: the trait bound `(): !Fn(u32)` is not satisfied --> $DIR/opaque-type-unsatisfied-fn-bound.rs:5:17 | LL | fn produce() -> impl !Fn<(u32,)> {} - | ^^^^^^^^^^^^^^^^ types differ + | ^^^^^^^^^^^^^^^^ the trait bound `(): !Fn(u32)` is not satisfied error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0271`. +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.is_send.stderr b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.is_send.stderr index 736c8c10da97..6d2bbd8b08b4 100644 --- a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.is_send.stderr +++ b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.is_send.stderr @@ -1,9 +1,16 @@ -error[E0284]: type annotations needed: cannot satisfy `Foo == _` +error[E0283]: type annotations needed: cannot satisfy `Foo: Send` --> $DIR/dont-type_of-tait-in-defining-scope.rs:16:18 | LL | needs_send::(); - | ^^^ cannot satisfy `Foo == _` + | ^^^ + | + = note: cannot satisfy `Foo: Send` +note: required by a bound in `needs_send` + --> $DIR/dont-type_of-tait-in-defining-scope.rs:12:18 + | +LL | fn needs_send() {} + | ^^^^ required by this bound in `needs_send` error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0283`. diff --git a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.not_send.stderr b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.not_send.stderr index 736c8c10da97..6d2bbd8b08b4 100644 --- a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.not_send.stderr +++ b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.not_send.stderr @@ -1,9 +1,16 @@ -error[E0284]: type annotations needed: cannot satisfy `Foo == _` +error[E0283]: type annotations needed: cannot satisfy `Foo: Send` --> $DIR/dont-type_of-tait-in-defining-scope.rs:16:18 | LL | needs_send::(); - | ^^^ cannot satisfy `Foo == _` + | ^^^ + | + = note: cannot satisfy `Foo: Send` +note: required by a bound in `needs_send` + --> $DIR/dont-type_of-tait-in-defining-scope.rs:12:18 + | +LL | fn needs_send() {} + | ^^^^ required by this bound in `needs_send` error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0283`. diff --git a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.rs b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.rs index 2a08a3b2b948..fddf892e1ef1 100644 --- a/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.rs +++ b/tests/ui/traits/next-solver/opaques/dont-type_of-tait-in-defining-scope.rs @@ -14,7 +14,7 @@ fn needs_send() {} #[define_opaque(Foo)] fn test(_: Foo) { needs_send::(); - //~^ ERROR type annotations needed: cannot satisfy `Foo == _` + //~^ ERROR type annotations needed } #[define_opaque(Foo)] diff --git a/tests/ui/traits/static-method-overwriting.rs b/tests/ui/traits/static-method-overwriting.rs index 7a2a51a4b995..28edcde4c499 100644 --- a/tests/ui/traits/static-method-overwriting.rs +++ b/tests/ui/traits/static-method-overwriting.rs @@ -9,7 +9,7 @@ mod base { dummy: (), } - impl ::base::HasNew for Foo { + impl crate::base::HasNew for Foo { fn new() -> Foo { println!("Foo"); Foo { dummy: () } @@ -20,7 +20,7 @@ mod base { dummy: (), } - impl ::base::HasNew for Bar { + impl crate::base::HasNew for Bar { fn new() -> Bar { println!("Bar"); Bar { dummy: () } diff --git a/tests/ui/transmutability/references/reject_extension.stderr b/tests/ui/transmutability/references/reject_extension.stderr index 182106acf12c..a5f677850946 100644 --- a/tests/ui/transmutability/references/reject_extension.stderr +++ b/tests/ui/transmutability/references/reject_extension.stderr @@ -2,7 +2,7 @@ error[E0277]: `&Packed` cannot be safely transmuted into `&Packed` --> $DIR/reject_extension.rs:48:37 | LL | assert::is_transmutable::<&Src, &Dst>(); - | ^^^^ the referent size of `&Packed` (2 bytes) is smaller than that of `&Packed` (4 bytes) + | ^^^^ the size of `Packed` (2 bytes) is smaller than that of `Packed` (4 bytes) | note: required by a bound in `is_transmutable` --> $DIR/reject_extension.rs:13:14 diff --git a/tests/ui/transmutability/references/unit-to-u8.stderr b/tests/ui/transmutability/references/unit-to-u8.stderr index bc9f286e097a..35d1179f451b 100644 --- a/tests/ui/transmutability/references/unit-to-u8.stderr +++ b/tests/ui/transmutability/references/unit-to-u8.stderr @@ -2,7 +2,7 @@ error[E0277]: `&Unit` cannot be safely transmuted into `&u8` --> $DIR/unit-to-u8.rs:22:52 | LL | assert::is_maybe_transmutable::<&'static Unit, &'static u8>(); - | ^^^^^^^^^^^ the referent size of `&Unit` (0 bytes) is smaller than that of `&u8` (1 bytes) + | ^^^^^^^^^^^ the size of `Unit` (0 bytes) is smaller than that of `u8` (1 bytes) | note: required by a bound in `is_maybe_transmutable` --> $DIR/unit-to-u8.rs:9:14 diff --git a/tests/ui/transmutability/references/unsafecell.rs b/tests/ui/transmutability/references/unsafecell.rs index 4001f139770a..b0db4af45f54 100644 --- a/tests/ui/transmutability/references/unsafecell.rs +++ b/tests/ui/transmutability/references/unsafecell.rs @@ -38,10 +38,10 @@ fn mut_to_mut() { } fn mut_to_ref() { - // We don't care about `UnsafeCell` for transmutations in the form `&mut T - // -> &U`, because downgrading a `&mut T` to a `&U` deactivates `&mut T` for - // the lifetime of `&U`. - assert::is_maybe_transmutable::<&'static mut u8, &'static UnsafeCell>(); - assert::is_maybe_transmutable::<&'static mut UnsafeCell, &'static u8>(); - assert::is_maybe_transmutable::<&'static mut UnsafeCell, &'static UnsafeCell>(); + // `&mut UnsafeCell` is irrelevant in the source. + assert::is_maybe_transmutable::<&'static mut UnsafeCell, &'static u8>(); + // `&UnsafeCell` in forbidden in the destination, since the destination can be used to + // invalidate a shadowed source reference. + assert::is_maybe_transmutable::<&'static mut bool, &'static UnsafeCell>(); //~ ERROR: cannot be safely transmuted + assert::is_maybe_transmutable::<&'static mut UnsafeCell, &'static UnsafeCell>(); //~ ERROR: cannot be safely transmuted } diff --git a/tests/ui/transmutability/references/unsafecell.stderr b/tests/ui/transmutability/references/unsafecell.stderr index 6664d8a7d6fb..02a0935e84ea 100644 --- a/tests/ui/transmutability/references/unsafecell.stderr +++ b/tests/ui/transmutability/references/unsafecell.stderr @@ -28,6 +28,36 @@ LL | where LL | Dst: TransmuteFrom | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `is_maybe_transmutable` -error: aborting due to 2 previous errors +error[E0277]: `&mut bool` cannot be safely transmuted into `&UnsafeCell` + --> $DIR/unsafecell.rs:45:56 + | +LL | assert::is_maybe_transmutable::<&'static mut bool, &'static UnsafeCell>(); + | ^^^^^^^^^^^^^^^^^^^^^^^ the trait `Freeze` is not implemented for `UnsafeCell` + | +note: required by a bound in `is_maybe_transmutable` + --> $DIR/unsafecell.rs:12:14 + | +LL | pub fn is_maybe_transmutable() + | --------------------- required by a bound in this function +LL | where +LL | Dst: TransmuteFrom + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `is_maybe_transmutable` + +error[E0277]: `&mut UnsafeCell` cannot be safely transmuted into `&UnsafeCell` + --> $DIR/unsafecell.rs:46:68 + | +LL | assert::is_maybe_transmutable::<&'static mut UnsafeCell, &'static UnsafeCell>(); + | ^^^^^^^^^^^^^^^^^^^^^^^ the trait `Freeze` is not implemented for `UnsafeCell` + | +note: required by a bound in `is_maybe_transmutable` + --> $DIR/unsafecell.rs:12:14 + | +LL | pub fn is_maybe_transmutable() + | --------------------- required by a bound in this function +LL | where +LL | Dst: TransmuteFrom + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `is_maybe_transmutable` + +error: aborting due to 4 previous errors For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/tuple/tuple-struct-fields/test.rs b/tests/ui/tuple/tuple-struct-fields/test.rs index 00677090d78c..29aabf4579b1 100644 --- a/tests/ui/tuple/tuple-struct-fields/test.rs +++ b/tests/ui/tuple/tuple-struct-fields/test.rs @@ -1,6 +1,6 @@ mod foo { type T = (); - struct S1(pub(in foo) (), pub(T), pub(crate) (), pub(((), T))); + struct S1(pub(in crate::foo) (), pub(T), pub(crate) (), pub(((), T))); struct S2(pub((foo)) ()); //~^ ERROR expected one of `)` or `,`, found `(` //~| ERROR cannot find type `foo` in this scope diff --git a/tests/ui/tuple/tuple-struct-fields/test2.rs b/tests/ui/tuple/tuple-struct-fields/test2.rs index 2b2a2c127e98..544d486752c7 100644 --- a/tests/ui/tuple/tuple-struct-fields/test2.rs +++ b/tests/ui/tuple/tuple-struct-fields/test2.rs @@ -1,7 +1,7 @@ macro_rules! define_struct { ($t:ty) => { struct S1(pub $t); - struct S2(pub (in foo) ()); + struct S2(pub (in crate::foo) ()); struct S3(pub $t ()); //~^ ERROR expected one of `)` or `,`, found `(` } diff --git a/tests/ui/tuple/tuple-struct-fields/test3.rs b/tests/ui/tuple/tuple-struct-fields/test3.rs index 98d19426e773..b5f98a65fa6b 100644 --- a/tests/ui/tuple/tuple-struct-fields/test3.rs +++ b/tests/ui/tuple/tuple-struct-fields/test3.rs @@ -1,7 +1,7 @@ macro_rules! define_struct { ($t:ty) => { struct S1(pub($t)); - struct S2(pub (in foo) ()); + struct S2(pub (in crate::foo) ()); struct S3(pub($t) ()); //~^ ERROR expected one of `)` or `,`, found `(` } diff --git a/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.next.stderr b/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.next.stderr index 9e83de5375fd..f7e0245bc831 100644 --- a/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.next.stderr +++ b/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.next.stderr @@ -7,7 +7,7 @@ LL | impl Trait for Out { LL | impl Trait<(), In> for Out { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ conflicting implementation -error[E0284]: type annotations needed: cannot satisfy `Bar == _` +error[E0282]: type annotations needed --> $DIR/issue-84660-unsoundness.rs:24:37 | LL | fn convert(_i: In) -> Self::Out { @@ -16,9 +16,9 @@ LL | | LL | | LL | | unreachable!(); LL | | } - | |_____^ cannot satisfy `Bar == _` + | |_____^ cannot infer type error: aborting due to 2 previous errors -Some errors have detailed explanations: E0119, E0284. +Some errors have detailed explanations: E0119, E0282. For more information about an error, try `rustc --explain E0119`. diff --git a/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.rs b/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.rs index 7a540d2a5749..a385138b2950 100644 --- a/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.rs +++ b/tests/ui/type-alias-impl-trait/issue-84660-unsoundness.rs @@ -22,7 +22,7 @@ impl Trait for Out { type Out = Out; #[define_opaque(Bar)] fn convert(_i: In) -> Self::Out { - //[next]~^ ERROR: type annotations needed: cannot satisfy `Bar == _` + //[next]~^ ERROR: type annotations needed //[current]~^^ ERROR: item does not constrain `Bar::{opaque#0}` unreachable!(); } diff --git a/tests/ui/type-alias-impl-trait/nested-tait-inference2.next.stderr b/tests/ui/type-alias-impl-trait/nested-tait-inference2.next.stderr index b733739e4c86..d2127976e7d2 100644 --- a/tests/ui/type-alias-impl-trait/nested-tait-inference2.next.stderr +++ b/tests/ui/type-alias-impl-trait/nested-tait-inference2.next.stderr @@ -1,9 +1,9 @@ -error[E0284]: type annotations needed: cannot satisfy `impl Foo == ()` +error[E0282]: type annotations needed --> $DIR/nested-tait-inference2.rs:20:5 | LL | () - | ^^ cannot satisfy `impl Foo == ()` + | ^^ cannot infer type error: aborting due to 1 previous error -For more information about this error, try `rustc --explain E0284`. +For more information about this error, try `rustc --explain E0282`. diff --git a/tests/ui/type-alias-impl-trait/nested-tait-inference2.rs b/tests/ui/type-alias-impl-trait/nested-tait-inference2.rs index 4aeecb9140c5..606336178e5e 100644 --- a/tests/ui/type-alias-impl-trait/nested-tait-inference2.rs +++ b/tests/ui/type-alias-impl-trait/nested-tait-inference2.rs @@ -18,7 +18,7 @@ impl Foo for () {} fn foo() -> impl Foo { //[current]~^ ERROR: the trait bound `(): Foo` is not satisfied () - //[next]~^ ERROR: cannot satisfy `impl Foo == ()` + //[next]~^ ERROR: type annotations needed } fn main() {} diff --git a/tests/ui/type/auxiliary/crate_a1.rs b/tests/ui/type/auxiliary/crate_a1.rs index 616493193fd6..f8ee9ae15c17 100644 --- a/tests/ui/type/auxiliary/crate_a1.rs +++ b/tests/ui/type/auxiliary/crate_a1.rs @@ -2,10 +2,10 @@ pub struct Foo; pub trait Bar {} -pub fn bar() -> Box { +pub fn bar() -> Box { unimplemented!() } pub fn try_foo(x: Foo){} -pub fn try_bar(x: Box){} +pub fn try_bar(x: Box){} diff --git a/tests/ui/type/auxiliary/crate_a2.rs b/tests/ui/type/auxiliary/crate_a2.rs index 57a7685b77c4..fe22598e63e9 100644 --- a/tests/ui/type/auxiliary/crate_a2.rs +++ b/tests/ui/type/auxiliary/crate_a2.rs @@ -2,6 +2,6 @@ pub struct Foo; pub trait Bar {} -pub fn bar() -> Box { +pub fn bar() -> Box { unimplemented!() } diff --git a/tests/ui/type/issue-7607-2.rs b/tests/ui/type/issue-7607-2.rs index ebc4fe1c2d30..53fafdf9489e 100644 --- a/tests/ui/type/issue-7607-2.rs +++ b/tests/ui/type/issue-7607-2.rs @@ -6,7 +6,7 @@ pub mod a { } pub mod b { - use a::Foo; + use crate::a::Foo; impl Foo { fn bar(&self) { } } diff --git a/tests/ui/type/pattern_types/matching.rs b/tests/ui/type/pattern_types/matching.rs index b8463a8e8229..21f89b3b673b 100644 --- a/tests/ui/type/pattern_types/matching.rs +++ b/tests/ui/type/pattern_types/matching.rs @@ -1,6 +1,7 @@ #![feature(pattern_types, pattern_type_macro, structural_match)] //@ check-pass +//@ compile-flags: -Zvalidate-mir use std::marker::StructuralPartialEq; use std::pat::pattern_type; diff --git a/tests/ui/type/type-mismatch-same-crate-name.stderr b/tests/ui/type/type-mismatch-same-crate-name.stderr index 7b791549f563..8fafbfaa9342 100644 --- a/tests/ui/type/type-mismatch-same-crate-name.stderr +++ b/tests/ui/type/type-mismatch-same-crate-name.stderr @@ -59,7 +59,7 @@ LL | extern crate crate_a1 as a; note: function defined here --> $DIR/auxiliary/crate_a1.rs:11:8 | -LL | pub fn try_bar(x: Box){} +LL | pub fn try_bar(x: Box){} | ^^^^^^^ error: aborting due to 2 previous errors diff --git a/tests/ui/typeck/issue-114529-illegal-break-with-value.stderr b/tests/ui/typeck/issue-114529-illegal-break-with-value.stderr index de993df722ce..872c506c7f1f 100644 --- a/tests/ui/typeck/issue-114529-illegal-break-with-value.stderr +++ b/tests/ui/typeck/issue-114529-illegal-break-with-value.stderr @@ -1,3 +1,21 @@ +error[E0571]: `break` with value from a `while` loop + --> $DIR/issue-114529-illegal-break-with-value.rs:22:9 + | +LL | while true { + | ---------- you can't `break` with a value in a `while` loop +LL | / break (|| { +LL | | let local = 9; +LL | | }); + | |__________^ can only break with a value inside `loop` or breakable block + | +help: use `break` on its own without a value inside this `while` loop + | +LL - break (|| { +LL - let local = 9; +LL - }); +LL + break; + | + error[E0571]: `break` with value from a `while` loop --> $DIR/issue-114529-illegal-break-with-value.rs:9:13 | @@ -26,24 +44,6 @@ LL - break v; LL + break; | -error[E0571]: `break` with value from a `while` loop - --> $DIR/issue-114529-illegal-break-with-value.rs:22:9 - | -LL | while true { - | ---------- you can't `break` with a value in a `while` loop -LL | / break (|| { -LL | | let local = 9; -LL | | }); - | |__________^ can only break with a value inside `loop` or breakable block - | -help: use `break` on its own without a value inside this `while` loop - | -LL - break (|| { -LL - let local = 9; -LL - }); -LL + break; - | - error: aborting due to 3 previous errors For more information about this error, try `rustc --explain E0571`. diff --git a/tests/ui/underscore-imports/basic.rs b/tests/ui/underscore-imports/basic.rs index 624ecb47ca68..8d8ff5c47bc2 100644 --- a/tests/ui/underscore-imports/basic.rs +++ b/tests/ui/underscore-imports/basic.rs @@ -18,25 +18,25 @@ mod m { fn tr2_is_in_scope(&self) {} } - impl Tr1 for ::S {} - impl Tr2 for ::S {} + impl Tr1 for crate::S {} + impl Tr2 for crate::S {} } mod unused { - use m::Tr1 as _; //~ WARN unused import - use S as _; //~ WARN unused import + use crate::m::Tr1 as _; //~ WARN unused import + use crate::S as _; //~ WARN unused import extern crate core as _; // OK } mod outer { mod middle { - pub use m::Tr1 as _; - pub use m::Tr2 as _; // OK, no name conflict + pub use crate::m::Tr1 as _; + pub use crate::m::Tr2 as _; // OK, no name conflict struct Tr1; // OK, no name conflict fn check() { // Both traits are in scope - ::S.tr1_is_in_scope(); - ::S.tr2_is_in_scope(); + crate::S.tr1_is_in_scope(); + crate::S.tr2_is_in_scope(); } mod inner { @@ -44,8 +44,8 @@ mod outer { use super::*; fn check() { // Both traits are in scope - ::S.tr1_is_in_scope(); - ::S.tr2_is_in_scope(); + crate::S.tr1_is_in_scope(); + crate::S.tr2_is_in_scope(); } } } @@ -54,8 +54,8 @@ mod outer { use self::middle::*; fn check() { // Both traits are in scope - ::S.tr1_is_in_scope(); - ::S.tr2_is_in_scope(); + crate::S.tr1_is_in_scope(); + crate::S.tr2_is_in_scope(); } } diff --git a/tests/ui/underscore-imports/basic.stderr b/tests/ui/underscore-imports/basic.stderr index c51493562ebd..666d07349dfb 100644 --- a/tests/ui/underscore-imports/basic.stderr +++ b/tests/ui/underscore-imports/basic.stderr @@ -1,8 +1,8 @@ -warning: unused import: `m::Tr1 as _` +warning: unused import: `crate::m::Tr1 as _` --> $DIR/basic.rs:26:9 | -LL | use m::Tr1 as _; - | ^^^^^^^^^^^ +LL | use crate::m::Tr1 as _; + | ^^^^^^^^^^^^^^^^^^ | note: the lint level is defined here --> $DIR/basic.rs:4:9 @@ -10,11 +10,11 @@ note: the lint level is defined here LL | #![warn(unused_imports, unused_extern_crates)] | ^^^^^^^^^^^^^^ -warning: unused import: `S as _` +warning: unused import: `crate::S as _` --> $DIR/basic.rs:27:9 | -LL | use S as _; - | ^^^^^^ +LL | use crate::S as _; + | ^^^^^^^^^^^^^ warning: 2 warnings emitted diff --git a/tests/ui/unpretty/exhaustive.expanded.stdout b/tests/ui/unpretty/exhaustive.expanded.stdout index 9712ba58e627..cd1a5d0af08a 100644 --- a/tests/ui/unpretty/exhaustive.expanded.stdout +++ b/tests/ui/unpretty/exhaustive.expanded.stdout @@ -190,7 +190,7 @@ mod expressions { (static async || value); (static async move || value); || -> u8 { value }; - 1 + (|| {}); + 1 + || {}; } /// ExprKind::Block diff --git a/tests/ui/unresolved/unresolved-import-recovery.rs b/tests/ui/unresolved/unresolved-import-recovery.rs index 0b0653378cbb..8657bb661a87 100644 --- a/tests/ui/unresolved/unresolved-import-recovery.rs +++ b/tests/ui/unresolved/unresolved-import-recovery.rs @@ -1,7 +1,7 @@ // Check that unresolved imports do not create additional errors and ICEs mod m { - pub use unresolved; //~ ERROR unresolved import `unresolved` + pub use crate::unresolved; //~ ERROR unresolved import `crate::unresolved` fn f() { let unresolved = 0; // OK diff --git a/tests/ui/unresolved/unresolved-import-recovery.stderr b/tests/ui/unresolved/unresolved-import-recovery.stderr index 1c006049756e..ec41c9e79d74 100644 --- a/tests/ui/unresolved/unresolved-import-recovery.stderr +++ b/tests/ui/unresolved/unresolved-import-recovery.stderr @@ -1,8 +1,8 @@ -error[E0432]: unresolved import `unresolved` +error[E0432]: unresolved import `crate::unresolved` --> $DIR/unresolved-import-recovery.rs:4:13 | -LL | pub use unresolved; - | ^^^^^^^^^^ no `unresolved` in the root +LL | pub use crate::unresolved; + | ^^^^^^^^^^^^^^^^^ no `unresolved` in the root error: aborting due to 1 previous error diff --git a/tests/ui/unsafe/break-inside-unsafe-block-issue-128604.stderr b/tests/ui/unsafe/break-inside-unsafe-block-issue-128604.stderr index b7cbe1a5cf46..2f01331db9a3 100644 --- a/tests/ui/unsafe/break-inside-unsafe-block-issue-128604.stderr +++ b/tests/ui/unsafe/break-inside-unsafe-block-issue-128604.stderr @@ -1,9 +1,3 @@ -error[E0268]: `break` outside of a loop or labeled block - --> $DIR/break-inside-unsafe-block-issue-128604.rs:2:28 - | -LL | let a = ["_"; unsafe { break; 1 + 2 }]; - | ^^^^^ cannot `break` outside of a loop or labeled block - error[E0268]: `break` outside of a loop or labeled block --> $DIR/break-inside-unsafe-block-issue-128604.rs:14:9 | @@ -37,6 +31,12 @@ LL | unsafe { LL ~ break 'block; | +error[E0268]: `break` outside of a loop or labeled block + --> $DIR/break-inside-unsafe-block-issue-128604.rs:2:28 + | +LL | let a = ["_"; unsafe { break; 1 + 2 }]; + | ^^^^^ cannot `break` outside of a loop or labeled block + error: aborting due to 4 previous errors For more information about this error, try `rustc --explain E0268`. diff --git a/tests/ui/unsized/unsized3-rpass.rs b/tests/ui/unsized/unsized3-rpass.rs index ff35051774bc..03aa1a538ead 100644 --- a/tests/ui/unsized/unsized3-rpass.rs +++ b/tests/ui/unsized/unsized3-rpass.rs @@ -37,7 +37,7 @@ impl Tr for St { } struct Qux<'a> { - f: Tr + 'a, + f: dyn Tr + 'a, } pub fn main() { @@ -85,7 +85,7 @@ pub fn main() { } let obj: Box = Box::new(St { f: 42 }); - let obj: &Tr = &*obj; + let obj: &dyn Tr = &*obj; let data: Box<_> = Box::new(Qux_ { f: St { f: 234 } }); let x: &Qux = &*ptr::from_raw_parts::(&*data as *const _, ptr::metadata(obj)); assert_eq!(x.f.foo(), 234); diff --git a/tests/ui/use/use-mod/use-mod-4.rs b/tests/ui/use/use-mod/use-mod-4.rs index 46ae8ddadc09..34ce7c719575 100644 --- a/tests/ui/use/use-mod/use-mod-4.rs +++ b/tests/ui/use/use-mod/use-mod-4.rs @@ -1,4 +1,4 @@ -use foo::self; //~ ERROR unresolved import `foo` +use crate::foo::self; //~ ERROR unresolved import `crate::foo` //~^ ERROR `self` imports are only allowed within a { } list use std::mem::self; diff --git a/tests/ui/use/use-mod/use-mod-4.stderr b/tests/ui/use/use-mod/use-mod-4.stderr index 0b4fbadb4582..d4621296c0d1 100644 --- a/tests/ui/use/use-mod/use-mod-4.stderr +++ b/tests/ui/use/use-mod/use-mod-4.stderr @@ -1,18 +1,18 @@ error[E0429]: `self` imports are only allowed within a { } list - --> $DIR/use-mod-4.rs:1:8 + --> $DIR/use-mod-4.rs:1:15 | -LL | use foo::self; - | ^^^^^^ +LL | use crate::foo::self; + | ^^^^^^ | help: consider importing the module directly | -LL - use foo::self; -LL + use foo; +LL - use crate::foo::self; +LL + use crate::foo; | help: alternatively, use the multi-path `use` syntax to import `self` | -LL | use foo::{self}; - | + + +LL | use crate::foo::{self}; + | + + error[E0429]: `self` imports are only allowed within a { } list --> $DIR/use-mod-4.rs:4:13 @@ -30,11 +30,11 @@ help: alternatively, use the multi-path `use` syntax to import `self` LL | use std::mem::{self}; | + + -error[E0432]: unresolved import `foo` +error[E0432]: unresolved import `crate::foo` --> $DIR/use-mod-4.rs:1:5 | -LL | use foo::self; - | ^^^^^^^^^ no `foo` in the root +LL | use crate::foo::self; + | ^^^^^^^^^^^^^^^^ no `foo` in the root error: aborting due to 3 previous errors diff --git a/tests/ui/variance/variance-trait-matching.stderr b/tests/ui/variance/variance-trait-matching.stderr index 9c72fe239dde..495669668c55 100644 --- a/tests/ui/variance/variance-trait-matching.stderr +++ b/tests/ui/variance/variance-trait-matching.stderr @@ -1,11 +1,13 @@ error[E0621]: explicit lifetime required in the type of `get` --> $DIR/variance-trait-matching.rs:24:5 | -LL | fn get<'a, G>(get: &G) -> i32 - | -- help: add explicit lifetime `'a` to the type of `get`: `&'a G` -... LL | pick(get, &22) | ^^^^^^^^^^^^^^ lifetime `'a` required + | +help: add explicit lifetime `'a` to the type of `get` + | +LL | fn get<'a, G>(get: &'a G) -> i32 + | ++ error: aborting due to 1 previous error diff --git a/tests/ui/warnings/no-explicit-path-issue-122509.rs b/tests/ui/warnings/no-explicit-path-issue-122509.rs index 4e8eefde5dad..5be4b174076d 100644 --- a/tests/ui/warnings/no-explicit-path-issue-122509.rs +++ b/tests/ui/warnings/no-explicit-path-issue-122509.rs @@ -7,13 +7,13 @@ fn one() -> usize { pub mod a { pub fn two() -> usize { - ::one() + ::one() + crate::one() + crate::one() } } pub mod b { pub fn three() -> usize { - ::one() + ::a::two() + crate::one() + crate::a::two() } } diff --git a/tests/ui/weird-exprs.rs b/tests/ui/weird-exprs.rs index b24e754a4ec9..7db92d460671 100644 --- a/tests/ui/weird-exprs.rs +++ b/tests/ui/weird-exprs.rs @@ -105,7 +105,7 @@ fn u8(u8: u8) { u8!(u8); let &u8: &u8 = u8::u8(&8u8); - ::u8(0u8); + crate::u8(0u8); u8 }); } diff --git a/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.rs b/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.rs index a95e10b7265d..53f07a94fd15 100644 --- a/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.rs +++ b/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.rs @@ -1,17 +1,11 @@ -trait Trait { +trait Trait { //~^ ERROR cannot find value `bar` in this scope //~| ERROR cycle detected when computing type of `Trait::N` - //~| WARN trait objects without an explicit `dyn` are deprecated [bare_trait_objects] - //~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! - fn fnc(&self) -> Trait { + fn fnc(&self) -> dyn Trait { //~^ ERROR the name `N` is already used for a generic parameter in this item's generic parameters //~| ERROR expected value, found builtin type `u32` //~| ERROR defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions //~| ERROR associated item referring to unboxed trait object for its own trait - //~| WARN trait objects without an explicit `dyn` are deprecated [bare_trait_objects] - //~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! - //~| WARN trait objects without an explicit `dyn` are deprecated [bare_trait_objects] - //~| WARN this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! bar //~^ ERROR cannot find value `bar` in this scope } diff --git a/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.stderr b/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.stderr index 59eef0c63278..a085dd6ac576 100644 --- a/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.stderr +++ b/tests/ui/wf/ice-hir-wf-check-anon-const-issue-122199.stderr @@ -1,106 +1,66 @@ error[E0403]: the name `N` is already used for a generic parameter in this item's generic parameters - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:18 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:18 | -LL | trait Trait { +LL | trait Trait { | - first use of `N` ... -LL | fn fnc(&self) -> Trait { +LL | fn fnc(&self) -> dyn Trait { | ^ already used error[E0425]: cannot find value `bar` in this scope - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:30 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:34 | -LL | trait Trait { - | ^^^ not found in this scope +LL | trait Trait { + | ^^^ not found in this scope error[E0423]: expected value, found builtin type `u32` - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:29 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:33 | -LL | fn fnc(&self) -> Trait { - | ^^^ not a value +LL | fn fnc(&self) -> dyn Trait { + | ^^^ not a value error[E0425]: cannot find value `bar` in this scope - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:15:9 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:9:9 | LL | bar | ^^^ not found in this scope -warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:22 - | -LL | trait Trait { - | ^^^^^ - | - = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! - = note: for more information, see - = note: `#[warn(bare_trait_objects)]` on by default -help: if this is a dyn-compatible trait, use `dyn` +error[E0391]: cycle detected when computing type of `Trait::N` + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:26 | LL | trait Trait { - | +++ - -error[E0391]: cycle detected when computing type of `Trait::N` - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:22 - | -LL | trait Trait { - | ^^^^^ + | ^^^^^ | = note: ...which immediately requires computing type of `Trait::N` again note: cycle used when computing explicit predicates of trait `Trait` --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:1:1 | -LL | trait Trait { - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +LL | trait Trait { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ = note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:12 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:12 | -LL | fn fnc(&self) -> Trait { - | ^^^^^^^^^^^^^^^^^^^^ - -warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:44 - | -LL | fn fnc(&self) -> Trait { - | ^^^^^ - | - = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! - = note: for more information, see -help: if this is a dyn-compatible trait, use `dyn` - | -LL | fn fnc(&self) -> dyn Trait { - | +++ - -warning: trait objects without an explicit `dyn` are deprecated - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:21 - | -LL | fn fnc(&self) -> Trait { - | ^^^^^ - | - = warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2021! - = note: for more information, see -help: if this is a dyn-compatible trait, use `dyn` - | -LL | fn fnc(&self) -> Trait { - | +++ +LL | fn fnc(&self) -> dyn Trait { + | ^^^^^^^^^^^^^^^^^^^^^^^^ error: associated item referring to unboxed trait object for its own trait - --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:6:44 + --> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:48 | -LL | trait Trait { +LL | trait Trait { | ----- in this trait ... -LL | fn fnc(&self) -> Trait { - | ^^^^^ +LL | fn fnc(&self) -> dyn Trait { + | ^^^^^^^^^ | help: you might have meant to use `Self` to refer to the implementing type | -LL - fn fnc(&self) -> Trait { -LL + fn fnc(&self) -> Self { +LL - fn fnc(&self) -> dyn Trait { +LL + fn fnc(&self) -> Self { | -error: aborting due to 7 previous errors; 3 warnings emitted +error: aborting due to 7 previous errors Some errors have detailed explanations: E0391, E0403, E0423, E0425. For more information about an error, try `rustc --explain E0391`. diff --git a/triagebot.toml b/triagebot.toml index 15c56f8861f5..e5af77b6d443 100644 --- a/triagebot.toml +++ b/triagebot.toml @@ -44,29 +44,6 @@ remove_labels = ["S-waiting-on-author"] # Those labels are added when PR author requests a review from an assignee add_labels = ["S-waiting-on-review"] -[ping.icebreakers-llvm] -message = """\ -Hey LLVM ICE-breakers! This bug has been identified as a good -"LLVM ICE-breaking candidate". In case it's useful, here are some -[instructions] for tackling these sorts of bugs. Maybe take a look? -Thanks! <3 - -[instructions]: https://rustc-dev-guide.rust-lang.org/notification-groups/llvm.html -""" -label = "ICEBreaker-LLVM" - -[ping.icebreakers-cleanup-crew] -alias = ["cleanup", "cleanups", "cleanup-crew", "shrink", "reduce", "bisect"] -message = """\ -Hey Cleanup Crew ICE-breakers! This bug has been identified as a good -"Cleanup ICE-breaking candidate". In case it's useful, here are some -[instructions] for tackling these sorts of bugs. Maybe take a look? -Thanks! <3 - -[instructions]: https://rustc-dev-guide.rust-lang.org/notification-groups/cleanup-crew.html -""" -label = "ICEBreaker-Cleanup-Crew" - [ping.windows] message = """\ Hey Windows Group! This bug has been identified as a good "Windows candidate". @@ -729,6 +706,41 @@ don't know ] message_on_remove = "PR #{number}'s stable-nomination has been removed." +[notify-zulip."beta-nominated".bootstrap] +required_labels = ["T-bootstrap"] +zulip_stream = 507486 # #t-infra/bootstrap/backports +topic = "#{number}: beta-nominated" +message_on_add = [ + """\ +@*T-bootstrap* PR #{number} "{title}" has been nominated for beta backport. +""", + """\ +/poll Approve beta backport of #{number}? +approve +decline +don't know +""", +] +message_on_remove = "PR #{number}'s beta-nomination has been removed." + +[notify-zulip."stable-nominated".bootstrap] +required_labels = ["T-bootstrap"] +zulip_stream = 507486 # #t-infra/bootstrap/backports +topic = "#{number}: stable-nominated" +message_on_add = [ + """\ +@*T-bootstrap* PR #{number} "{title}" has been nominated for stable backport. +""", + """\ +/poll Approve stable backport of #{number}? +approve +approve (but does not justify new dot release on its own) +decline +don't know +""", +] +message_on_remove = "PR #{number}'s stable-nomination has been removed." + [notify-zulip."A-edition-2021"] required_labels = ["C-bug"] zulip_stream = 268952 # #edition @@ -1217,6 +1229,7 @@ compiler = [ "@oli-obk", "@petrochenkov", "@SparrowLii", + "@WaffleLapkin", "@wesleywiser", ] libs = [ @@ -1228,14 +1241,6 @@ libs = [ "@thomcc", "@ibraheemdev", ] -bootstrap = [ - "@Mark-Simulacrum", - "@albertlarsan68", - "@onur-ozkan", - "@kobzol", - "@jieyouxu", - "@clubby789", -] infra-ci = [ "@Mark-Simulacrum", "@Kobzol", @@ -1255,6 +1260,7 @@ codegen = [ "@dianqk", "@saethlin", "@workingjubilee", + "@WaffleLapkin", ] query-system = [ "@oli-obk", @@ -1424,8 +1430,8 @@ compiletest = [ "/src/tools/rustdoc-themes" = ["rustdoc"] "/src/tools/tidy" = ["bootstrap"] "/src/tools/x" = ["bootstrap"] -"/src/tools/rustdoc-gui-test" = ["bootstrap", "@onur-ozkan"] -"/src/tools/libcxx-version" = ["@onur-ozkan"] +"/src/tools/rustdoc-gui-test" = ["bootstrap"] +"/src/tools/libcxx-version" = ["bootstrap"] # Enable review queue tracking # Documentation at: https://forge.rust-lang.org/triagebot/review-queue-tracking.html