mirror of
https://github.com/rust-lang/rust.git
synced 2025-05-14 02:49:40 +00:00
Merge from rustc
This commit is contained in:
commit
cae5d8a81c
1
.gitattributes
vendored
1
.gitattributes
vendored
@ -5,6 +5,7 @@
|
||||
*.h rust
|
||||
*.rs rust diff=rust
|
||||
*.fixed linguist-language=Rust
|
||||
*.pp linguist-language=Rust
|
||||
*.mir linguist-language=Rust
|
||||
src/etc/installer/gfx/* binary
|
||||
src/vendor/** -text
|
||||
|
21
.github/workflows/ci.yml
vendored
21
.github/workflows/ci.yml
vendored
@ -69,6 +69,8 @@ jobs:
|
||||
env:
|
||||
CI_JOB_NAME: ${{ matrix.name }}
|
||||
CI_JOB_DOC_URL: ${{ matrix.doc_url }}
|
||||
GITHUB_WORKFLOW_RUN_ID: ${{ github.run_id }}
|
||||
GITHUB_REPOSITORY: ${{ github.repository }}
|
||||
CARGO_REGISTRIES_CRATES_IO_PROTOCOL: sparse
|
||||
# commit of PR sha or commit sha. `GITHUB_SHA` is not accurate for PRs.
|
||||
HEAD_SHA: ${{ github.event.pull_request.head.sha || github.sha }}
|
||||
@ -239,16 +241,31 @@ jobs:
|
||||
if: github.event_name == 'push' || env.DEPLOY == '1' || env.DEPLOY_ALT == '1'
|
||||
|
||||
- name: postprocess metrics into the summary
|
||||
# This step is not critical, and if some I/O problem happens, we don't want
|
||||
# to cancel the build.
|
||||
continue-on-error: true
|
||||
run: |
|
||||
if [ -f build/metrics.json ]; then
|
||||
./build/citool/debug/citool postprocess-metrics build/metrics.json ${GITHUB_STEP_SUMMARY}
|
||||
METRICS=build/metrics.json
|
||||
elif [ -f obj/build/metrics.json ]; then
|
||||
./build/citool/debug/citool postprocess-metrics obj/build/metrics.json ${GITHUB_STEP_SUMMARY}
|
||||
METRICS=obj/build/metrics.json
|
||||
else
|
||||
echo "No metrics.json found"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Get closest bors merge commit
|
||||
PARENT_COMMIT=`git rev-list --author='bors <bors@rust-lang.org>' -n1 --first-parent HEAD^1`
|
||||
|
||||
./build/citool/debug/citool postprocess-metrics \
|
||||
--job-name ${CI_JOB_NAME} \
|
||||
--parent ${PARENT_COMMIT} \
|
||||
${METRICS} >> ${GITHUB_STEP_SUMMARY}
|
||||
|
||||
- name: upload job metrics to DataDog
|
||||
# This step is not critical, and if some I/O problem happens, we don't want
|
||||
# to cancel the build.
|
||||
continue-on-error: true
|
||||
if: needs.calculate_matrix.outputs.run_type != 'pr'
|
||||
env:
|
||||
DATADOG_API_KEY: ${{ secrets.DATADOG_API_KEY }}
|
||||
|
7
.github/workflows/ghcr.yml
vendored
7
.github/workflows/ghcr.yml
vendored
@ -5,6 +5,9 @@
|
||||
# Docker Hub has a rate limit, while ghcr.io doesn't.
|
||||
# Those images are pushed to ghcr.io by this job.
|
||||
#
|
||||
# While Docker Hub rate limit *shouldn't* be an issue on GitHub Actions,
|
||||
# it certainly is for AWS codebuild.
|
||||
#
|
||||
# Note that authenticating to DockerHub or other registries isn't possible
|
||||
# for PR jobs, because forks can't access secrets.
|
||||
# That's why we use ghcr.io: it has no rate limit and it doesn't require authentication.
|
||||
@ -54,6 +57,10 @@ jobs:
|
||||
"ubuntu:22.04"
|
||||
# Mirrored because used by all linux CI jobs, including mingw-check-tidy
|
||||
"moby/buildkit:buildx-stable-1"
|
||||
# Mirrored because used when CI is running inside a Docker container
|
||||
"alpine:3.4"
|
||||
# Mirrored because used by dist-x86_64-linux
|
||||
"centos:7"
|
||||
)
|
||||
|
||||
# Mirror each image from DockerHub to ghcr.io
|
||||
|
7
.github/workflows/post-merge.yml
vendored
7
.github/workflows/post-merge.yml
vendored
@ -35,13 +35,12 @@ jobs:
|
||||
|
||||
cd src/ci/citool
|
||||
|
||||
printf "*This is an experimental post-merge analysis report. You can ignore it.*\n\n" > output.log
|
||||
printf "<details>\n<summary>Post-merge report</summary>\n\n" >> output.log
|
||||
printf "<details>\n<summary>What is this?</summary>\n" >> output.log
|
||||
printf "This is an experimental post-merge analysis report that shows differences in test outcomes between the merged PR and its parent PR.\n" >> output.log
|
||||
printf "</details>\n\n" >> output.log
|
||||
|
||||
cargo run --release post-merge-report ${PARENT_COMMIT} ${{ github.sha }} >> output.log
|
||||
|
||||
printf "</details>\n" >> output.log
|
||||
|
||||
cat output.log
|
||||
|
||||
gh pr comment ${HEAD_PR} -F output.log
|
||||
|
2
.gitmodules
vendored
2
.gitmodules
vendored
@ -45,7 +45,7 @@
|
||||
shallow = true
|
||||
[submodule "src/tools/enzyme"]
|
||||
path = src/tools/enzyme
|
||||
url = https://github.com/EnzymeAD/Enzyme.git
|
||||
url = https://github.com/rust-lang/Enzyme.git
|
||||
shallow = true
|
||||
[submodule "src/gcc"]
|
||||
path = src/gcc
|
||||
|
910
Cargo.lock
910
Cargo.lock
File diff suppressed because it is too large
Load Diff
134
RELEASES.md
134
RELEASES.md
@ -1,3 +1,137 @@
|
||||
Version 1.86.0 (2025-04-03)
|
||||
==========================
|
||||
|
||||
<a id="1.86.0-Language"></a>
|
||||
|
||||
Language
|
||||
--------
|
||||
- [Stabilize upcasting trait objects to supertraits.](https://github.com/rust-lang/rust/pull/134367)
|
||||
- [Allow safe functions to be marked with the `#[target_feature]` attribute.](https://github.com/rust-lang/rust/pull/134090)
|
||||
- [The `missing_abi` lint now warns-by-default.](https://github.com/rust-lang/rust/pull/132397)
|
||||
- Rust now lints about double negations, to catch cases that might have intended to be a prefix decrement operator (`--x`) as written in other languages. This was previously a clippy lint, `clippy::double_neg`, and is [now available directly in Rust as `double_negations`.](https://github.com/rust-lang/rust/pull/126604)
|
||||
- [More pointers are now detected as definitely not-null based on their alignment in const eval.](https://github.com/rust-lang/rust/pull/133700)
|
||||
- [Empty `repr()` attribute applied to invalid items are now correctly rejected.](https://github.com/rust-lang/rust/pull/133925)
|
||||
- [Inner attributes `#![test]` and `#![rustfmt::skip]` are no longer accepted in more places than intended.](https://github.com/rust-lang/rust/pull/134276)
|
||||
|
||||
<a id="1.86.0-Compiler"></a>
|
||||
|
||||
Compiler
|
||||
--------
|
||||
- [Debug-assert that raw pointers are non-null on access.](https://github.com/rust-lang/rust/pull/134424)
|
||||
- [Change `-O` to mean `-C opt-level=3` instead of `-C opt-level=2` to match Cargo's defaults.](https://github.com/rust-lang/rust/pull/135439)
|
||||
- [Fix emission of `overflowing_literals` under certain macro environments.](https://github.com/rust-lang/rust/pull/136393)
|
||||
|
||||
<a id="1.86.0-Platform-Support"></a>
|
||||
|
||||
Platform Support
|
||||
----------------
|
||||
- [Replace `i686-unknown-redox` target with `i586-unknown-redox`.](https://github.com/rust-lang/rust/pull/136698)
|
||||
- [Increase baseline CPU of `i686-unknown-hurd-gnu` to Pentium 4.](https://github.com/rust-lang/rust/pull/136700)
|
||||
- New tier 3 targets:
|
||||
- [`{aarch64-unknown,x86_64-pc}-nto-qnx710_iosock`](https://github.com/rust-lang/rust/pull/133631).
|
||||
For supporting Neutrino QNX 7.1 with `io-socket` network stack.
|
||||
- [`{aarch64-unknown,x86_64-pc}-nto-qnx800`](https://github.com/rust-lang/rust/pull/133631).
|
||||
For supporting Neutrino QNX 8.0 (`no_std`-only).
|
||||
- [`{x86_64,i686}-win7-windows-gnu`](https://github.com/rust-lang/rust/pull/134609).
|
||||
Intended for backwards compatibility with Windows 7. `{x86_64,i686}-win7-windows-msvc` are the Windows MSVC counterparts that already exist as Tier 3 targets.
|
||||
- [`amdgcn-amd-amdhsa`](https://github.com/rust-lang/rust/pull/134740).
|
||||
- [`x86_64-pc-cygwin`](https://github.com/rust-lang/rust/pull/134999).
|
||||
- [`{mips,mipsel}-mti-none-elf`](https://github.com/rust-lang/rust/pull/135074).
|
||||
Initial bare-metal support.
|
||||
- [`m68k-unknown-none-elf`](https://github.com/rust-lang/rust/pull/135085).
|
||||
- [`armv7a-nuttx-{eabi,eabihf}`, `aarch64-unknown-nuttx`, and `thumbv7a-nuttx-{eabi,eabihf}`](https://github.com/rust-lang/rust/pull/135757).
|
||||
|
||||
Refer to Rust's [platform support page][platform-support-doc]
|
||||
for more information on Rust's tiered platform support.
|
||||
|
||||
<a id="1.86.0-Libraries"></a>
|
||||
|
||||
Libraries
|
||||
---------
|
||||
- The type of `FromBytesWithNulError` in `CStr::from_bytes_with_nul(bytes: &[u8]) -> Result<&Self, FromBytesWithNulError>` was [changed from an opaque struct to an enum](https://github.com/rust-lang/rust/pull/134143), allowing users to examine why the conversion failed.
|
||||
- [Remove `RustcDecodable` and `RustcEncodable`.](https://github.com/rust-lang/rust/pull/134272)
|
||||
- [Deprecate libtest's `--logfile` option.](https://github.com/rust-lang/rust/pull/134283)
|
||||
- [On recent versions of Windows, `std::fs::remove_file` will now remove read-only files.](https://github.com/rust-lang/rust/pull/134679)
|
||||
|
||||
<a id="1.86.0-Stabilized-APIs"></a>
|
||||
|
||||
Stabilized APIs
|
||||
---------------
|
||||
|
||||
- [`{float}::next_down`](https://doc.rust-lang.org/stable/std/primitive.f64.html#method.next_down)
|
||||
- [`{float}::next_up`](https://doc.rust-lang.org/stable/std/primitive.f64.html#method.next_up)
|
||||
- [`<[_]>::get_disjoint_mut`](https://doc.rust-lang.org/stable/std/primitive.slice.html#method.get_disjoint_mut)
|
||||
- [`<[_]>::get_disjoint_unchecked_mut`](https://doc.rust-lang.org/stable/std/primitive.slice.html#method.get_disjoint_unchecked_mut)
|
||||
- [`slice::GetDisjointMutError`](https://doc.rust-lang.org/stable/std/slice/enum.GetDisjointMutError.html)
|
||||
- [`HashMap::get_disjoint_mut`](https://doc.rust-lang.org/std/collections/hash_map/struct.HashMap.html#method.get_disjoint_mut)
|
||||
- [`HashMap::get_disjoint_unchecked_mut`](https://doc.rust-lang.org/std/collections/hash_map/struct.HashMap.html#method.get_disjoint_unchecked_mut)
|
||||
- [`NonZero::count_ones`](https://doc.rust-lang.org/stable/std/num/struct.NonZero.html#method.count_ones)
|
||||
- [`Vec::pop_if`](https://doc.rust-lang.org/std/vec/struct.Vec.html#method.pop_if)
|
||||
- [`sync::Once::wait`](https://doc.rust-lang.org/stable/std/sync/struct.Once.html#method.wait)
|
||||
- [`sync::Once::wait_force`](https://doc.rust-lang.org/stable/std/sync/struct.Once.html#method.wait_force)
|
||||
- [`sync::OnceLock::wait`](https://doc.rust-lang.org/stable/std/sync/struct.OnceLock.html#method.wait)
|
||||
|
||||
These APIs are now stable in const contexts:
|
||||
|
||||
- [`hint::black_box`](https://doc.rust-lang.org/stable/std/hint/fn.black_box.html)
|
||||
- [`io::Cursor::get_mut`](https://doc.rust-lang.org/stable/std/io/struct.Cursor.html#method.get_mut)
|
||||
- [`io::Cursor::set_position`](https://doc.rust-lang.org/stable/std/io/struct.Cursor.html#method.set_position)
|
||||
- [`str::is_char_boundary`](https://doc.rust-lang.org/stable/std/primitive.str.html#method.is_char_boundary)
|
||||
- [`str::split_at`](https://doc.rust-lang.org/stable/std/primitive.str.html#method.split_at)
|
||||
- [`str::split_at_checked`](https://doc.rust-lang.org/stable/std/primitive.str.html#method.split_at_checked)
|
||||
- [`str::split_at_mut`](https://doc.rust-lang.org/stable/std/primitive.str.html#method.split_at_mut)
|
||||
- [`str::split_at_mut_checked`](https://doc.rust-lang.org/stable/std/primitive.str.html#method.split_at_mut_checked)
|
||||
|
||||
<a id="1.86.0-Cargo"></a>
|
||||
|
||||
Cargo
|
||||
-----
|
||||
- [When merging, replace rather than combine configuration keys that refer to a program path and its arguments.](https://github.com/rust-lang/cargo/pull/15066/)
|
||||
- [Error if both `--package` and `--workspace` are passed but the requested package is missing.](https://github.com/rust-lang/cargo/pull/15071/) This was previously silently ignored, which was considered a bug since missing packages should be reported.
|
||||
- [Deprecate the token argument in `cargo login` to avoid shell history leaks.](https://github.com/rust-lang/cargo/pull/15057/)
|
||||
- [Simplify the implementation of `SourceID` comparisons.](https://github.com/rust-lang/cargo/pull/14980/) This may potentially change behavior if the canonicalized URL compares differently in alternative registries.
|
||||
|
||||
<a id="1.86.0-Rustdoc"></a>
|
||||
|
||||
Rustdoc
|
||||
-----
|
||||
- [Add a sans-serif font setting.](https://github.com/rust-lang/rust/pull/133636)
|
||||
|
||||
<a id="1.86.0-Compatibility-Notes"></a>
|
||||
|
||||
Compatibility Notes
|
||||
-------------------
|
||||
- [The `wasm_c_abi` future compatibility warning is now a hard error.](https://github.com/rust-lang/rust/pull/133951)
|
||||
Users of `wasm-bindgen` should upgrade to at least version 0.2.89, otherwise compilation will fail.
|
||||
- [Remove long-deprecated no-op attributes `#![no_start]` and `#![crate_id]`.](https://github.com/rust-lang/rust/pull/134300)
|
||||
- [The future incompatibility lint `cenum_impl_drop_cast` has been made into a hard error.](https://github.com/rust-lang/rust/pull/135964) This means it is now an error to cast a field-less enum to an integer if the enum implements `Drop`.
|
||||
- [SSE2 is now required for "i686" 32-bit x86 hard-float targets; disabling it causes a warning that will become a hard error eventually.](https://github.com/rust-lang/rust/pull/137037)
|
||||
To compile for pre-SSE2 32-bit x86, use a "i586" target instead.
|
||||
|
||||
<a id="1.86.0-Internal-Changes"></a>
|
||||
|
||||
Internal Changes
|
||||
----------------
|
||||
|
||||
These changes do not affect any public interfaces of Rust, but they represent
|
||||
significant improvements to the performance or internals of rustc and related
|
||||
tools.
|
||||
|
||||
- [Build the rustc on AArch64 Linux with ThinLTO + PGO.](https://github.com/rust-lang/rust/pull/133807)
|
||||
The ARM 64-bit compiler (AArch64) on Linux is now optimized with ThinLTO and PGO, similar to the optimizations we have already performed for the x86-64 compiler on Linux. This should make it up to 30% faster.
|
||||
|
||||
|
||||
Version 1.85.1 (2025-03-18)
|
||||
==========================
|
||||
|
||||
<a id="1.85.1"></a>
|
||||
|
||||
- [Fix the doctest-merging feature of the 2024 Edition.](https://github.com/rust-lang/rust/pull/137899/)
|
||||
- [Relax some `target_feature` checks when generating docs.](https://github.com/rust-lang/rust/pull/137632/)
|
||||
- [Fix errors in `std::fs::rename` on Windows 10, version 1607.](https://github.com/rust-lang/rust/pull/137528/)
|
||||
- [Downgrade bootstrap `cc` to fix custom targets.](https://github.com/rust-lang/rust/pull/137460/)
|
||||
- [Skip submodule updates when building Rust from a source tarball.](https://github.com/rust-lang/rust/pull/137338/)
|
||||
|
||||
Version 1.85.0 (2025-02-20)
|
||||
==========================
|
||||
|
||||
|
@ -1,7 +1,7 @@
|
||||
# Sample TOML configuration file for building Rust.
|
||||
#
|
||||
# To configure bootstrap, run `./configure` or `./x.py setup`.
|
||||
# See https://rustc-dev-guide.rust-lang.org/building/how-to-build-and-run.html#create-a-configtoml for more information.
|
||||
# See https://rustc-dev-guide.rust-lang.org/building/how-to-build-and-run.html#create-a-bootstraptoml for more information.
|
||||
#
|
||||
# All options are commented out by default in this file, and they're commented
|
||||
# out with their default values. The build system by default looks for
|
||||
@ -28,8 +28,9 @@
|
||||
# - A new option
|
||||
# - A change in the default values
|
||||
#
|
||||
# If `change-id` does not match the version that is currently running,
|
||||
# `x.py` will inform you about the changes made on bootstrap.
|
||||
# If the change-id does not match the version currently in use, x.py will
|
||||
# display the changes made to the bootstrap.
|
||||
# To suppress these warnings, you can set change-id = "ignore".
|
||||
#change-id = <latest change id in src/bootstrap/src/utils/change_tracker.rs>
|
||||
|
||||
# =============================================================================
|
||||
@ -446,7 +447,7 @@
|
||||
# a specific version.
|
||||
#ccache = false
|
||||
|
||||
# List of paths to exclude from the build and test processes.
|
||||
# List of paths to exclude from the build and test processes.
|
||||
# For example, exclude = ["tests/ui", "src/tools/tidy"].
|
||||
#exclude = []
|
||||
|
||||
|
@ -1462,7 +1462,8 @@ impl BackendRepr {
|
||||
!self.is_unsized()
|
||||
}
|
||||
|
||||
/// Returns `true` if this is a single signed integer scalar
|
||||
/// Returns `true` if this is a single signed integer scalar.
|
||||
/// Sanity check: panics if this is not a scalar type (see PR #70189).
|
||||
#[inline]
|
||||
pub fn is_signed(&self) -> bool {
|
||||
match self {
|
||||
|
@ -6,7 +6,6 @@ edition = "2024"
|
||||
[dependencies]
|
||||
# tidy-alphabetical-start
|
||||
bitflags = "2.4.1"
|
||||
literal-escaper = { path = "../../library/literal-escaper" }
|
||||
memchr = "2.7.4"
|
||||
rustc_ast_ir = { path = "../rustc_ast_ir" }
|
||||
rustc_data_structures = { path = "../rustc_data_structures" }
|
||||
|
@ -545,14 +545,6 @@ pub struct Block {
|
||||
pub rules: BlockCheckMode,
|
||||
pub span: Span,
|
||||
pub tokens: Option<LazyAttrTokenStream>,
|
||||
/// The following *isn't* a parse error, but will cause multiple errors in following stages.
|
||||
/// ```compile_fail
|
||||
/// let x = {
|
||||
/// foo: var
|
||||
/// };
|
||||
/// ```
|
||||
/// #34255
|
||||
pub could_be_bare_literal: bool,
|
||||
}
|
||||
|
||||
/// A match pattern.
|
||||
@ -1657,7 +1649,7 @@ pub enum ExprKind {
|
||||
Try(P<Expr>),
|
||||
|
||||
/// A `yield`, with an optional value to be yielded.
|
||||
Yield(Option<P<Expr>>),
|
||||
Yield(YieldKind),
|
||||
|
||||
/// A `do yeet` (aka `throw`/`fail`/`bail`/`raise`/whatever),
|
||||
/// with an optional value to be returned.
|
||||
@ -1903,6 +1895,44 @@ pub enum MatchKind {
|
||||
Postfix,
|
||||
}
|
||||
|
||||
/// The kind of yield expression
|
||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||
pub enum YieldKind {
|
||||
/// yield expr { ... }
|
||||
Prefix(Option<P<Expr>>),
|
||||
/// expr.yield { ... }
|
||||
Postfix(P<Expr>),
|
||||
}
|
||||
|
||||
impl YieldKind {
|
||||
/// Returns the expression inside the yield expression, if any.
|
||||
///
|
||||
/// For postfix yields, this is guaranteed to be `Some`.
|
||||
pub const fn expr(&self) -> Option<&P<Expr>> {
|
||||
match self {
|
||||
YieldKind::Prefix(expr) => expr.as_ref(),
|
||||
YieldKind::Postfix(expr) => Some(expr),
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a mutable reference to the expression being yielded, if any.
|
||||
pub const fn expr_mut(&mut self) -> Option<&mut P<Expr>> {
|
||||
match self {
|
||||
YieldKind::Prefix(expr) => expr.as_mut(),
|
||||
YieldKind::Postfix(expr) => Some(expr),
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns true if both yields are prefix or both are postfix.
|
||||
pub const fn same_kind(&self, other: &Self) -> bool {
|
||||
match (self, other) {
|
||||
(YieldKind::Prefix(_), YieldKind::Prefix(_)) => true,
|
||||
(YieldKind::Postfix(_), YieldKind::Postfix(_)) => true,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// A literal in a meta item.
|
||||
#[derive(Clone, Encodable, Decodable, Debug, HashStable_Generic)]
|
||||
pub struct MetaItemLit {
|
||||
@ -3273,9 +3303,6 @@ pub struct Item<K = ItemKind> {
|
||||
pub id: NodeId,
|
||||
pub span: Span,
|
||||
pub vis: Visibility,
|
||||
/// The name of the item.
|
||||
/// It might be a dummy name in case of anonymous items.
|
||||
pub ident: Ident,
|
||||
|
||||
pub kind: K,
|
||||
|
||||
@ -3297,23 +3324,23 @@ impl Item {
|
||||
|
||||
pub fn opt_generics(&self) -> Option<&Generics> {
|
||||
match &self.kind {
|
||||
ItemKind::ExternCrate(_)
|
||||
ItemKind::ExternCrate(..)
|
||||
| ItemKind::Use(_)
|
||||
| ItemKind::Mod(_, _)
|
||||
| ItemKind::Mod(..)
|
||||
| ItemKind::ForeignMod(_)
|
||||
| ItemKind::GlobalAsm(_)
|
||||
| ItemKind::MacCall(_)
|
||||
| ItemKind::Delegation(_)
|
||||
| ItemKind::DelegationMac(_)
|
||||
| ItemKind::MacroDef(_) => None,
|
||||
| ItemKind::MacroDef(..) => None,
|
||||
ItemKind::Static(_) => None,
|
||||
ItemKind::Const(i) => Some(&i.generics),
|
||||
ItemKind::Fn(i) => Some(&i.generics),
|
||||
ItemKind::TyAlias(i) => Some(&i.generics),
|
||||
ItemKind::TraitAlias(generics, _)
|
||||
| ItemKind::Enum(_, generics)
|
||||
| ItemKind::Struct(_, generics)
|
||||
| ItemKind::Union(_, generics) => Some(&generics),
|
||||
ItemKind::TraitAlias(_, generics, _)
|
||||
| ItemKind::Enum(_, _, generics)
|
||||
| ItemKind::Struct(_, _, generics)
|
||||
| ItemKind::Union(_, _, generics) => Some(&generics),
|
||||
ItemKind::Trait(i) => Some(&i.generics),
|
||||
ItemKind::Impl(i) => Some(&i.generics),
|
||||
}
|
||||
@ -3390,6 +3417,7 @@ impl Default for FnHeader {
|
||||
pub struct Trait {
|
||||
pub safety: Safety,
|
||||
pub is_auto: IsAuto,
|
||||
pub ident: Ident,
|
||||
pub generics: Generics,
|
||||
pub bounds: GenericBounds,
|
||||
pub items: ThinVec<P<AssocItem>>,
|
||||
@ -3435,6 +3463,7 @@ pub struct TyAliasWhereClauses {
|
||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||
pub struct TyAlias {
|
||||
pub defaultness: Defaultness,
|
||||
pub ident: Ident,
|
||||
pub generics: Generics,
|
||||
pub where_clauses: TyAliasWhereClauses,
|
||||
pub bounds: GenericBounds,
|
||||
@ -3463,6 +3492,7 @@ pub struct FnContract {
|
||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||
pub struct Fn {
|
||||
pub defaultness: Defaultness,
|
||||
pub ident: Ident,
|
||||
pub generics: Generics,
|
||||
pub sig: FnSig,
|
||||
pub contract: Option<P<FnContract>>,
|
||||
@ -3476,6 +3506,7 @@ pub struct Delegation {
|
||||
pub id: NodeId,
|
||||
pub qself: Option<P<QSelf>>,
|
||||
pub path: Path,
|
||||
pub ident: Ident,
|
||||
pub rename: Option<Ident>,
|
||||
pub body: Option<P<Block>>,
|
||||
/// The item was expanded from a glob delegation item.
|
||||
@ -3493,18 +3524,22 @@ pub struct DelegationMac {
|
||||
|
||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||
pub struct StaticItem {
|
||||
pub ident: Ident,
|
||||
pub ty: P<Ty>,
|
||||
pub safety: Safety,
|
||||
pub mutability: Mutability,
|
||||
pub expr: Option<P<Expr>>,
|
||||
pub define_opaque: Option<ThinVec<(NodeId, Path)>>,
|
||||
}
|
||||
|
||||
#[derive(Clone, Encodable, Decodable, Debug)]
|
||||
pub struct ConstItem {
|
||||
pub defaultness: Defaultness,
|
||||
pub ident: Ident,
|
||||
pub generics: Generics,
|
||||
pub ty: P<Ty>,
|
||||
pub expr: Option<P<Expr>>,
|
||||
pub define_opaque: Option<ThinVec<(NodeId, Path)>>,
|
||||
}
|
||||
|
||||
// Adding a new variant? Please update `test_item` in `tests/ui/macros/stringify.rs`.
|
||||
@ -3513,7 +3548,7 @@ pub enum ItemKind {
|
||||
/// An `extern crate` item, with the optional *original* crate name if the crate was renamed.
|
||||
///
|
||||
/// E.g., `extern crate foo` or `extern crate foo_bar as foo`.
|
||||
ExternCrate(Option<Symbol>),
|
||||
ExternCrate(Option<Symbol>, Ident),
|
||||
/// A use declaration item (`use`).
|
||||
///
|
||||
/// E.g., `use foo;`, `use foo::bar;` or `use foo::bar as FooBar;`.
|
||||
@ -3535,7 +3570,7 @@ pub enum ItemKind {
|
||||
/// E.g., `mod foo;` or `mod foo { .. }`.
|
||||
/// `unsafe` keyword on modules is accepted syntactically for macro DSLs, but not
|
||||
/// semantically by Rust.
|
||||
Mod(Safety, ModKind),
|
||||
Mod(Safety, Ident, ModKind),
|
||||
/// An external module (`extern`).
|
||||
///
|
||||
/// E.g., `extern {}` or `extern "C" {}`.
|
||||
@ -3549,15 +3584,15 @@ pub enum ItemKind {
|
||||
/// An enum definition (`enum`).
|
||||
///
|
||||
/// E.g., `enum Foo<A, B> { C<A>, D<B> }`.
|
||||
Enum(EnumDef, Generics),
|
||||
Enum(Ident, EnumDef, Generics),
|
||||
/// A struct definition (`struct`).
|
||||
///
|
||||
/// E.g., `struct Foo<A> { x: A }`.
|
||||
Struct(VariantData, Generics),
|
||||
Struct(Ident, VariantData, Generics),
|
||||
/// A union definition (`union`).
|
||||
///
|
||||
/// E.g., `union Foo<A, B> { x: A, y: B }`.
|
||||
Union(VariantData, Generics),
|
||||
Union(Ident, VariantData, Generics),
|
||||
/// A trait declaration (`trait`).
|
||||
///
|
||||
/// E.g., `trait Foo { .. }`, `trait Foo<T> { .. }` or `auto trait Foo {}`.
|
||||
@ -3565,7 +3600,7 @@ pub enum ItemKind {
|
||||
/// Trait alias.
|
||||
///
|
||||
/// E.g., `trait Foo = Bar + Quux;`.
|
||||
TraitAlias(Generics, GenericBounds),
|
||||
TraitAlias(Ident, Generics, GenericBounds),
|
||||
/// An implementation.
|
||||
///
|
||||
/// E.g., `impl<A> Foo<A> { .. }` or `impl<A> Trait for Foo<A> { .. }`.
|
||||
@ -3576,7 +3611,7 @@ pub enum ItemKind {
|
||||
MacCall(P<MacCall>),
|
||||
|
||||
/// A macro definition.
|
||||
MacroDef(MacroDef),
|
||||
MacroDef(Ident, MacroDef),
|
||||
|
||||
/// A single delegation item (`reuse`).
|
||||
///
|
||||
@ -3588,6 +3623,31 @@ pub enum ItemKind {
|
||||
}
|
||||
|
||||
impl ItemKind {
|
||||
pub fn ident(&self) -> Option<Ident> {
|
||||
match *self {
|
||||
ItemKind::ExternCrate(_, ident)
|
||||
| ItemKind::Static(box StaticItem { ident, .. })
|
||||
| ItemKind::Const(box ConstItem { ident, .. })
|
||||
| ItemKind::Fn(box Fn { ident, .. })
|
||||
| ItemKind::Mod(_, ident, _)
|
||||
| ItemKind::TyAlias(box TyAlias { ident, .. })
|
||||
| ItemKind::Enum(ident, ..)
|
||||
| ItemKind::Struct(ident, ..)
|
||||
| ItemKind::Union(ident, ..)
|
||||
| ItemKind::Trait(box Trait { ident, .. })
|
||||
| ItemKind::TraitAlias(ident, ..)
|
||||
| ItemKind::MacroDef(ident, _)
|
||||
| ItemKind::Delegation(box Delegation { ident, .. }) => Some(ident),
|
||||
|
||||
ItemKind::Use(_)
|
||||
| ItemKind::ForeignMod(_)
|
||||
| ItemKind::GlobalAsm(_)
|
||||
| ItemKind::Impl(_)
|
||||
| ItemKind::MacCall(_)
|
||||
| ItemKind::DelegationMac(_) => None,
|
||||
}
|
||||
}
|
||||
|
||||
/// "a" or "an"
|
||||
pub fn article(&self) -> &'static str {
|
||||
use ItemKind::*;
|
||||
@ -3628,11 +3688,11 @@ impl ItemKind {
|
||||
Self::Fn(box Fn { generics, .. })
|
||||
| Self::TyAlias(box TyAlias { generics, .. })
|
||||
| Self::Const(box ConstItem { generics, .. })
|
||||
| Self::Enum(_, generics)
|
||||
| Self::Struct(_, generics)
|
||||
| Self::Union(_, generics)
|
||||
| Self::Enum(_, _, generics)
|
||||
| Self::Struct(_, _, generics)
|
||||
| Self::Union(_, _, generics)
|
||||
| Self::Trait(box Trait { generics, .. })
|
||||
| Self::TraitAlias(generics, _)
|
||||
| Self::TraitAlias(_, generics, _)
|
||||
| Self::Impl(box Impl { generics, .. }) => Some(generics),
|
||||
_ => None,
|
||||
}
|
||||
@ -3668,6 +3728,17 @@ pub enum AssocItemKind {
|
||||
}
|
||||
|
||||
impl AssocItemKind {
|
||||
pub fn ident(&self) -> Option<Ident> {
|
||||
match *self {
|
||||
AssocItemKind::Const(box ConstItem { ident, .. })
|
||||
| AssocItemKind::Fn(box Fn { ident, .. })
|
||||
| AssocItemKind::Type(box TyAlias { ident, .. })
|
||||
| AssocItemKind::Delegation(box Delegation { ident, .. }) => Some(ident),
|
||||
|
||||
AssocItemKind::MacCall(_) | AssocItemKind::DelegationMac(_) => None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn defaultness(&self) -> Defaultness {
|
||||
match *self {
|
||||
Self::Const(box ConstItem { defaultness, .. })
|
||||
@ -3714,14 +3785,26 @@ impl TryFrom<ItemKind> for AssocItemKind {
|
||||
pub enum ForeignItemKind {
|
||||
/// A foreign static item (`static FOO: u8`).
|
||||
Static(Box<StaticItem>),
|
||||
/// An foreign function.
|
||||
/// A foreign function.
|
||||
Fn(Box<Fn>),
|
||||
/// An foreign type.
|
||||
/// A foreign type.
|
||||
TyAlias(Box<TyAlias>),
|
||||
/// A macro expanding to foreign items.
|
||||
MacCall(P<MacCall>),
|
||||
}
|
||||
|
||||
impl ForeignItemKind {
|
||||
pub fn ident(&self) -> Option<Ident> {
|
||||
match *self {
|
||||
ForeignItemKind::Static(box StaticItem { ident, .. })
|
||||
| ForeignItemKind::Fn(box Fn { ident, .. })
|
||||
| ForeignItemKind::TyAlias(box TyAlias { ident, .. }) => Some(ident),
|
||||
|
||||
ForeignItemKind::MacCall(_) => None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<ForeignItemKind> for ItemKind {
|
||||
fn from(foreign_item_kind: ForeignItemKind) -> ItemKind {
|
||||
match foreign_item_kind {
|
||||
@ -3758,21 +3841,21 @@ mod size_asserts {
|
||||
|
||||
use super::*;
|
||||
// tidy-alphabetical-start
|
||||
static_assert_size!(AssocItem, 88);
|
||||
static_assert_size!(AssocItem, 80);
|
||||
static_assert_size!(AssocItemKind, 16);
|
||||
static_assert_size!(Attribute, 32);
|
||||
static_assert_size!(Block, 32);
|
||||
static_assert_size!(Expr, 72);
|
||||
static_assert_size!(ExprKind, 40);
|
||||
static_assert_size!(Fn, 176);
|
||||
static_assert_size!(ForeignItem, 88);
|
||||
static_assert_size!(Fn, 184);
|
||||
static_assert_size!(ForeignItem, 80);
|
||||
static_assert_size!(ForeignItemKind, 16);
|
||||
static_assert_size!(GenericArg, 24);
|
||||
static_assert_size!(GenericBound, 88);
|
||||
static_assert_size!(Generics, 40);
|
||||
static_assert_size!(Impl, 136);
|
||||
static_assert_size!(Item, 136);
|
||||
static_assert_size!(ItemKind, 64);
|
||||
static_assert_size!(Item, 144);
|
||||
static_assert_size!(ItemKind, 80);
|
||||
static_assert_size!(LitKind, 24);
|
||||
static_assert_size!(Local, 80);
|
||||
static_assert_size!(MetaItemLit, 40);
|
||||
|
@ -209,13 +209,11 @@ impl HasTokens for Attribute {
|
||||
impl HasTokens for Nonterminal {
|
||||
fn tokens(&self) -> Option<&LazyAttrTokenStream> {
|
||||
match self {
|
||||
Nonterminal::NtExpr(expr) | Nonterminal::NtLiteral(expr) => expr.tokens(),
|
||||
Nonterminal::NtBlock(block) => block.tokens(),
|
||||
}
|
||||
}
|
||||
fn tokens_mut(&mut self) -> Option<&mut Option<LazyAttrTokenStream>> {
|
||||
match self {
|
||||
Nonterminal::NtExpr(expr) | Nonterminal::NtLiteral(expr) => expr.tokens_mut(),
|
||||
Nonterminal::NtBlock(block) => block.tokens_mut(),
|
||||
}
|
||||
}
|
||||
|
@ -41,7 +41,6 @@ pub trait WalkItemKind {
|
||||
&mut self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &mut Ident,
|
||||
visibility: &mut Visibility,
|
||||
ctxt: Self::Ctxt,
|
||||
visitor: &mut impl MutVisitor,
|
||||
@ -238,6 +237,10 @@ pub trait MutVisitor: Sized {
|
||||
walk_ident(self, i);
|
||||
}
|
||||
|
||||
fn visit_modifiers(&mut self, m: &mut TraitBoundModifiers) {
|
||||
walk_modifiers(self, m);
|
||||
}
|
||||
|
||||
fn visit_path(&mut self, p: &mut Path) {
|
||||
walk_path(self, p);
|
||||
}
|
||||
@ -896,8 +899,6 @@ pub fn visit_token<T: MutVisitor>(vis: &mut T, t: &mut Token) {
|
||||
fn visit_nonterminal<T: MutVisitor>(vis: &mut T, nt: &mut token::Nonterminal) {
|
||||
match nt {
|
||||
token::NtBlock(block) => vis.visit_block(block),
|
||||
token::NtExpr(expr) => vis.visit_expr(expr),
|
||||
token::NtLiteral(expr) => vis.visit_expr(expr),
|
||||
}
|
||||
}
|
||||
|
||||
@ -959,10 +960,10 @@ fn walk_fn<T: MutVisitor>(vis: &mut T, kind: FnKind<'_>) {
|
||||
match kind {
|
||||
FnKind::Fn(
|
||||
_ctxt,
|
||||
_ident,
|
||||
_vis,
|
||||
Fn {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
contract,
|
||||
body,
|
||||
@ -970,8 +971,9 @@ fn walk_fn<T: MutVisitor>(vis: &mut T, kind: FnKind<'_>) {
|
||||
define_opaque,
|
||||
},
|
||||
) => {
|
||||
// Identifier and visibility are visited as a part of the item.
|
||||
// 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);
|
||||
@ -983,10 +985,7 @@ fn walk_fn<T: MutVisitor>(vis: &mut T, kind: FnKind<'_>) {
|
||||
}
|
||||
vis.visit_span(span);
|
||||
|
||||
for (id, path) in define_opaque.iter_mut().flatten() {
|
||||
vis.visit_id(id);
|
||||
vis.visit_path(path)
|
||||
}
|
||||
walk_define_opaques(vis, define_opaque);
|
||||
}
|
||||
FnKind::Closure(binder, coroutine_kind, decl, body) => {
|
||||
vis.visit_closure_binder(binder);
|
||||
@ -1156,12 +1155,29 @@ fn walk_trait_ref<T: MutVisitor>(vis: &mut T, TraitRef { path, ref_id }: &mut Tr
|
||||
}
|
||||
|
||||
fn walk_poly_trait_ref<T: MutVisitor>(vis: &mut T, p: &mut PolyTraitRef) {
|
||||
let PolyTraitRef { bound_generic_params, modifiers: _, trait_ref, span } = p;
|
||||
let PolyTraitRef { bound_generic_params, modifiers, trait_ref, span } = p;
|
||||
vis.visit_modifiers(modifiers);
|
||||
bound_generic_params.flat_map_in_place(|param| vis.flat_map_generic_param(param));
|
||||
vis.visit_trait_ref(trait_ref);
|
||||
vis.visit_span(span);
|
||||
}
|
||||
|
||||
fn walk_modifiers<V: MutVisitor>(vis: &mut V, m: &mut TraitBoundModifiers) {
|
||||
let TraitBoundModifiers { constness, asyncness, polarity } = m;
|
||||
match constness {
|
||||
BoundConstness::Never => {}
|
||||
BoundConstness::Always(span) | BoundConstness::Maybe(span) => vis.visit_span(span),
|
||||
}
|
||||
match asyncness {
|
||||
BoundAsyncness::Normal => {}
|
||||
BoundAsyncness::Async(span) => vis.visit_span(span),
|
||||
}
|
||||
match polarity {
|
||||
BoundPolarity::Positive => {}
|
||||
BoundPolarity::Negative(span) | BoundPolarity::Maybe(span) => vis.visit_span(span),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_field_def<T: MutVisitor>(visitor: &mut T, fd: &mut FieldDef) {
|
||||
let FieldDef { span, ident, vis, id, ty, attrs, is_placeholder: _, safety, default } = fd;
|
||||
visitor.visit_id(id);
|
||||
@ -1204,7 +1220,7 @@ fn walk_mt<T: MutVisitor>(vis: &mut T, MutTy { ty, mutbl: _ }: &mut MutTy) {
|
||||
}
|
||||
|
||||
pub fn walk_block<T: MutVisitor>(vis: &mut T, block: &mut P<Block>) {
|
||||
let Block { id, stmts, rules: _, span, tokens, could_be_bare_literal: _ } = block.deref_mut();
|
||||
let Block { id, stmts, rules: _, span, tokens } = block.deref_mut();
|
||||
vis.visit_id(id);
|
||||
stmts.flat_map_in_place(|stmt| vis.flat_map_stmt(stmt));
|
||||
visit_lazy_tts(vis, tokens);
|
||||
@ -1215,12 +1231,11 @@ pub fn walk_item_kind<K: WalkItemKind>(
|
||||
kind: &mut K,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &mut Ident,
|
||||
visibility: &mut Visibility,
|
||||
ctxt: K::Ctxt,
|
||||
vis: &mut impl MutVisitor,
|
||||
) {
|
||||
kind.walk(span, id, ident, visibility, ctxt, vis)
|
||||
kind.walk(span, id, visibility, ctxt, vis)
|
||||
}
|
||||
|
||||
impl WalkItemKind for ItemKind {
|
||||
@ -1229,26 +1244,35 @@ impl WalkItemKind for ItemKind {
|
||||
&mut self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &mut Ident,
|
||||
visibility: &mut Visibility,
|
||||
_ctxt: Self::Ctxt,
|
||||
vis: &mut impl MutVisitor,
|
||||
) {
|
||||
match self {
|
||||
ItemKind::ExternCrate(_orig_name) => {}
|
||||
ItemKind::ExternCrate(_orig_name, ident) => vis.visit_ident(ident),
|
||||
ItemKind::Use(use_tree) => vis.visit_use_tree(use_tree),
|
||||
ItemKind::Static(box StaticItem { ty, safety: _, mutability: _, expr }) => {
|
||||
ItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
safety: _,
|
||||
mutability: _,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_ty(ty);
|
||||
visit_opt(expr, |expr| vis.visit_expr(expr));
|
||||
walk_define_opaques(vis, define_opaque);
|
||||
}
|
||||
ItemKind::Const(item) => {
|
||||
visit_const_item(item, vis);
|
||||
walk_const_item(vis, item);
|
||||
}
|
||||
ItemKind::Fn(func) => {
|
||||
vis.visit_fn(FnKind::Fn(FnCtxt::Free, ident, visibility, &mut *func), span, id);
|
||||
vis.visit_fn(FnKind::Fn(FnCtxt::Free, visibility, &mut *func), span, id);
|
||||
}
|
||||
ItemKind::Mod(safety, mod_kind) => {
|
||||
ItemKind::Mod(safety, ident, mod_kind) => {
|
||||
visit_safety(vis, safety);
|
||||
vis.visit_ident(ident);
|
||||
match mod_kind {
|
||||
ModKind::Loaded(
|
||||
items,
|
||||
@ -1265,18 +1289,29 @@ impl WalkItemKind for ItemKind {
|
||||
}
|
||||
ItemKind::ForeignMod(nm) => vis.visit_foreign_mod(nm),
|
||||
ItemKind::GlobalAsm(asm) => vis.visit_inline_asm(asm),
|
||||
ItemKind::TyAlias(box TyAlias { defaultness, generics, where_clauses, bounds, ty }) => {
|
||||
ItemKind::TyAlias(box TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
visit_defaultness(vis, defaultness);
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
visit_bounds(vis, bounds, BoundKind::Bound);
|
||||
visit_opt(ty, |ty| vis.visit_ty(ty));
|
||||
walk_ty_alias_where_clauses(vis, where_clauses);
|
||||
}
|
||||
ItemKind::Enum(EnumDef { variants }, generics) => {
|
||||
ItemKind::Enum(ident, EnumDef { variants }, generics) => {
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
variants.flat_map_in_place(|variant| vis.flat_map_variant(variant));
|
||||
}
|
||||
ItemKind::Struct(variant_data, generics) | ItemKind::Union(variant_data, generics) => {
|
||||
ItemKind::Struct(ident, variant_data, generics)
|
||||
| ItemKind::Union(ident, variant_data, generics) => {
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
vis.visit_variant_data(variant_data);
|
||||
}
|
||||
@ -1297,24 +1332,32 @@ impl WalkItemKind for ItemKind {
|
||||
visit_polarity(vis, polarity);
|
||||
visit_opt(of_trait, |trait_ref| vis.visit_trait_ref(trait_ref));
|
||||
vis.visit_ty(self_ty);
|
||||
items.flat_map_in_place(|item| vis.flat_map_assoc_item(item, AssocCtxt::Impl));
|
||||
items.flat_map_in_place(|item| {
|
||||
vis.flat_map_assoc_item(item, AssocCtxt::Impl { of_trait: of_trait.is_some() })
|
||||
});
|
||||
}
|
||||
ItemKind::Trait(box Trait { safety, is_auto: _, generics, bounds, items }) => {
|
||||
ItemKind::Trait(box Trait { safety, is_auto: _, ident, generics, bounds, items }) => {
|
||||
visit_safety(vis, safety);
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
visit_bounds(vis, bounds, BoundKind::Bound);
|
||||
items.flat_map_in_place(|item| vis.flat_map_assoc_item(item, AssocCtxt::Trait));
|
||||
}
|
||||
ItemKind::TraitAlias(generics, bounds) => {
|
||||
ItemKind::TraitAlias(ident, generics, bounds) => {
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
visit_bounds(vis, bounds, BoundKind::Bound);
|
||||
}
|
||||
ItemKind::MacCall(m) => vis.visit_mac_call(m),
|
||||
ItemKind::MacroDef(def) => vis.visit_macro_def(def),
|
||||
ItemKind::MacroDef(ident, def) => {
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_macro_def(def)
|
||||
}
|
||||
ItemKind::Delegation(box Delegation {
|
||||
id,
|
||||
qself,
|
||||
path,
|
||||
ident,
|
||||
rename,
|
||||
body,
|
||||
from_glob: _,
|
||||
@ -1322,6 +1365,7 @@ impl WalkItemKind for ItemKind {
|
||||
vis.visit_id(id);
|
||||
vis.visit_qself(qself);
|
||||
vis.visit_path(path);
|
||||
vis.visit_ident(ident);
|
||||
if let Some(rename) = rename {
|
||||
vis.visit_ident(rename);
|
||||
}
|
||||
@ -1354,30 +1398,27 @@ impl WalkItemKind for AssocItemKind {
|
||||
&mut self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &mut Ident,
|
||||
visibility: &mut Visibility,
|
||||
ctxt: Self::Ctxt,
|
||||
visitor: &mut impl MutVisitor,
|
||||
) {
|
||||
match self {
|
||||
AssocItemKind::Const(item) => {
|
||||
visit_const_item(item, visitor);
|
||||
walk_const_item(visitor, item);
|
||||
}
|
||||
AssocItemKind::Fn(func) => {
|
||||
visitor.visit_fn(
|
||||
FnKind::Fn(FnCtxt::Assoc(ctxt), ident, visibility, &mut *func),
|
||||
span,
|
||||
id,
|
||||
);
|
||||
visitor.visit_fn(FnKind::Fn(FnCtxt::Assoc(ctxt), visibility, &mut *func), span, id);
|
||||
}
|
||||
AssocItemKind::Type(box TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
visit_defaultness(visitor, defaultness);
|
||||
visitor.visit_ident(ident);
|
||||
visitor.visit_generics(generics);
|
||||
visit_bounds(visitor, bounds, BoundKind::Bound);
|
||||
visit_opt(ty, |ty| visitor.visit_ty(ty));
|
||||
@ -1388,6 +1429,7 @@ impl WalkItemKind for AssocItemKind {
|
||||
id,
|
||||
qself,
|
||||
path,
|
||||
ident,
|
||||
rename,
|
||||
body,
|
||||
from_glob: _,
|
||||
@ -1395,6 +1437,7 @@ impl WalkItemKind for AssocItemKind {
|
||||
visitor.visit_id(id);
|
||||
visitor.visit_qself(qself);
|
||||
visitor.visit_path(path);
|
||||
visitor.visit_ident(ident);
|
||||
if let Some(rename) = rename {
|
||||
visitor.visit_ident(rename);
|
||||
}
|
||||
@ -1421,14 +1464,14 @@ impl WalkItemKind for AssocItemKind {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_const_item<T: MutVisitor>(
|
||||
ConstItem { defaultness, generics, ty, expr }: &mut ConstItem,
|
||||
visitor: &mut T,
|
||||
) {
|
||||
visit_defaultness(visitor, defaultness);
|
||||
visitor.visit_generics(generics);
|
||||
visitor.visit_ty(ty);
|
||||
visit_opt(expr, |expr| visitor.visit_expr(expr));
|
||||
fn walk_const_item<T: MutVisitor>(vis: &mut T, item: &mut ConstItem) {
|
||||
let ConstItem { defaultness, ident, generics, ty, expr, define_opaque } = item;
|
||||
visit_defaultness(vis, defaultness);
|
||||
vis.visit_ident(ident);
|
||||
vis.visit_generics(generics);
|
||||
vis.visit_ty(ty);
|
||||
visit_opt(expr, |expr| vis.visit_expr(expr));
|
||||
walk_define_opaques(vis, define_opaque);
|
||||
}
|
||||
|
||||
fn walk_fn_header<T: MutVisitor>(vis: &mut T, header: &mut FnHeader) {
|
||||
@ -1461,12 +1504,11 @@ fn walk_item_ctxt<K: WalkItemKind>(
|
||||
item: &mut P<Item<K>>,
|
||||
ctxt: K::Ctxt,
|
||||
) {
|
||||
let Item { ident, attrs, id, kind, vis, span, tokens } = item.deref_mut();
|
||||
let Item { attrs, id, kind, vis, span, tokens } = item.deref_mut();
|
||||
visitor.visit_id(id);
|
||||
visit_attrs(visitor, attrs);
|
||||
visitor.visit_vis(vis);
|
||||
visitor.visit_ident(ident);
|
||||
kind.walk(*span, *id, ident, vis, ctxt, visitor);
|
||||
kind.walk(*span, *id, vis, ctxt, visitor);
|
||||
visit_lazy_tts(visitor, tokens);
|
||||
visitor.visit_span(span);
|
||||
}
|
||||
@ -1499,31 +1541,37 @@ impl WalkItemKind for ForeignItemKind {
|
||||
&mut self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &mut Ident,
|
||||
visibility: &mut Visibility,
|
||||
_ctxt: Self::Ctxt,
|
||||
visitor: &mut impl MutVisitor,
|
||||
) {
|
||||
match self {
|
||||
ForeignItemKind::Static(box StaticItem { ty, mutability: _, expr, safety: _ }) => {
|
||||
ForeignItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
mutability: _,
|
||||
expr,
|
||||
safety: _,
|
||||
define_opaque,
|
||||
}) => {
|
||||
visitor.visit_ident(ident);
|
||||
visitor.visit_ty(ty);
|
||||
visit_opt(expr, |expr| visitor.visit_expr(expr));
|
||||
walk_define_opaques(visitor, define_opaque);
|
||||
}
|
||||
ForeignItemKind::Fn(func) => {
|
||||
visitor.visit_fn(
|
||||
FnKind::Fn(FnCtxt::Foreign, ident, visibility, &mut *func),
|
||||
span,
|
||||
id,
|
||||
);
|
||||
visitor.visit_fn(FnKind::Fn(FnCtxt::Foreign, visibility, &mut *func), span, id);
|
||||
}
|
||||
ForeignItemKind::TyAlias(box TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
visit_defaultness(visitor, defaultness);
|
||||
visitor.visit_ident(ident);
|
||||
visitor.visit_generics(generics);
|
||||
visit_bounds(visitor, bounds, BoundKind::Bound);
|
||||
visit_opt(ty, |ty| visitor.visit_ty(ty));
|
||||
@ -1813,8 +1861,11 @@ pub fn walk_expr<T: MutVisitor>(vis: &mut T, Expr { kind, id, span, attrs, token
|
||||
ExprKind::Paren(expr) => {
|
||||
vis.visit_expr(expr);
|
||||
}
|
||||
ExprKind::Yield(expr) => {
|
||||
visit_opt(expr, |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),
|
||||
@ -1905,6 +1956,18 @@ fn walk_capture_by<T: MutVisitor>(vis: &mut T, capture_by: &mut CaptureBy) {
|
||||
}
|
||||
}
|
||||
|
||||
fn walk_define_opaques<T: MutVisitor>(
|
||||
vis: &mut T,
|
||||
define_opaque: &mut Option<ThinVec<(NodeId, Path)>>,
|
||||
) {
|
||||
if let Some(define_opaque) = define_opaque {
|
||||
for (id, path) in define_opaque {
|
||||
vis.visit_id(id);
|
||||
vis.visit_path(path)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Some value for the AST node that is valid but possibly meaningless. Similar
|
||||
/// to `Default` but not intended for wide use. The value will never be used
|
||||
/// meaningfully, it exists just to support unwinding in `visit_clobber` in the
|
||||
@ -1936,8 +1999,7 @@ impl DummyAstNode for Item {
|
||||
span: Default::default(),
|
||||
tokens: Default::default(),
|
||||
},
|
||||
ident: Ident::dummy(),
|
||||
kind: ItemKind::ExternCrate(None),
|
||||
kind: ItemKind::ExternCrate(None, Ident::dummy()),
|
||||
tokens: Default::default(),
|
||||
}
|
||||
}
|
||||
@ -2004,7 +2066,7 @@ impl<N: DummyAstNode, T: DummyAstNode> DummyAstNode for crate::ast_traits::AstNo
|
||||
#[derive(Debug)]
|
||||
pub enum FnKind<'a> {
|
||||
/// E.g., `fn foo()`, `fn foo(&self)`, or `extern "Abi" fn foo()`.
|
||||
Fn(FnCtxt, &'a mut Ident, &'a mut Visibility, &'a mut Fn),
|
||||
Fn(FnCtxt, &'a mut Visibility, &'a mut Fn),
|
||||
|
||||
/// E.g., `|x, y| body`.
|
||||
Closure(
|
||||
|
@ -198,16 +198,17 @@ impl Lit {
|
||||
}
|
||||
}
|
||||
|
||||
/// Keep this in sync with `Token::can_begin_literal_maybe_minus` excluding unary negation.
|
||||
/// Keep this in sync with `Token::can_begin_literal_maybe_minus` and
|
||||
/// `Parser::eat_token_lit` (excluding unary negation).
|
||||
pub fn from_token(token: &Token) -> Option<Lit> {
|
||||
match token.uninterpolate().kind {
|
||||
Ident(name, IdentIsRaw::No) if name.is_bool_lit() => Some(Lit::new(Bool, name, None)),
|
||||
Literal(token_lit) => Some(token_lit),
|
||||
Interpolated(ref nt)
|
||||
if let NtExpr(expr) | NtLiteral(expr) = &**nt
|
||||
&& let ast::ExprKind::Lit(token_lit) = expr.kind =>
|
||||
{
|
||||
Some(token_lit)
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(
|
||||
MetaVarKind::Literal | MetaVarKind::Expr { .. },
|
||||
))) => {
|
||||
// Unreachable with the current test suite.
|
||||
panic!("from_token metavar");
|
||||
}
|
||||
_ => None,
|
||||
}
|
||||
@ -447,8 +448,9 @@ pub enum TokenKind {
|
||||
|
||||
/// Identifier token.
|
||||
/// Do not forget about `NtIdent` when you want to match on identifiers.
|
||||
/// It's recommended to use `Token::(ident,uninterpolate,uninterpolated_span)` to
|
||||
/// treat regular and interpolated identifiers in the same way.
|
||||
/// It's recommended to use `Token::{ident,uninterpolate}` and
|
||||
/// `Parser::token_uninterpolated_span` to treat regular and interpolated
|
||||
/// identifiers in the same way.
|
||||
Ident(Symbol, IdentIsRaw),
|
||||
/// This identifier (and its span) is the identifier passed to the
|
||||
/// declarative macro. The span in the surrounding `Token` is the span of
|
||||
@ -457,8 +459,9 @@ pub enum TokenKind {
|
||||
|
||||
/// Lifetime identifier token.
|
||||
/// Do not forget about `NtLifetime` when you want to match on lifetime identifiers.
|
||||
/// It's recommended to use `Token::(lifetime,uninterpolate,uninterpolated_span)` to
|
||||
/// treat regular and interpolated lifetime identifiers in the same way.
|
||||
/// It's recommended to use `Token::{ident,uninterpolate}` and
|
||||
/// `Parser::token_uninterpolated_span` to treat regular and interpolated
|
||||
/// identifiers in the same way.
|
||||
Lifetime(Symbol, IdentIsRaw),
|
||||
/// This identifier (and its span) is the lifetime passed to the
|
||||
/// declarative macro. The span in the surrounding `Token` is the span of
|
||||
@ -584,20 +587,6 @@ impl Token {
|
||||
Token::new(Ident(ident.name, ident.is_raw_guess().into()), ident.span)
|
||||
}
|
||||
|
||||
/// For interpolated tokens, returns a span of the fragment to which the interpolated
|
||||
/// token refers. For all other tokens this is just a regular span.
|
||||
/// It is particularly important to use this for identifiers and lifetimes
|
||||
/// for which spans affect name resolution and edition checks.
|
||||
/// Note that keywords are also identifiers, so they should use this
|
||||
/// if they keep spans or perform edition checks.
|
||||
pub fn uninterpolated_span(&self) -> Span {
|
||||
match self.kind {
|
||||
NtIdent(ident, _) | NtLifetime(ident, _) => ident.span,
|
||||
Interpolated(ref nt) => nt.use_span(),
|
||||
_ => self.span,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_range_separator(&self) -> bool {
|
||||
[DotDot, DotDotDot, DotDotEq].contains(&self.kind)
|
||||
}
|
||||
@ -642,12 +631,7 @@ impl Token {
|
||||
PathSep | // global path
|
||||
Lifetime(..) | // labeled loop
|
||||
Pound => true, // expression attributes
|
||||
Interpolated(ref nt) =>
|
||||
matches!(&**nt,
|
||||
NtBlock(..) |
|
||||
NtExpr(..) |
|
||||
NtLiteral(..)
|
||||
),
|
||||
Interpolated(ref nt) => matches!(&**nt, NtBlock(..)),
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(
|
||||
MetaVarKind::Block |
|
||||
MetaVarKind::Expr { .. } |
|
||||
@ -677,11 +661,6 @@ impl Token {
|
||||
Lt | // path (UFCS constant)
|
||||
Shl => true, // path (double UFCS)
|
||||
Or => matches!(pat_kind, PatWithOr), // leading vert `|` or-pattern
|
||||
Interpolated(nt) =>
|
||||
matches!(&**nt,
|
||||
| NtExpr(..)
|
||||
| NtLiteral(..)
|
||||
),
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(
|
||||
MetaVarKind::Expr { .. } |
|
||||
MetaVarKind::Literal |
|
||||
@ -724,7 +703,7 @@ impl Token {
|
||||
match self.kind {
|
||||
OpenDelim(Delimiter::Brace) | Literal(..) | Minus => true,
|
||||
Ident(name, IdentIsRaw::No) if name.is_bool_lit() => true,
|
||||
Interpolated(ref nt) => matches!(&**nt, NtExpr(..) | NtBlock(..) | NtLiteral(..)),
|
||||
Interpolated(ref nt) => matches!(&**nt, NtBlock(..)),
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(
|
||||
MetaVarKind::Expr { .. } | MetaVarKind::Block | MetaVarKind::Literal,
|
||||
))) => true,
|
||||
@ -768,22 +747,12 @@ impl Token {
|
||||
///
|
||||
/// In other words, would this token be a valid start of `parse_literal_maybe_minus`?
|
||||
///
|
||||
/// Keep this in sync with and `Lit::from_token`, excluding unary negation.
|
||||
/// Keep this in sync with `Lit::from_token` and `Parser::eat_token_lit`
|
||||
/// (excluding unary negation).
|
||||
pub fn can_begin_literal_maybe_minus(&self) -> bool {
|
||||
match self.uninterpolate().kind {
|
||||
Literal(..) | Minus => true,
|
||||
Ident(name, IdentIsRaw::No) if name.is_bool_lit() => true,
|
||||
Interpolated(ref nt) => match &**nt {
|
||||
NtLiteral(_) => true,
|
||||
NtExpr(e) => match &e.kind {
|
||||
ast::ExprKind::Lit(_) => true,
|
||||
ast::ExprKind::Unary(ast::UnOp::Neg, e) => {
|
||||
matches!(&e.kind, ast::ExprKind::Lit(_))
|
||||
}
|
||||
_ => false,
|
||||
},
|
||||
_ => false,
|
||||
},
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(mv_kind))) => match mv_kind {
|
||||
MetaVarKind::Literal => true,
|
||||
MetaVarKind::Expr { can_begin_literal_maybe_minus, .. } => {
|
||||
@ -798,14 +767,6 @@ impl Token {
|
||||
pub fn can_begin_string_literal(&self) -> bool {
|
||||
match self.uninterpolate().kind {
|
||||
Literal(..) => true,
|
||||
Interpolated(ref nt) => match &**nt {
|
||||
NtLiteral(_) => true,
|
||||
NtExpr(e) => match &e.kind {
|
||||
ast::ExprKind::Lit(_) => true,
|
||||
_ => false,
|
||||
},
|
||||
_ => false,
|
||||
},
|
||||
OpenDelim(Delimiter::Invisible(InvisibleOrigin::MetaVar(mv_kind))) => match mv_kind {
|
||||
MetaVarKind::Literal => true,
|
||||
MetaVarKind::Expr { can_begin_string_literal, .. } => can_begin_string_literal,
|
||||
@ -869,12 +830,17 @@ impl Token {
|
||||
|
||||
/// Is this a pre-parsed expression dropped into the token stream
|
||||
/// (which happens while parsing the result of macro expansion)?
|
||||
pub fn is_whole_expr(&self) -> bool {
|
||||
pub fn is_metavar_expr(&self) -> bool {
|
||||
#[allow(irrefutable_let_patterns)] // FIXME: temporary
|
||||
if let Interpolated(nt) = &self.kind
|
||||
&& let NtExpr(_) | NtLiteral(_) | NtBlock(_) = &**nt
|
||||
&& let NtBlock(_) = &**nt
|
||||
{
|
||||
true
|
||||
} else if matches!(
|
||||
self.is_metavar_seq(),
|
||||
Some(MetaVarKind::Expr { .. } | MetaVarKind::Literal | MetaVarKind::Path)
|
||||
) {
|
||||
true
|
||||
} else {
|
||||
matches!(self.is_metavar_seq(), Some(MetaVarKind::Path))
|
||||
}
|
||||
@ -882,6 +848,7 @@ impl Token {
|
||||
|
||||
/// Is the token an interpolated block (`$b:block`)?
|
||||
pub fn is_whole_block(&self) -> bool {
|
||||
#[allow(irrefutable_let_patterns)] // FIXME: temporary
|
||||
if let Interpolated(nt) = &self.kind
|
||||
&& let NtBlock(..) = &**nt
|
||||
{
|
||||
@ -928,11 +895,6 @@ impl Token {
|
||||
self.is_non_raw_ident_where(Ident::is_path_segment_keyword)
|
||||
}
|
||||
|
||||
/// Don't use this unless you're doing something very loose and heuristic-y.
|
||||
pub fn is_any_keyword(&self) -> bool {
|
||||
self.is_non_raw_ident_where(Ident::is_any_keyword)
|
||||
}
|
||||
|
||||
/// Returns true for reserved identifiers used internally for elided lifetimes,
|
||||
/// unnamed method parameters, crate root module, error recovery etc.
|
||||
pub fn is_special_ident(&self) -> bool {
|
||||
@ -1105,8 +1067,6 @@ pub enum NtExprKind {
|
||||
/// For interpolation during macro expansion.
|
||||
pub enum Nonterminal {
|
||||
NtBlock(P<ast::Block>),
|
||||
NtExpr(P<ast::Expr>),
|
||||
NtLiteral(P<ast::Expr>),
|
||||
}
|
||||
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq, Encodable, Decodable, Hash, HashStable_Generic)]
|
||||
@ -1196,15 +1156,12 @@ impl Nonterminal {
|
||||
pub fn use_span(&self) -> Span {
|
||||
match self {
|
||||
NtBlock(block) => block.span,
|
||||
NtExpr(expr) | NtLiteral(expr) => expr.span,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn descr(&self) -> &'static str {
|
||||
match self {
|
||||
NtBlock(..) => "block",
|
||||
NtExpr(..) => "expression",
|
||||
NtLiteral(..) => "literal",
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1223,8 +1180,6 @@ impl fmt::Debug for Nonterminal {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
match *self {
|
||||
NtBlock(..) => f.pad("NtBlock(..)"),
|
||||
NtExpr(..) => f.pad("NtExpr(..)"),
|
||||
NtLiteral(..) => f.pad("NtLiteral(..)"),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1247,7 +1202,7 @@ mod size_asserts {
|
||||
// tidy-alphabetical-start
|
||||
static_assert_size!(Lit, 12);
|
||||
static_assert_size!(LitKind, 2);
|
||||
static_assert_size!(Nonterminal, 16);
|
||||
static_assert_size!(Nonterminal, 8);
|
||||
static_assert_size!(Token, 24);
|
||||
static_assert_size!(TokenKind, 16);
|
||||
// tidy-alphabetical-end
|
||||
|
@ -233,35 +233,52 @@ fn attrs_and_tokens_to_token_trees(
|
||||
|
||||
// Insert inner attribute tokens.
|
||||
if !inner_attrs.is_empty() {
|
||||
let mut found = false;
|
||||
// Check the last two trees (to account for a trailing semi)
|
||||
for tree in res.iter_mut().rev().take(2) {
|
||||
if let TokenTree::Delimited(span, spacing, delim, delim_tokens) = tree {
|
||||
// Inner attributes are only supported on extern blocks, functions,
|
||||
// impls, and modules. All of these have their inner attributes
|
||||
// placed at the beginning of the rightmost outermost braced group:
|
||||
// e.g. fn foo() { #![my_attr] }
|
||||
//
|
||||
// Therefore, we can insert them back into the right location
|
||||
// without needing to do any extra position tracking.
|
||||
//
|
||||
// Note: Outline modules are an exception - they can
|
||||
// have attributes like `#![my_attr]` at the start of a file.
|
||||
// Support for custom attributes in this position is not
|
||||
// properly implemented - we always synthesize fake tokens,
|
||||
// so we never reach this code.
|
||||
let found = insert_inner_attrs(inner_attrs, res);
|
||||
assert!(found, "Failed to find trailing delimited group in: {res:?}");
|
||||
}
|
||||
|
||||
// Inner attributes are only supported on blocks, functions, impls, and
|
||||
// modules. All of these have their inner attributes placed at the
|
||||
// beginning of the rightmost outermost braced group:
|
||||
// e.g. `fn foo() { #![my_attr] }`. (Note: the braces may be within
|
||||
// invisible delimiters.)
|
||||
//
|
||||
// Therefore, we can insert them back into the right location without
|
||||
// needing to do any extra position tracking.
|
||||
//
|
||||
// Note: Outline modules are an exception - they can have attributes like
|
||||
// `#![my_attr]` at the start of a file. Support for custom attributes in
|
||||
// this position is not properly implemented - we always synthesize fake
|
||||
// tokens, so we never reach this code.
|
||||
fn insert_inner_attrs(inner_attrs: &[Attribute], tts: &mut Vec<TokenTree>) -> bool {
|
||||
for tree in tts.iter_mut().rev() {
|
||||
if let TokenTree::Delimited(span, spacing, Delimiter::Brace, stream) = tree {
|
||||
// Found it: the rightmost, outermost braced group.
|
||||
let mut tts = vec![];
|
||||
for inner_attr in inner_attrs {
|
||||
tts.extend(inner_attr.token_trees());
|
||||
}
|
||||
tts.extend(delim_tokens.0.iter().cloned());
|
||||
tts.extend(stream.0.iter().cloned());
|
||||
let stream = TokenStream::new(tts);
|
||||
*tree = TokenTree::Delimited(*span, *spacing, *delim, stream);
|
||||
found = true;
|
||||
break;
|
||||
*tree = TokenTree::Delimited(*span, *spacing, Delimiter::Brace, stream);
|
||||
return true;
|
||||
} else if let TokenTree::Delimited(span, spacing, Delimiter::Invisible(src), stream) =
|
||||
tree
|
||||
{
|
||||
// Recurse inside invisible delimiters.
|
||||
let mut vec: Vec<_> = stream.iter().cloned().collect();
|
||||
if insert_inner_attrs(inner_attrs, &mut vec) {
|
||||
*tree = TokenTree::Delimited(
|
||||
*span,
|
||||
*spacing,
|
||||
Delimiter::Invisible(*src),
|
||||
TokenStream::new(vec),
|
||||
);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
assert!(found, "Failed to find trailing delimited group in: {res:?}");
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
@ -462,7 +479,6 @@ impl TokenStream {
|
||||
pub fn from_nonterminal_ast(nt: &Nonterminal) -> TokenStream {
|
||||
match nt {
|
||||
Nonterminal::NtBlock(block) => TokenStream::from_ast(block),
|
||||
Nonterminal::NtExpr(expr) | Nonterminal::NtLiteral(expr) => TokenStream::from_ast(expr),
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -182,11 +182,14 @@ pub fn expr_trailing_brace(mut expr: &ast::Expr) -> Option<TrailingBrace<'_>> {
|
||||
| Range(_, Some(e), _)
|
||||
| Ret(Some(e))
|
||||
| Unary(_, e)
|
||||
| Yield(Some(e))
|
||||
| Yeet(Some(e))
|
||||
| Become(e) => {
|
||||
expr = e;
|
||||
}
|
||||
Yield(kind) => match kind.expr() {
|
||||
Some(e) => expr = e,
|
||||
None => break None,
|
||||
},
|
||||
Closure(closure) => {
|
||||
expr = &closure.body;
|
||||
}
|
||||
@ -217,7 +220,6 @@ pub fn expr_trailing_brace(mut expr: &ast::Expr) -> Option<TrailingBrace<'_>> {
|
||||
Break(_, None)
|
||||
| Range(_, None, _)
|
||||
| Ret(None)
|
||||
| Yield(None)
|
||||
| Array(_)
|
||||
| Call(_, _)
|
||||
| MethodCall(_)
|
||||
@ -237,7 +239,9 @@ pub fn expr_trailing_brace(mut expr: &ast::Expr) -> Option<TrailingBrace<'_>> {
|
||||
| Yeet(None)
|
||||
| UnsafeBinderCast(..)
|
||||
| Err(_)
|
||||
| Dummy => break None,
|
||||
| Dummy => {
|
||||
break None;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,7 +2,7 @@
|
||||
|
||||
use std::{ascii, fmt, str};
|
||||
|
||||
use literal_escaper::{
|
||||
use rustc_lexer::unescape::{
|
||||
MixedUnit, Mode, byte_from_char, unescape_byte, unescape_char, unescape_mixed, unescape_unicode,
|
||||
};
|
||||
use rustc_span::{Span, Symbol, kw, sym};
|
||||
|
@ -16,6 +16,7 @@
|
||||
pub use rustc_ast_ir::visit::VisitorResult;
|
||||
pub use rustc_ast_ir::{try_visit, visit_opt, walk_list, walk_visitable_list};
|
||||
use rustc_span::{Ident, Span};
|
||||
use thin_vec::ThinVec;
|
||||
|
||||
use crate::ast::*;
|
||||
use crate::ptr::P;
|
||||
@ -23,7 +24,7 @@ use crate::ptr::P;
|
||||
#[derive(Copy, Clone, Debug, PartialEq)]
|
||||
pub enum AssocCtxt {
|
||||
Trait,
|
||||
Impl,
|
||||
Impl { of_trait: bool },
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq)]
|
||||
@ -65,7 +66,7 @@ impl BoundKind {
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub enum FnKind<'a> {
|
||||
/// E.g., `fn foo()`, `fn foo(&self)`, or `extern "Abi" fn foo()`.
|
||||
Fn(FnCtxt, &'a Ident, &'a Visibility, &'a Fn),
|
||||
Fn(FnCtxt, &'a Visibility, &'a Fn),
|
||||
|
||||
/// E.g., `|x, y| body`.
|
||||
Closure(&'a ClosureBinder, &'a Option<CoroutineKind>, &'a FnDecl, &'a Expr),
|
||||
@ -74,21 +75,21 @@ pub enum FnKind<'a> {
|
||||
impl<'a> FnKind<'a> {
|
||||
pub fn header(&self) -> Option<&'a FnHeader> {
|
||||
match *self {
|
||||
FnKind::Fn(_, _, _, Fn { sig, .. }) => Some(&sig.header),
|
||||
FnKind::Fn(_, _, Fn { sig, .. }) => Some(&sig.header),
|
||||
FnKind::Closure(..) => None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn ident(&self) -> Option<&Ident> {
|
||||
match self {
|
||||
FnKind::Fn(_, ident, ..) => Some(ident),
|
||||
FnKind::Fn(_, _, Fn { ident, .. }) => Some(ident),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn decl(&self) -> &'a FnDecl {
|
||||
match self {
|
||||
FnKind::Fn(_, _, _, Fn { sig, .. }) => &sig.decl,
|
||||
FnKind::Fn(_, _, Fn { sig, .. }) => &sig.decl,
|
||||
FnKind::Closure(_, _, decl, _) => decl,
|
||||
}
|
||||
}
|
||||
@ -117,7 +118,6 @@ pub trait WalkItemKind {
|
||||
&'a self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &'a Ident,
|
||||
visibility: &'a Visibility,
|
||||
ctxt: Self::Ctxt,
|
||||
visitor: &mut V,
|
||||
@ -363,49 +363,72 @@ impl WalkItemKind for ItemKind {
|
||||
&'a self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &'a Ident,
|
||||
vis: &'a Visibility,
|
||||
_ctxt: Self::Ctxt,
|
||||
visitor: &mut V,
|
||||
) -> V::Result {
|
||||
match self {
|
||||
ItemKind::ExternCrate(_rename) => {}
|
||||
ItemKind::ExternCrate(_rename, ident) => try_visit!(visitor.visit_ident(ident)),
|
||||
ItemKind::Use(use_tree) => try_visit!(visitor.visit_use_tree(use_tree, id, false)),
|
||||
ItemKind::Static(box StaticItem { ty, safety: _, mutability: _, expr }) => {
|
||||
ItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
safety: _,
|
||||
mutability: _,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_ty(ty));
|
||||
visit_opt!(visitor, visit_expr, expr);
|
||||
try_visit!(walk_define_opaques(visitor, define_opaque));
|
||||
}
|
||||
ItemKind::Const(box ConstItem { defaultness: _, generics, ty, expr }) => {
|
||||
ItemKind::Const(box ConstItem {
|
||||
defaultness: _,
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
try_visit!(visitor.visit_ty(ty));
|
||||
visit_opt!(visitor, visit_expr, expr);
|
||||
try_visit!(walk_define_opaques(visitor, define_opaque));
|
||||
}
|
||||
ItemKind::Fn(func) => {
|
||||
let kind = FnKind::Fn(FnCtxt::Free, ident, vis, &*func);
|
||||
let kind = FnKind::Fn(FnCtxt::Free, vis, &*func);
|
||||
try_visit!(visitor.visit_fn(kind, span, id));
|
||||
}
|
||||
ItemKind::Mod(_unsafety, mod_kind) => match mod_kind {
|
||||
ModKind::Loaded(items, _inline, _inner_span, _) => {
|
||||
walk_list!(visitor, visit_item, items);
|
||||
ItemKind::Mod(_unsafety, ident, mod_kind) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
match mod_kind {
|
||||
ModKind::Loaded(items, _inline, _inner_span, _) => {
|
||||
walk_list!(visitor, visit_item, items);
|
||||
}
|
||||
ModKind::Unloaded => {}
|
||||
}
|
||||
ModKind::Unloaded => {}
|
||||
},
|
||||
}
|
||||
ItemKind::ForeignMod(ForeignMod { extern_span: _, safety: _, abi: _, items }) => {
|
||||
walk_list!(visitor, visit_foreign_item, items);
|
||||
}
|
||||
ItemKind::GlobalAsm(asm) => try_visit!(visitor.visit_inline_asm(asm)),
|
||||
ItemKind::TyAlias(box TyAlias {
|
||||
generics,
|
||||
ident,
|
||||
bounds,
|
||||
ty,
|
||||
defaultness: _,
|
||||
where_clauses: _,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound);
|
||||
visit_opt!(visitor, visit_ty, ty);
|
||||
}
|
||||
ItemKind::Enum(enum_definition, generics) => {
|
||||
ItemKind::Enum(ident, enum_definition, generics) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
try_visit!(visitor.visit_enum_def(enum_definition));
|
||||
}
|
||||
@ -422,34 +445,54 @@ impl WalkItemKind for ItemKind {
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
visit_opt!(visitor, visit_trait_ref, of_trait);
|
||||
try_visit!(visitor.visit_ty(self_ty));
|
||||
walk_list!(visitor, visit_assoc_item, items, AssocCtxt::Impl);
|
||||
walk_list!(
|
||||
visitor,
|
||||
visit_assoc_item,
|
||||
items,
|
||||
AssocCtxt::Impl { of_trait: of_trait.is_some() }
|
||||
);
|
||||
}
|
||||
ItemKind::Struct(struct_definition, generics)
|
||||
| ItemKind::Union(struct_definition, generics) => {
|
||||
ItemKind::Struct(ident, struct_definition, generics)
|
||||
| ItemKind::Union(ident, struct_definition, generics) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
try_visit!(visitor.visit_variant_data(struct_definition));
|
||||
}
|
||||
ItemKind::Trait(box Trait { safety: _, is_auto: _, generics, bounds, items }) => {
|
||||
ItemKind::Trait(box Trait {
|
||||
safety: _,
|
||||
is_auto: _,
|
||||
ident,
|
||||
generics,
|
||||
bounds,
|
||||
items,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
walk_list!(visitor, visit_param_bound, bounds, BoundKind::SuperTraits);
|
||||
walk_list!(visitor, visit_assoc_item, items, AssocCtxt::Trait);
|
||||
}
|
||||
ItemKind::TraitAlias(generics, bounds) => {
|
||||
ItemKind::TraitAlias(ident, generics, bounds) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound);
|
||||
}
|
||||
ItemKind::MacCall(mac) => try_visit!(visitor.visit_mac_call(mac)),
|
||||
ItemKind::MacroDef(ts) => try_visit!(visitor.visit_mac_def(ts, id)),
|
||||
ItemKind::MacroDef(ident, ts) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_mac_def(ts, id))
|
||||
}
|
||||
ItemKind::Delegation(box Delegation {
|
||||
id,
|
||||
qself,
|
||||
path,
|
||||
ident,
|
||||
rename,
|
||||
body,
|
||||
from_glob: _,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_qself(qself));
|
||||
try_visit!(visitor.visit_path(path, *id));
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
visit_opt!(visitor, visit_ident, rename);
|
||||
visit_opt!(visitor, visit_block, body);
|
||||
}
|
||||
@ -723,27 +766,37 @@ impl WalkItemKind for ForeignItemKind {
|
||||
&'a self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &'a Ident,
|
||||
vis: &'a Visibility,
|
||||
_ctxt: Self::Ctxt,
|
||||
visitor: &mut V,
|
||||
) -> V::Result {
|
||||
match self {
|
||||
ForeignItemKind::Static(box StaticItem { ty, mutability: _, expr, safety: _ }) => {
|
||||
ForeignItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
mutability: _,
|
||||
expr,
|
||||
safety: _,
|
||||
define_opaque,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_ty(ty));
|
||||
visit_opt!(visitor, visit_expr, expr);
|
||||
try_visit!(walk_define_opaques(visitor, define_opaque));
|
||||
}
|
||||
ForeignItemKind::Fn(func) => {
|
||||
let kind = FnKind::Fn(FnCtxt::Foreign, ident, vis, &*func);
|
||||
let kind = FnKind::Fn(FnCtxt::Foreign, vis, &*func);
|
||||
try_visit!(visitor.visit_fn(kind, span, id));
|
||||
}
|
||||
ForeignItemKind::TyAlias(box TyAlias {
|
||||
generics,
|
||||
ident,
|
||||
bounds,
|
||||
ty,
|
||||
defaultness: _,
|
||||
where_clauses: _,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound);
|
||||
visit_opt!(visitor, visit_ty, ty);
|
||||
@ -890,10 +943,10 @@ pub fn walk_fn<'a, V: Visitor<'a>>(visitor: &mut V, kind: FnKind<'a>) -> V::Resu
|
||||
match kind {
|
||||
FnKind::Fn(
|
||||
_ctxt,
|
||||
_ident,
|
||||
_vis,
|
||||
Fn {
|
||||
defaultness: _,
|
||||
ident,
|
||||
sig: FnSig { header, decl, span: _ },
|
||||
generics,
|
||||
contract,
|
||||
@ -901,15 +954,14 @@ pub fn walk_fn<'a, V: Visitor<'a>>(visitor: &mut V, kind: FnKind<'a>) -> V::Resu
|
||||
define_opaque,
|
||||
},
|
||||
) => {
|
||||
// Identifier and visibility are visited as a part of the item.
|
||||
// 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);
|
||||
for (id, path) in define_opaque.iter().flatten() {
|
||||
try_visit!(visitor.visit_path(path, *id))
|
||||
}
|
||||
try_visit!(walk_define_opaques(visitor, define_opaque));
|
||||
}
|
||||
FnKind::Closure(binder, coroutine_kind, decl, body) => {
|
||||
try_visit!(visitor.visit_closure_binder(binder));
|
||||
@ -927,29 +979,39 @@ impl WalkItemKind for AssocItemKind {
|
||||
&'a self,
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
ident: &'a Ident,
|
||||
vis: &'a Visibility,
|
||||
ctxt: Self::Ctxt,
|
||||
visitor: &mut V,
|
||||
) -> V::Result {
|
||||
match self {
|
||||
AssocItemKind::Const(box ConstItem { defaultness: _, generics, ty, expr }) => {
|
||||
AssocItemKind::Const(box ConstItem {
|
||||
defaultness: _,
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
try_visit!(visitor.visit_ty(ty));
|
||||
visit_opt!(visitor, visit_expr, expr);
|
||||
try_visit!(walk_define_opaques(visitor, define_opaque));
|
||||
}
|
||||
AssocItemKind::Fn(func) => {
|
||||
let kind = FnKind::Fn(FnCtxt::Assoc(ctxt), ident, vis, &*func);
|
||||
let kind = FnKind::Fn(FnCtxt::Assoc(ctxt), vis, &*func);
|
||||
try_visit!(visitor.visit_fn(kind, span, id));
|
||||
}
|
||||
AssocItemKind::Type(box TyAlias {
|
||||
generics,
|
||||
ident,
|
||||
bounds,
|
||||
ty,
|
||||
defaultness: _,
|
||||
where_clauses: _,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_generics(generics));
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
walk_list!(visitor, visit_param_bound, bounds, BoundKind::Bound);
|
||||
visit_opt!(visitor, visit_ty, ty);
|
||||
}
|
||||
@ -960,12 +1022,14 @@ impl WalkItemKind for AssocItemKind {
|
||||
id,
|
||||
qself,
|
||||
path,
|
||||
ident,
|
||||
rename,
|
||||
body,
|
||||
from_glob: _,
|
||||
}) => {
|
||||
try_visit!(visitor.visit_qself(qself));
|
||||
try_visit!(visitor.visit_path(path, *id));
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
visit_opt!(visitor, visit_ident, rename);
|
||||
visit_opt!(visitor, visit_block, body);
|
||||
}
|
||||
@ -1007,11 +1071,10 @@ fn walk_item_ctxt<'a, V: Visitor<'a>, K: WalkItemKind>(
|
||||
item: &'a Item<K>,
|
||||
ctxt: K::Ctxt,
|
||||
) -> V::Result {
|
||||
let Item { id, span, ident, vis, attrs, kind, tokens: _ } = item;
|
||||
let Item { id, span, vis, attrs, kind, tokens: _ } = item;
|
||||
walk_list!(visitor, visit_attribute, attrs);
|
||||
try_visit!(visitor.visit_vis(vis));
|
||||
try_visit!(visitor.visit_ident(ident));
|
||||
try_visit!(kind.walk(*span, *id, ident, vis, ctxt, visitor));
|
||||
try_visit!(kind.walk(*span, *id, vis, ctxt, visitor));
|
||||
V::Result::output()
|
||||
}
|
||||
|
||||
@ -1035,7 +1098,7 @@ pub fn walk_field_def<'a, V: Visitor<'a>>(visitor: &mut V, field: &'a FieldDef)
|
||||
}
|
||||
|
||||
pub fn walk_block<'a, V: Visitor<'a>>(visitor: &mut V, block: &'a Block) -> V::Result {
|
||||
let Block { stmts, id: _, rules: _, span: _, tokens: _, could_be_bare_literal: _ } = block;
|
||||
let Block { stmts, id: _, rules: _, span: _, tokens: _ } = block;
|
||||
walk_list!(visitor, visit_stmt, stmts);
|
||||
V::Result::output()
|
||||
}
|
||||
@ -1269,8 +1332,8 @@ pub fn walk_expr<'a, V: Visitor<'a>>(visitor: &mut V, expression: &'a Expr) -> V
|
||||
try_visit!(visitor.visit_ty(container));
|
||||
walk_list!(visitor, visit_ident, fields.iter());
|
||||
}
|
||||
ExprKind::Yield(optional_expression) => {
|
||||
visit_opt!(visitor, visit_expr, optional_expression);
|
||||
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)),
|
||||
@ -1337,3 +1400,15 @@ pub fn walk_attr_args<'a, V: Visitor<'a>>(visitor: &mut V, args: &'a AttrArgs) -
|
||||
}
|
||||
V::Result::output()
|
||||
}
|
||||
|
||||
fn walk_define_opaques<'a, V: Visitor<'a>>(
|
||||
visitor: &mut V,
|
||||
define_opaque: &'a Option<ThinVec<(NodeId, Path)>>,
|
||||
) -> V::Result {
|
||||
if let Some(define_opaque) = define_opaque {
|
||||
for (id, path) in define_opaque {
|
||||
try_visit!(visitor.visit_path(path, *id));
|
||||
}
|
||||
}
|
||||
V::Result::output()
|
||||
}
|
||||
|
@ -8,7 +8,6 @@ edition = "2024"
|
||||
rustc_data_structures = { path = "../rustc_data_structures", optional = true }
|
||||
rustc_macros = { path = "../rustc_macros", optional = true }
|
||||
rustc_serialize = { path = "../rustc_serialize", optional = true }
|
||||
rustc_span = { path = "../rustc_span", optional = true }
|
||||
# tidy-alphabetical-end
|
||||
|
||||
[features]
|
||||
@ -17,5 +16,4 @@ nightly = [
|
||||
"dep:rustc_serialize",
|
||||
"dep:rustc_data_structures",
|
||||
"dep:rustc_macros",
|
||||
"dep:rustc_span",
|
||||
]
|
||||
|
@ -20,7 +20,6 @@ rustc_hir = { path = "../rustc_hir" }
|
||||
rustc_index = { path = "../rustc_index" }
|
||||
rustc_macros = { path = "../rustc_macros" }
|
||||
rustc_middle = { path = "../rustc_middle" }
|
||||
rustc_parse = { path = "../rustc_parse" }
|
||||
rustc_session = { path = "../rustc_session" }
|
||||
rustc_span = { path = "../rustc_span" }
|
||||
rustc_target = { path = "../rustc_target" }
|
||||
|
@ -141,9 +141,6 @@ ast_lowering_never_pattern_with_guard =
|
||||
|
||||
ast_lowering_no_precise_captures_on_apit = `use<...>` precise capturing syntax not allowed in argument-position `impl Trait`
|
||||
|
||||
ast_lowering_no_precise_captures_on_rpitit = `use<...>` precise capturing syntax is currently not allowed in return-position `impl Trait` in traits
|
||||
.note = currently, return-position `impl Trait` in traits and trait implementations capture all lifetimes in scope
|
||||
|
||||
ast_lowering_previously_used_here = previously used here
|
||||
|
||||
ast_lowering_register1 = register `{$reg1_name}`
|
||||
|
@ -56,13 +56,20 @@ use crate::{AllowReturnTypeNotation, ImplTraitPosition, ResolverAstLoweringExt};
|
||||
pub(crate) struct DelegationResults<'hir> {
|
||||
pub body_id: hir::BodyId,
|
||||
pub sig: hir::FnSig<'hir>,
|
||||
pub ident: Ident,
|
||||
pub generics: &'hir hir::Generics<'hir>,
|
||||
}
|
||||
|
||||
impl<'hir> LoweringContext<'_, 'hir> {
|
||||
/// Defines whether the delegatee is an associated function whose first parameter is `self`.
|
||||
pub(crate) fn delegatee_is_method(&self, item_id: NodeId, path_id: NodeId, span: Span) -> bool {
|
||||
let sig_id = self.get_delegation_sig_id(item_id, path_id, span);
|
||||
pub(crate) fn delegatee_is_method(
|
||||
&self,
|
||||
item_id: NodeId,
|
||||
path_id: NodeId,
|
||||
span: Span,
|
||||
is_in_trait_impl: bool,
|
||||
) -> bool {
|
||||
let sig_id = self.get_delegation_sig_id(item_id, path_id, span, is_in_trait_impl);
|
||||
let Ok(sig_id) = sig_id else {
|
||||
return false;
|
||||
};
|
||||
@ -88,18 +95,19 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
&mut self,
|
||||
delegation: &Delegation,
|
||||
item_id: NodeId,
|
||||
is_in_trait_impl: bool,
|
||||
) -> DelegationResults<'hir> {
|
||||
let span = self.lower_span(delegation.path.segments.last().unwrap().ident.span);
|
||||
let sig_id = self.get_delegation_sig_id(item_id, delegation.id, span);
|
||||
let sig_id = self.get_delegation_sig_id(item_id, delegation.id, span, is_in_trait_impl);
|
||||
match sig_id {
|
||||
Ok(sig_id) => {
|
||||
let (param_count, c_variadic) = self.param_count(sig_id);
|
||||
let decl = self.lower_delegation_decl(sig_id, param_count, c_variadic, span);
|
||||
let sig = self.lower_delegation_sig(sig_id, decl, span);
|
||||
let body_id = self.lower_delegation_body(delegation, param_count, span);
|
||||
|
||||
let ident = self.lower_ident(delegation.ident);
|
||||
let generics = self.lower_delegation_generics(span);
|
||||
DelegationResults { body_id, sig, generics }
|
||||
DelegationResults { body_id, sig, ident, generics }
|
||||
}
|
||||
Err(err) => self.generate_delegation_error(err, span),
|
||||
}
|
||||
@ -110,8 +118,9 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
item_id: NodeId,
|
||||
path_id: NodeId,
|
||||
span: Span,
|
||||
is_in_trait_impl: bool,
|
||||
) -> Result<DefId, ErrorGuaranteed> {
|
||||
let sig_id = if self.is_in_trait_impl { item_id } else { path_id };
|
||||
let sig_id = if is_in_trait_impl { item_id } else { path_id };
|
||||
self.get_resolution_id(sig_id, span)
|
||||
}
|
||||
|
||||
@ -397,8 +406,9 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
let header = self.generate_header_error();
|
||||
let sig = hir::FnSig { decl, header, span };
|
||||
|
||||
let ident = Ident::dummy();
|
||||
let body_id = self.lower_body(|this| (&[], this.mk_expr(hir::ExprKind::Err(err), span)));
|
||||
DelegationResults { generics, body_id, sig }
|
||||
DelegationResults { ident, generics, body_id, sig }
|
||||
}
|
||||
|
||||
fn generate_header_error(&self) -> hir::FnHeader {
|
||||
|
@ -444,14 +444,6 @@ pub(crate) struct NoPreciseCapturesOnApit {
|
||||
pub span: Span,
|
||||
}
|
||||
|
||||
#[derive(Diagnostic)]
|
||||
#[diag(ast_lowering_no_precise_captures_on_rpitit)]
|
||||
#[note]
|
||||
pub(crate) struct NoPreciseCapturesOnRpitit {
|
||||
#[primary_span]
|
||||
pub span: Span,
|
||||
}
|
||||
|
||||
#[derive(Diagnostic)]
|
||||
#[diag(ast_lowering_yield_in_closure)]
|
||||
pub(crate) struct YieldInClosure {
|
||||
|
@ -351,7 +351,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
rest,
|
||||
)
|
||||
}
|
||||
ExprKind::Yield(opt_expr) => self.lower_expr_yield(e.span, opt_expr.as_deref()),
|
||||
ExprKind::Yield(kind) => self.lower_expr_yield(e.span, kind.expr().map(|x| &**x)),
|
||||
ExprKind::Err(guar) => hir::ExprKind::Err(*guar),
|
||||
|
||||
ExprKind::UnsafeBinderCast(kind, expr, ty) => hir::ExprKind::UnsafeBinderCast(
|
||||
@ -2150,11 +2150,6 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
self.expr_uint(sp, ast::UintTy::U16, value as u128)
|
||||
}
|
||||
|
||||
pub(super) fn expr_char(&mut self, sp: Span, value: char) -> hir::Expr<'hir> {
|
||||
let lit = self.arena.alloc(hir::Lit { span: sp, node: ast::LitKind::Char(value) });
|
||||
self.expr(sp, hir::ExprKind::Lit(lit))
|
||||
}
|
||||
|
||||
pub(super) fn expr_str(&mut self, sp: Span, value: Symbol) -> hir::Expr<'hir> {
|
||||
let lit = self
|
||||
.arena
|
||||
|
@ -323,14 +323,12 @@ fn make_count<'hir>(
|
||||
/// Generates
|
||||
///
|
||||
/// ```text
|
||||
/// <core::fmt::rt::Placeholder::new(
|
||||
/// …usize, // position
|
||||
/// '…', // fill
|
||||
/// <core::fmt::rt::Alignment>::…, // alignment
|
||||
/// …u32, // flags
|
||||
/// <core::fmt::rt::Count::…>, // width
|
||||
/// <core::fmt::rt::Count::…>, // precision
|
||||
/// )
|
||||
/// <core::fmt::rt::Placeholder {
|
||||
/// position: …usize,
|
||||
/// flags: …u32,
|
||||
/// precision: <core::fmt::rt::Count::…>,
|
||||
/// width: <core::fmt::rt::Count::…>,
|
||||
/// }
|
||||
/// ```
|
||||
fn make_format_spec<'hir>(
|
||||
ctx: &mut LoweringContext<'_, 'hir>,
|
||||
@ -361,34 +359,36 @@ fn make_format_spec<'hir>(
|
||||
zero_pad,
|
||||
debug_hex,
|
||||
} = &placeholder.format_options;
|
||||
let fill = ctx.expr_char(sp, fill.unwrap_or(' '));
|
||||
let align = ctx.expr_lang_item_type_relative(
|
||||
sp,
|
||||
hir::LangItem::FormatAlignment,
|
||||
match alignment {
|
||||
Some(FormatAlignment::Left) => sym::Left,
|
||||
Some(FormatAlignment::Right) => sym::Right,
|
||||
Some(FormatAlignment::Center) => sym::Center,
|
||||
None => sym::Unknown,
|
||||
},
|
||||
);
|
||||
// This needs to match `Flag` in library/core/src/fmt/rt.rs.
|
||||
let flags: u32 = ((sign == Some(FormatSign::Plus)) as u32)
|
||||
| ((sign == Some(FormatSign::Minus)) as u32) << 1
|
||||
| (alternate as u32) << 2
|
||||
| (zero_pad as u32) << 3
|
||||
| ((debug_hex == Some(FormatDebugHex::Lower)) as u32) << 4
|
||||
| ((debug_hex == Some(FormatDebugHex::Upper)) as u32) << 5;
|
||||
let fill = fill.unwrap_or(' ');
|
||||
// These need to match the constants in library/core/src/fmt/rt.rs.
|
||||
let align = match alignment {
|
||||
Some(FormatAlignment::Left) => 0,
|
||||
Some(FormatAlignment::Right) => 1,
|
||||
Some(FormatAlignment::Center) => 2,
|
||||
None => 3,
|
||||
};
|
||||
// This needs to match the constants in library/core/src/fmt/rt.rs.
|
||||
let flags: u32 = fill as u32
|
||||
| ((sign == Some(FormatSign::Plus)) as u32) << 21
|
||||
| ((sign == Some(FormatSign::Minus)) as u32) << 22
|
||||
| (alternate as u32) << 23
|
||||
| (zero_pad as u32) << 24
|
||||
| ((debug_hex == Some(FormatDebugHex::Lower)) as u32) << 25
|
||||
| ((debug_hex == Some(FormatDebugHex::Upper)) as u32) << 26
|
||||
| (width.is_some() as u32) << 27
|
||||
| (precision.is_some() as u32) << 28
|
||||
| align << 29
|
||||
| 1 << 31; // Highest bit always set.
|
||||
let flags = ctx.expr_u32(sp, flags);
|
||||
let precision = make_count(ctx, sp, precision, argmap);
|
||||
let width = make_count(ctx, sp, width, argmap);
|
||||
let format_placeholder_new = ctx.arena.alloc(ctx.expr_lang_item_type_relative(
|
||||
sp,
|
||||
hir::LangItem::FormatPlaceholder,
|
||||
sym::new,
|
||||
));
|
||||
let args = ctx.arena.alloc_from_iter([position, fill, align, flags, precision, width]);
|
||||
ctx.expr_call_mut(sp, format_placeholder_new, args)
|
||||
let position = ctx.expr_field(Ident::new(sym::position, sp), ctx.arena.alloc(position), sp);
|
||||
let flags = ctx.expr_field(Ident::new(sym::flags, sp), ctx.arena.alloc(flags), sp);
|
||||
let precision = ctx.expr_field(Ident::new(sym::precision, sp), ctx.arena.alloc(precision), sp);
|
||||
let width = ctx.expr_field(Ident::new(sym::width, sp), ctx.arena.alloc(width), sp);
|
||||
let placeholder = ctx.arena.alloc(hir::QPath::LangItem(hir::LangItem::FormatPlaceholder, sp));
|
||||
let fields = ctx.arena.alloc_from_iter([position, flags, precision, width]);
|
||||
ctx.expr(sp, hir::ExprKind::Struct(placeholder, fields, hir::StructTailExpr::None))
|
||||
}
|
||||
|
||||
fn expand_format_args<'hir>(
|
||||
|
@ -164,7 +164,7 @@ impl<'a, 'hir> Visitor<'hir> for NodeCollector<'a, 'hir> {
|
||||
fn visit_item(&mut self, i: &'hir Item<'hir>) {
|
||||
debug_assert_eq!(i.owner_id, self.owner);
|
||||
self.with_parent(i.hir_id(), |this| {
|
||||
if let ItemKind::Struct(struct_def, _) = &i.kind {
|
||||
if let ItemKind::Struct(_, struct_def, _) = &i.kind {
|
||||
// If this is a tuple or unit-like struct, register the constructor.
|
||||
if let Some(ctor_hir_id) = struct_def.ctor_hir_id() {
|
||||
this.insert(i.span, ctor_hir_id, Node::Ctor(struct_def));
|
||||
|
@ -5,9 +5,8 @@ use rustc_ast::*;
|
||||
use rustc_errors::ErrorGuaranteed;
|
||||
use rustc_hir::def::{DefKind, Res};
|
||||
use rustc_hir::def_id::{CRATE_DEF_ID, LocalDefId};
|
||||
use rustc_hir::{self as hir, HirId, PredicateOrigin};
|
||||
use rustc_hir::{self as hir, HirId, IsAnonInPath, PredicateOrigin};
|
||||
use rustc_index::{IndexSlice, IndexVec};
|
||||
use rustc_middle::span_bug;
|
||||
use rustc_middle::ty::{ResolverAstLowering, TyCtxt};
|
||||
use rustc_span::edit_distance::find_best_match_for_name;
|
||||
use rustc_span::{DUMMY_SP, DesugaringKind, Ident, Span, Symbol, kw, sym};
|
||||
@ -104,10 +103,7 @@ impl<'a, 'hir> ItemLowerer<'a, 'hir> {
|
||||
}
|
||||
|
||||
fn lower_assoc_item(&mut self, item: &AssocItem, ctxt: AssocCtxt) {
|
||||
let def_id = self.resolver.node_id_to_def_id[&item.id];
|
||||
let parent_id = self.tcx.local_parent(def_id);
|
||||
let parent_hir = self.lower_node(parent_id).unwrap();
|
||||
self.with_lctx(item.id, |lctx| lctx.lower_assoc_item(item, ctxt, parent_hir))
|
||||
self.with_lctx(item.id, |lctx| lctx.lower_assoc_item(item, ctxt))
|
||||
}
|
||||
|
||||
fn lower_foreign_item(&mut self, item: &ForeignItem) {
|
||||
@ -131,8 +127,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
}
|
||||
|
||||
pub(super) fn lower_item_ref(&mut self, i: &Item) -> SmallVec<[hir::ItemId; 1]> {
|
||||
let mut node_ids =
|
||||
smallvec![hir::ItemId { owner_id: hir::OwnerId { def_id: self.local_def_id(i.id) } }];
|
||||
let mut node_ids = smallvec![hir::ItemId { owner_id: self.owner_id(i.id) }];
|
||||
if let ItemKind::Use(use_tree) = &i.kind {
|
||||
self.lower_item_id_use_tree(use_tree, &mut node_ids);
|
||||
}
|
||||
@ -143,9 +138,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
match &tree.kind {
|
||||
UseTreeKind::Nested { items, .. } => {
|
||||
for &(ref nested, id) in items {
|
||||
vec.push(hir::ItemId {
|
||||
owner_id: hir::OwnerId { def_id: self.local_def_id(id) },
|
||||
});
|
||||
vec.push(hir::ItemId { owner_id: self.owner_id(id) });
|
||||
self.lower_item_id_use_tree(nested, vec);
|
||||
}
|
||||
}
|
||||
@ -154,14 +147,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
}
|
||||
|
||||
fn lower_item(&mut self, i: &Item) -> &'hir hir::Item<'hir> {
|
||||
let mut ident = i.ident;
|
||||
let vis_span = self.lower_span(i.vis.span);
|
||||
let hir_id = hir::HirId::make_owner(self.current_hir_id_owner.def_id);
|
||||
let attrs = self.lower_attrs(hir_id, &i.attrs, i.span);
|
||||
let kind = self.lower_item_kind(i.span, i.id, hir_id, &mut ident, attrs, vis_span, &i.kind);
|
||||
let kind = self.lower_item_kind(i.span, i.id, hir_id, attrs, vis_span, &i.kind);
|
||||
let item = hir::Item {
|
||||
owner_id: hir_id.expect_owner(),
|
||||
ident: self.lower_ident(ident),
|
||||
kind,
|
||||
vis_span,
|
||||
span: self.lower_span(i.span),
|
||||
@ -174,25 +165,44 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
span: Span,
|
||||
id: NodeId,
|
||||
hir_id: hir::HirId,
|
||||
ident: &mut Ident,
|
||||
attrs: &'hir [hir::Attribute],
|
||||
vis_span: Span,
|
||||
i: &ItemKind,
|
||||
) -> hir::ItemKind<'hir> {
|
||||
match i {
|
||||
ItemKind::ExternCrate(orig_name) => hir::ItemKind::ExternCrate(*orig_name),
|
||||
ItemKind::ExternCrate(orig_name, ident) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
hir::ItemKind::ExternCrate(*orig_name, ident)
|
||||
}
|
||||
ItemKind::Use(use_tree) => {
|
||||
// Start with an empty prefix.
|
||||
let prefix = Path { segments: ThinVec::new(), span: use_tree.span, tokens: None };
|
||||
|
||||
self.lower_use_tree(use_tree, &prefix, id, vis_span, ident, attrs)
|
||||
self.lower_use_tree(use_tree, &prefix, id, vis_span, attrs)
|
||||
}
|
||||
ItemKind::Static(box ast::StaticItem { ty: t, safety: _, mutability: m, expr: e }) => {
|
||||
ItemKind::Static(box ast::StaticItem {
|
||||
ident,
|
||||
ty: t,
|
||||
safety: _,
|
||||
mutability: m,
|
||||
expr: e,
|
||||
define_opaque,
|
||||
}) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (ty, body_id) =
|
||||
self.lower_const_item(t, span, e.as_deref(), ImplTraitPosition::StaticTy);
|
||||
hir::ItemKind::Static(ty, *m, body_id)
|
||||
self.lower_define_opaque(hir_id, define_opaque);
|
||||
hir::ItemKind::Static(ident, ty, *m, body_id)
|
||||
}
|
||||
ItemKind::Const(box ast::ConstItem { generics, ty, expr, .. }) => {
|
||||
ItemKind::Const(box ast::ConstItem {
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
..
|
||||
}) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, (ty, body_id)) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
@ -201,10 +211,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
this.lower_const_item(ty, span, expr.as_deref(), ImplTraitPosition::ConstTy)
|
||||
},
|
||||
);
|
||||
hir::ItemKind::Const(ty, generics, body_id)
|
||||
self.lower_define_opaque(hir_id, &define_opaque);
|
||||
hir::ItemKind::Const(ident, ty, generics, body_id)
|
||||
}
|
||||
ItemKind::Fn(box Fn {
|
||||
sig: FnSig { decl, header, span: fn_sig_span },
|
||||
ident,
|
||||
generics,
|
||||
body,
|
||||
contract,
|
||||
@ -237,16 +249,26 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
header: this.lower_fn_header(*header, hir::Safety::Safe, attrs),
|
||||
span: this.lower_span(*fn_sig_span),
|
||||
};
|
||||
this.lower_define_opaque(hir_id, &define_opaque);
|
||||
hir::ItemKind::Fn { sig, generics, body: body_id, has_body: body.is_some() }
|
||||
this.lower_define_opaque(hir_id, define_opaque);
|
||||
let ident = this.lower_ident(*ident);
|
||||
hir::ItemKind::Fn {
|
||||
ident,
|
||||
sig,
|
||||
generics,
|
||||
body: body_id,
|
||||
has_body: body.is_some(),
|
||||
}
|
||||
})
|
||||
}
|
||||
ItemKind::Mod(_, mod_kind) => match mod_kind {
|
||||
ModKind::Loaded(items, _, spans, _) => {
|
||||
hir::ItemKind::Mod(self.lower_mod(items, spans))
|
||||
ItemKind::Mod(_, ident, mod_kind) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
match mod_kind {
|
||||
ModKind::Loaded(items, _, spans, _) => {
|
||||
hir::ItemKind::Mod(ident, self.lower_mod(items, spans))
|
||||
}
|
||||
ModKind::Unloaded => panic!("`mod` items should have been loaded by now"),
|
||||
}
|
||||
ModKind::Unloaded => panic!("`mod` items should have been loaded by now"),
|
||||
},
|
||||
}
|
||||
ItemKind::ForeignMod(fm) => hir::ItemKind::ForeignMod {
|
||||
abi: fm.abi.map_or(ExternAbi::FALLBACK, |abi| self.lower_abi(abi)),
|
||||
items: self
|
||||
@ -259,7 +281,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
self.lower_body(|this| (&[], this.expr(span, hir::ExprKind::InlineAsm(asm))));
|
||||
hir::ItemKind::GlobalAsm { asm, fake_body }
|
||||
}
|
||||
ItemKind::TyAlias(box TyAlias { generics, where_clauses, ty, .. }) => {
|
||||
ItemKind::TyAlias(box TyAlias { ident, generics, where_clauses, ty, .. }) => {
|
||||
// We lower
|
||||
//
|
||||
// type Foo = impl Trait
|
||||
@ -268,6 +290,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
//
|
||||
// type Foo = Foo1
|
||||
// opaque type Foo1: Trait
|
||||
let ident = self.lower_ident(*ident);
|
||||
let mut generics = generics.clone();
|
||||
add_ty_alias_where_clause(&mut generics, *where_clauses, true);
|
||||
let (generics, ty) = self.lower_generics(
|
||||
@ -293,9 +316,10 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
),
|
||||
},
|
||||
);
|
||||
hir::ItemKind::TyAlias(ty, generics)
|
||||
hir::ItemKind::TyAlias(ident, ty, generics)
|
||||
}
|
||||
ItemKind::Enum(enum_definition, generics) => {
|
||||
ItemKind::Enum(ident, enum_definition, generics) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, variants) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
@ -306,25 +330,27 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
)
|
||||
},
|
||||
);
|
||||
hir::ItemKind::Enum(hir::EnumDef { variants }, generics)
|
||||
hir::ItemKind::Enum(ident, hir::EnumDef { variants }, generics)
|
||||
}
|
||||
ItemKind::Struct(struct_def, generics) => {
|
||||
ItemKind::Struct(ident, struct_def, generics) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, struct_def) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| this.lower_variant_data(hir_id, struct_def),
|
||||
);
|
||||
hir::ItemKind::Struct(struct_def, generics)
|
||||
hir::ItemKind::Struct(ident, struct_def, generics)
|
||||
}
|
||||
ItemKind::Union(vdata, generics) => {
|
||||
ItemKind::Union(ident, vdata, generics) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, vdata) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| this.lower_variant_data(hir_id, vdata),
|
||||
);
|
||||
hir::ItemKind::Union(vdata, generics)
|
||||
hir::ItemKind::Union(ident, vdata, generics)
|
||||
}
|
||||
ItemKind::Impl(box Impl {
|
||||
safety,
|
||||
@ -375,10 +401,11 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
(trait_ref, lowered_ty)
|
||||
});
|
||||
|
||||
self.is_in_trait_impl = trait_ref.is_some();
|
||||
let new_impl_items = self
|
||||
.arena
|
||||
.alloc_from_iter(impl_items.iter().map(|item| self.lower_impl_item_ref(item)));
|
||||
let new_impl_items = self.arena.alloc_from_iter(
|
||||
impl_items
|
||||
.iter()
|
||||
.map(|item| self.lower_impl_item_ref(item, trait_ref.is_some())),
|
||||
);
|
||||
|
||||
// `defaultness.has_value()` is never called for an `impl`, always `true` in order
|
||||
// to not cause an assertion failure inside the `lower_defaultness` function.
|
||||
@ -400,7 +427,8 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
items: new_impl_items,
|
||||
}))
|
||||
}
|
||||
ItemKind::Trait(box Trait { is_auto, safety, generics, bounds, items }) => {
|
||||
ItemKind::Trait(box Trait { is_auto, safety, ident, generics, bounds, items }) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, (safety, items, bounds)) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
@ -417,9 +445,10 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
(safety, items, bounds)
|
||||
},
|
||||
);
|
||||
hir::ItemKind::Trait(*is_auto, safety, generics, bounds, items)
|
||||
hir::ItemKind::Trait(*is_auto, safety, ident, generics, bounds, items)
|
||||
}
|
||||
ItemKind::TraitAlias(generics, bounds) => {
|
||||
ItemKind::TraitAlias(ident, generics, bounds) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let (generics, bounds) = self.lower_generics(
|
||||
generics,
|
||||
id,
|
||||
@ -431,9 +460,10 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
)
|
||||
},
|
||||
);
|
||||
hir::ItemKind::TraitAlias(generics, bounds)
|
||||
hir::ItemKind::TraitAlias(ident, generics, bounds)
|
||||
}
|
||||
ItemKind::MacroDef(MacroDef { body, macro_rules }) => {
|
||||
ItemKind::MacroDef(ident, MacroDef { body, macro_rules }) => {
|
||||
let ident = self.lower_ident(*ident);
|
||||
let body = P(self.lower_delim_args(body));
|
||||
let def_id = self.local_def_id(id);
|
||||
let def_kind = self.tcx.def_kind(def_id);
|
||||
@ -444,11 +474,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
);
|
||||
};
|
||||
let macro_def = self.arena.alloc(ast::MacroDef { body, macro_rules: *macro_rules });
|
||||
hir::ItemKind::Macro(macro_def, macro_kind)
|
||||
hir::ItemKind::Macro(ident, macro_def, macro_kind)
|
||||
}
|
||||
ItemKind::Delegation(box delegation) => {
|
||||
let delegation_results = self.lower_delegation(delegation, id);
|
||||
let delegation_results = self.lower_delegation(delegation, id, false);
|
||||
hir::ItemKind::Fn {
|
||||
ident: delegation_results.ident,
|
||||
sig: delegation_results.sig,
|
||||
generics: delegation_results.generics,
|
||||
body: delegation_results.body_id,
|
||||
@ -479,7 +510,6 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
prefix: &Path,
|
||||
id: NodeId,
|
||||
vis_span: Span,
|
||||
ident: &mut Ident,
|
||||
attrs: &'hir [hir::Attribute],
|
||||
) -> hir::ItemKind<'hir> {
|
||||
let path = &tree.prefix;
|
||||
@ -487,7 +517,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
|
||||
match tree.kind {
|
||||
UseTreeKind::Simple(rename) => {
|
||||
*ident = tree.ident();
|
||||
let mut ident = tree.ident();
|
||||
|
||||
// First, apply the prefix to the path.
|
||||
let mut path = Path { segments, span: path.span, tokens: None };
|
||||
@ -498,13 +528,14 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
{
|
||||
let _ = path.segments.pop();
|
||||
if rename.is_none() {
|
||||
*ident = path.segments.last().unwrap().ident;
|
||||
ident = path.segments.last().unwrap().ident;
|
||||
}
|
||||
}
|
||||
|
||||
let res = self.lower_import_res(id, path.span);
|
||||
let path = self.lower_use_path(res, &path, ParamMode::Explicit);
|
||||
hir::ItemKind::Use(path, hir::UseKind::Single)
|
||||
let ident = self.lower_ident(ident);
|
||||
hir::ItemKind::Use(path, hir::UseKind::Single(ident))
|
||||
}
|
||||
UseTreeKind::Glob => {
|
||||
let res = self.expect_full_res(id);
|
||||
@ -543,7 +574,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
|
||||
// Add all the nested `PathListItem`s to the HIR.
|
||||
for &(ref use_tree, id) in trees {
|
||||
let new_hir_id = self.local_def_id(id);
|
||||
let owner_id = self.owner_id(id);
|
||||
|
||||
// Each `use` import is an item and thus are owners of the
|
||||
// names in the path. Up to this point the nested import is
|
||||
@ -551,20 +582,16 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
// own its own names, we have to adjust the owner before
|
||||
// lowering the rest of the import.
|
||||
self.with_hir_id_owner(id, |this| {
|
||||
let mut ident = *ident;
|
||||
|
||||
// `prefix` is lowered multiple times, but in different HIR owners.
|
||||
// So each segment gets renewed `HirId` with the same
|
||||
// `ItemLocalId` and the new owner. (See `lower_node_id`)
|
||||
let kind =
|
||||
this.lower_use_tree(use_tree, &prefix, id, vis_span, &mut ident, attrs);
|
||||
let kind = this.lower_use_tree(use_tree, &prefix, id, vis_span, attrs);
|
||||
if !attrs.is_empty() {
|
||||
this.attrs.insert(hir::ItemLocalId::ZERO, attrs);
|
||||
}
|
||||
|
||||
let item = hir::Item {
|
||||
owner_id: hir::OwnerId { def_id: new_hir_id },
|
||||
ident: this.lower_ident(ident),
|
||||
owner_id,
|
||||
kind,
|
||||
vis_span,
|
||||
span: this.lower_span(use_tree.span),
|
||||
@ -593,29 +620,15 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
}
|
||||
}
|
||||
|
||||
fn lower_assoc_item(
|
||||
&mut self,
|
||||
item: &AssocItem,
|
||||
ctxt: AssocCtxt,
|
||||
parent_hir: &'hir hir::OwnerInfo<'hir>,
|
||||
) -> hir::OwnerNode<'hir> {
|
||||
let parent_item = parent_hir.node().expect_item();
|
||||
match parent_item.kind {
|
||||
hir::ItemKind::Impl(impl_) => {
|
||||
self.is_in_trait_impl = impl_.of_trait.is_some();
|
||||
}
|
||||
hir::ItemKind::Trait(_, _, _, _, _) => {}
|
||||
kind => {
|
||||
span_bug!(item.span, "assoc item has unexpected kind of parent: {}", kind.descr())
|
||||
}
|
||||
}
|
||||
|
||||
fn lower_assoc_item(&mut self, item: &AssocItem, ctxt: AssocCtxt) -> hir::OwnerNode<'hir> {
|
||||
// Evaluate with the lifetimes in `params` in-scope.
|
||||
// This is used to track which lifetimes have already been defined,
|
||||
// and which need to be replicated when lowering an async fn.
|
||||
match ctxt {
|
||||
AssocCtxt::Trait => hir::OwnerNode::TraitItem(self.lower_trait_item(item)),
|
||||
AssocCtxt::Impl => hir::OwnerNode::ImplItem(self.lower_impl_item(item)),
|
||||
AssocCtxt::Impl { of_trait } => {
|
||||
hir::OwnerNode::ImplItem(self.lower_impl_item(item, of_trait))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -623,47 +636,64 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
let hir_id = hir::HirId::make_owner(self.current_hir_id_owner.def_id);
|
||||
let owner_id = hir_id.expect_owner();
|
||||
let attrs = self.lower_attrs(hir_id, &i.attrs, i.span);
|
||||
let item = hir::ForeignItem {
|
||||
owner_id,
|
||||
ident: self.lower_ident(i.ident),
|
||||
kind: match &i.kind {
|
||||
ForeignItemKind::Fn(box Fn { sig, generics, .. }) => {
|
||||
let fdec = &sig.decl;
|
||||
let itctx = ImplTraitContext::Universal;
|
||||
let (generics, (decl, fn_args)) =
|
||||
self.lower_generics(generics, i.id, itctx, |this| {
|
||||
(
|
||||
// Disallow `impl Trait` in foreign items.
|
||||
this.lower_fn_decl(
|
||||
fdec,
|
||||
i.id,
|
||||
sig.span,
|
||||
FnDeclKind::ExternFn,
|
||||
None,
|
||||
),
|
||||
this.lower_fn_params_to_names(fdec),
|
||||
)
|
||||
});
|
||||
let (ident, kind) = match &i.kind {
|
||||
ForeignItemKind::Fn(box Fn { sig, ident, generics, define_opaque, .. }) => {
|
||||
let fdec = &sig.decl;
|
||||
let itctx = ImplTraitContext::Universal;
|
||||
let (generics, (decl, fn_args)) =
|
||||
self.lower_generics(generics, i.id, itctx, |this| {
|
||||
(
|
||||
// Disallow `impl Trait` in foreign items.
|
||||
this.lower_fn_decl(fdec, i.id, sig.span, FnDeclKind::ExternFn, None),
|
||||
this.lower_fn_params_to_names(fdec),
|
||||
)
|
||||
});
|
||||
|
||||
// Unmarked safety in unsafe block defaults to unsafe.
|
||||
let header = self.lower_fn_header(sig.header, hir::Safety::Unsafe, attrs);
|
||||
// Unmarked safety in unsafe block defaults to unsafe.
|
||||
let header = self.lower_fn_header(sig.header, hir::Safety::Unsafe, attrs);
|
||||
|
||||
if define_opaque.is_some() {
|
||||
self.dcx().span_err(i.span, "foreign functions cannot define opaque types");
|
||||
}
|
||||
|
||||
(
|
||||
ident,
|
||||
hir::ForeignItemKind::Fn(
|
||||
hir::FnSig { header, decl, span: self.lower_span(sig.span) },
|
||||
fn_args,
|
||||
generics,
|
||||
)
|
||||
}
|
||||
ForeignItemKind::Static(box StaticItem { ty, mutability, expr: _, safety }) => {
|
||||
let ty = self
|
||||
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::StaticTy));
|
||||
let safety = self.lower_safety(*safety, hir::Safety::Unsafe);
|
||||
),
|
||||
)
|
||||
}
|
||||
ForeignItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
mutability,
|
||||
expr: _,
|
||||
safety,
|
||||
define_opaque,
|
||||
}) => {
|
||||
let ty =
|
||||
self.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::StaticTy));
|
||||
let safety = self.lower_safety(*safety, hir::Safety::Unsafe);
|
||||
|
||||
hir::ForeignItemKind::Static(ty, *mutability, safety)
|
||||
// njn: where for this?
|
||||
if define_opaque.is_some() {
|
||||
self.dcx().span_err(i.span, "foreign statics cannot define opaque types");
|
||||
}
|
||||
ForeignItemKind::TyAlias(..) => hir::ForeignItemKind::Type,
|
||||
ForeignItemKind::MacCall(_) => panic!("macro shouldn't exist here"),
|
||||
},
|
||||
|
||||
(ident, hir::ForeignItemKind::Static(ty, *mutability, safety))
|
||||
}
|
||||
ForeignItemKind::TyAlias(box TyAlias { ident, .. }) => {
|
||||
(ident, hir::ForeignItemKind::Type)
|
||||
}
|
||||
ForeignItemKind::MacCall(_) => panic!("macro shouldn't exist here"),
|
||||
};
|
||||
|
||||
let item = hir::ForeignItem {
|
||||
owner_id,
|
||||
ident: self.lower_ident(*ident),
|
||||
kind,
|
||||
vis_span: self.lower_span(i.vis.span),
|
||||
span: self.lower_span(i.span),
|
||||
};
|
||||
@ -672,8 +702,10 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
|
||||
fn lower_foreign_item_ref(&mut self, i: &ForeignItem) -> hir::ForeignItemRef {
|
||||
hir::ForeignItemRef {
|
||||
id: hir::ForeignItemId { owner_id: hir::OwnerId { def_id: self.local_def_id(i.id) } },
|
||||
ident: self.lower_ident(i.ident),
|
||||
id: hir::ForeignItemId { owner_id: self.owner_id(i.id) },
|
||||
// `unwrap` is safe because `ForeignItemKind::MacCall` is the only foreign item kind
|
||||
// without an identifier and it cannot reach here.
|
||||
ident: self.lower_ident(i.kind.ident().unwrap()),
|
||||
span: self.lower_span(i.span),
|
||||
}
|
||||
}
|
||||
@ -764,8 +796,15 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
let attrs = self.lower_attrs(hir_id, &i.attrs, i.span);
|
||||
let trait_item_def_id = hir_id.expect_owner();
|
||||
|
||||
let (generics, kind, has_default) = match &i.kind {
|
||||
AssocItemKind::Const(box ConstItem { generics, ty, expr, .. }) => {
|
||||
let (ident, generics, kind, has_default) = match &i.kind {
|
||||
AssocItemKind::Const(box ConstItem {
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
..
|
||||
}) => {
|
||||
let (generics, kind) = self.lower_generics(
|
||||
generics,
|
||||
i.id,
|
||||
@ -778,9 +817,23 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
hir::TraitItemKind::Const(ty, body)
|
||||
},
|
||||
);
|
||||
(generics, kind, expr.is_some())
|
||||
|
||||
if define_opaque.is_some() {
|
||||
if expr.is_some() {
|
||||
self.lower_define_opaque(hir_id, &define_opaque);
|
||||
} else {
|
||||
self.dcx().span_err(
|
||||
i.span,
|
||||
"only trait consts with default bodies can define opaque types",
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
(*ident, generics, kind, expr.is_some())
|
||||
}
|
||||
AssocItemKind::Fn(box Fn { sig, generics, body: None, define_opaque, .. }) => {
|
||||
AssocItemKind::Fn(box Fn {
|
||||
sig, ident, generics, body: None, define_opaque, ..
|
||||
}) => {
|
||||
// FIXME(contracts): Deny contract here since it won't apply to
|
||||
// any impl method or callees.
|
||||
let names = self.lower_fn_params_to_names(&sig.decl);
|
||||
@ -798,10 +851,16 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
"only trait methods with default bodies can define opaque types",
|
||||
);
|
||||
}
|
||||
(generics, hir::TraitItemKind::Fn(sig, hir::TraitFn::Required(names)), false)
|
||||
(
|
||||
*ident,
|
||||
generics,
|
||||
hir::TraitItemKind::Fn(sig, hir::TraitFn::Required(names)),
|
||||
false,
|
||||
)
|
||||
}
|
||||
AssocItemKind::Fn(box Fn {
|
||||
sig,
|
||||
ident,
|
||||
generics,
|
||||
body: Some(body),
|
||||
contract,
|
||||
@ -827,9 +886,16 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
attrs,
|
||||
);
|
||||
self.lower_define_opaque(hir_id, &define_opaque);
|
||||
(generics, hir::TraitItemKind::Fn(sig, hir::TraitFn::Provided(body_id)), true)
|
||||
(
|
||||
*ident,
|
||||
generics,
|
||||
hir::TraitItemKind::Fn(sig, hir::TraitFn::Provided(body_id)),
|
||||
true,
|
||||
)
|
||||
}
|
||||
AssocItemKind::Type(box TyAlias { generics, where_clauses, bounds, ty, .. }) => {
|
||||
AssocItemKind::Type(box TyAlias {
|
||||
ident, generics, where_clauses, bounds, ty, ..
|
||||
}) => {
|
||||
let mut generics = generics.clone();
|
||||
add_ty_alias_where_clause(&mut generics, *where_clauses, false);
|
||||
let (generics, kind) = self.lower_generics(
|
||||
@ -852,15 +918,15 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
)
|
||||
},
|
||||
);
|
||||
(generics, kind, ty.is_some())
|
||||
(*ident, generics, kind, ty.is_some())
|
||||
}
|
||||
AssocItemKind::Delegation(box delegation) => {
|
||||
let delegation_results = self.lower_delegation(delegation, i.id);
|
||||
let delegation_results = self.lower_delegation(delegation, i.id, false);
|
||||
let item_kind = hir::TraitItemKind::Fn(
|
||||
delegation_results.sig,
|
||||
hir::TraitFn::Provided(delegation_results.body_id),
|
||||
);
|
||||
(delegation_results.generics, item_kind, true)
|
||||
(delegation.ident, delegation_results.generics, item_kind, true)
|
||||
}
|
||||
AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
|
||||
panic!("macros should have been expanded by now")
|
||||
@ -869,7 +935,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
|
||||
let item = hir::TraitItem {
|
||||
owner_id: trait_item_def_id,
|
||||
ident: self.lower_ident(i.ident),
|
||||
ident: self.lower_ident(ident),
|
||||
generics,
|
||||
kind,
|
||||
span: self.lower_span(i.span),
|
||||
@ -879,23 +945,28 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
}
|
||||
|
||||
fn lower_trait_item_ref(&mut self, i: &AssocItem) -> hir::TraitItemRef {
|
||||
let kind = match &i.kind {
|
||||
AssocItemKind::Const(..) => hir::AssocItemKind::Const,
|
||||
AssocItemKind::Type(..) => hir::AssocItemKind::Type,
|
||||
AssocItemKind::Fn(box Fn { sig, .. }) => {
|
||||
hir::AssocItemKind::Fn { has_self: sig.decl.has_self() }
|
||||
let (ident, kind) = match &i.kind {
|
||||
AssocItemKind::Const(box ConstItem { ident, .. }) => {
|
||||
(*ident, hir::AssocItemKind::Const)
|
||||
}
|
||||
AssocItemKind::Delegation(box delegation) => hir::AssocItemKind::Fn {
|
||||
has_self: self.delegatee_is_method(i.id, delegation.id, i.span),
|
||||
},
|
||||
AssocItemKind::Type(box TyAlias { ident, .. }) => (*ident, hir::AssocItemKind::Type),
|
||||
AssocItemKind::Fn(box Fn { ident, sig, .. }) => {
|
||||
(*ident, hir::AssocItemKind::Fn { has_self: sig.decl.has_self() })
|
||||
}
|
||||
AssocItemKind::Delegation(box delegation) => (
|
||||
delegation.ident,
|
||||
hir::AssocItemKind::Fn {
|
||||
has_self: self.delegatee_is_method(i.id, delegation.id, i.span, false),
|
||||
},
|
||||
),
|
||||
AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
|
||||
panic!("macros should have been expanded by now")
|
||||
}
|
||||
};
|
||||
let id = hir::TraitItemId { owner_id: hir::OwnerId { def_id: self.local_def_id(i.id) } };
|
||||
let id = hir::TraitItemId { owner_id: self.owner_id(i.id) };
|
||||
hir::TraitItemRef {
|
||||
id,
|
||||
ident: self.lower_ident(i.ident),
|
||||
ident: self.lower_ident(ident),
|
||||
span: self.lower_span(i.span),
|
||||
kind,
|
||||
}
|
||||
@ -906,27 +977,49 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
self.expr(span, hir::ExprKind::Err(guar))
|
||||
}
|
||||
|
||||
fn lower_impl_item(&mut self, i: &AssocItem) -> &'hir hir::ImplItem<'hir> {
|
||||
fn lower_impl_item(
|
||||
&mut self,
|
||||
i: &AssocItem,
|
||||
is_in_trait_impl: bool,
|
||||
) -> &'hir hir::ImplItem<'hir> {
|
||||
// Since `default impl` is not yet implemented, this is always true in impls.
|
||||
let has_value = true;
|
||||
let (defaultness, _) = self.lower_defaultness(i.kind.defaultness(), has_value);
|
||||
let hir_id = hir::HirId::make_owner(self.current_hir_id_owner.def_id);
|
||||
let attrs = self.lower_attrs(hir_id, &i.attrs, i.span);
|
||||
|
||||
let (generics, kind) = match &i.kind {
|
||||
AssocItemKind::Const(box ConstItem { generics, ty, expr, .. }) => self.lower_generics(
|
||||
let (ident, (generics, kind)) = match &i.kind {
|
||||
AssocItemKind::Const(box ConstItem {
|
||||
ident,
|
||||
generics,
|
||||
i.id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| {
|
||||
let ty =
|
||||
this.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
|
||||
let body = this.lower_const_body(i.span, expr.as_deref());
|
||||
|
||||
hir::ImplItemKind::Const(ty, body)
|
||||
},
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
..
|
||||
}) => (
|
||||
*ident,
|
||||
self.lower_generics(
|
||||
generics,
|
||||
i.id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| {
|
||||
let ty = this
|
||||
.lower_ty(ty, ImplTraitContext::Disallowed(ImplTraitPosition::ConstTy));
|
||||
let body = this.lower_const_body(i.span, expr.as_deref());
|
||||
this.lower_define_opaque(hir_id, &define_opaque);
|
||||
hir::ImplItemKind::Const(ty, body)
|
||||
},
|
||||
),
|
||||
),
|
||||
AssocItemKind::Fn(box Fn { sig, generics, body, contract, define_opaque, .. }) => {
|
||||
AssocItemKind::Fn(box Fn {
|
||||
sig,
|
||||
ident,
|
||||
generics,
|
||||
body,
|
||||
contract,
|
||||
define_opaque,
|
||||
..
|
||||
}) => {
|
||||
let body_id = self.lower_maybe_coroutine_body(
|
||||
sig.span,
|
||||
i.span,
|
||||
@ -941,50 +1034,56 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
generics,
|
||||
sig,
|
||||
i.id,
|
||||
if self.is_in_trait_impl { FnDeclKind::Impl } else { FnDeclKind::Inherent },
|
||||
if is_in_trait_impl { FnDeclKind::Impl } else { FnDeclKind::Inherent },
|
||||
sig.header.coroutine_kind,
|
||||
attrs,
|
||||
);
|
||||
self.lower_define_opaque(hir_id, &define_opaque);
|
||||
|
||||
(generics, hir::ImplItemKind::Fn(sig, body_id))
|
||||
(*ident, (generics, hir::ImplItemKind::Fn(sig, body_id)))
|
||||
}
|
||||
AssocItemKind::Type(box TyAlias { generics, where_clauses, ty, .. }) => {
|
||||
AssocItemKind::Type(box TyAlias { ident, generics, where_clauses, ty, .. }) => {
|
||||
let mut generics = generics.clone();
|
||||
add_ty_alias_where_clause(&mut generics, *where_clauses, false);
|
||||
self.lower_generics(
|
||||
&generics,
|
||||
i.id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| match ty {
|
||||
None => {
|
||||
let guar = this.dcx().span_delayed_bug(
|
||||
i.span,
|
||||
"expected to lower associated type, but it was missing",
|
||||
);
|
||||
let ty = this.arena.alloc(this.ty(i.span, hir::TyKind::Err(guar)));
|
||||
hir::ImplItemKind::Type(ty)
|
||||
}
|
||||
Some(ty) => {
|
||||
let ty = this.lower_ty(
|
||||
ty,
|
||||
ImplTraitContext::OpaqueTy {
|
||||
origin: hir::OpaqueTyOrigin::TyAlias {
|
||||
parent: this.local_def_id(i.id),
|
||||
in_assoc_ty: true,
|
||||
(
|
||||
*ident,
|
||||
self.lower_generics(
|
||||
&generics,
|
||||
i.id,
|
||||
ImplTraitContext::Disallowed(ImplTraitPosition::Generic),
|
||||
|this| match ty {
|
||||
None => {
|
||||
let guar = this.dcx().span_delayed_bug(
|
||||
i.span,
|
||||
"expected to lower associated type, but it was missing",
|
||||
);
|
||||
let ty = this.arena.alloc(this.ty(i.span, hir::TyKind::Err(guar)));
|
||||
hir::ImplItemKind::Type(ty)
|
||||
}
|
||||
Some(ty) => {
|
||||
let ty = this.lower_ty(
|
||||
ty,
|
||||
ImplTraitContext::OpaqueTy {
|
||||
origin: hir::OpaqueTyOrigin::TyAlias {
|
||||
parent: this.local_def_id(i.id),
|
||||
in_assoc_ty: true,
|
||||
},
|
||||
},
|
||||
},
|
||||
);
|
||||
hir::ImplItemKind::Type(ty)
|
||||
}
|
||||
},
|
||||
);
|
||||
hir::ImplItemKind::Type(ty)
|
||||
}
|
||||
},
|
||||
),
|
||||
)
|
||||
}
|
||||
AssocItemKind::Delegation(box delegation) => {
|
||||
let delegation_results = self.lower_delegation(delegation, i.id);
|
||||
let delegation_results = self.lower_delegation(delegation, i.id, is_in_trait_impl);
|
||||
(
|
||||
delegation_results.generics,
|
||||
hir::ImplItemKind::Fn(delegation_results.sig, delegation_results.body_id),
|
||||
delegation.ident,
|
||||
(
|
||||
delegation_results.generics,
|
||||
hir::ImplItemKind::Fn(delegation_results.sig, delegation_results.body_id),
|
||||
),
|
||||
)
|
||||
}
|
||||
AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
|
||||
@ -994,7 +1093,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
|
||||
let item = hir::ImplItem {
|
||||
owner_id: hir_id.expect_owner(),
|
||||
ident: self.lower_ident(i.ident),
|
||||
ident: self.lower_ident(ident),
|
||||
generics,
|
||||
kind,
|
||||
vis_span: self.lower_span(i.vis.span),
|
||||
@ -1004,10 +1103,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
self.arena.alloc(item)
|
||||
}
|
||||
|
||||
fn lower_impl_item_ref(&mut self, i: &AssocItem) -> hir::ImplItemRef {
|
||||
fn lower_impl_item_ref(&mut self, i: &AssocItem, is_in_trait_impl: bool) -> hir::ImplItemRef {
|
||||
hir::ImplItemRef {
|
||||
id: hir::ImplItemId { owner_id: hir::OwnerId { def_id: self.local_def_id(i.id) } },
|
||||
ident: self.lower_ident(i.ident),
|
||||
id: hir::ImplItemId { owner_id: self.owner_id(i.id) },
|
||||
// `unwrap` is safe because `AssocItemKind::{MacCall,DelegationMac}` are the only
|
||||
// assoc item kinds without an identifier and they cannot reach here.
|
||||
ident: self.lower_ident(i.kind.ident().unwrap()),
|
||||
span: self.lower_span(i.span),
|
||||
kind: match &i.kind {
|
||||
AssocItemKind::Const(..) => hir::AssocItemKind::Const,
|
||||
@ -1016,7 +1117,12 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
hir::AssocItemKind::Fn { has_self: sig.decl.has_self() }
|
||||
}
|
||||
AssocItemKind::Delegation(box delegation) => hir::AssocItemKind::Fn {
|
||||
has_self: self.delegatee_is_method(i.id, delegation.id, i.span),
|
||||
has_self: self.delegatee_is_method(
|
||||
i.id,
|
||||
delegation.id,
|
||||
i.span,
|
||||
is_in_trait_impl,
|
||||
),
|
||||
},
|
||||
AssocItemKind::MacCall(..) | AssocItemKind::DelegationMac(..) => {
|
||||
panic!("macros should have been expanded by now")
|
||||
@ -1684,8 +1790,8 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
return;
|
||||
};
|
||||
let define_opaque = define_opaque.iter().filter_map(|(id, path)| {
|
||||
let res = self.resolver.get_partial_res(*id).unwrap();
|
||||
let Some(did) = res.expect_full_res().opt_def_id() else {
|
||||
let res = self.resolver.get_partial_res(*id);
|
||||
let Some(did) = res.and_then(|res| res.expect_full_res().opt_def_id()) else {
|
||||
self.dcx().span_delayed_bug(path.span, "should have errored in resolve");
|
||||
return None;
|
||||
};
|
||||
@ -1758,7 +1864,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
||||
}
|
||||
GenericParamKind::Lifetime => {
|
||||
let lt_id = self.next_node_id();
|
||||
let lifetime = self.new_named_lifetime(id, lt_id, ident);
|
||||
let lifetime = self.new_named_lifetime(id, lt_id, ident, IsAnonInPath::No);
|
||||
hir::WherePredicateKind::RegionPredicate(hir::WhereRegionPredicate {
|
||||
lifetime,
|
||||
bounds,
|
||||
|
@ -55,7 +55,8 @@ 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::{
|
||||
self as hir, ConstArg, GenericArg, HirId, ItemLocalMap, LangItem, ParamName, TraitCandidate,
|
||||
self as hir, ConstArg, GenericArg, HirId, IsAnonInPath, ItemLocalMap, LangItem, ParamName,
|
||||
TraitCandidate,
|
||||
};
|
||||
use rustc_index::{Idx, IndexSlice, IndexVec};
|
||||
use rustc_macros::extension;
|
||||
@ -121,7 +122,6 @@ struct LoweringContext<'a, 'hir> {
|
||||
catch_scope: Option<HirId>,
|
||||
loop_scope: Option<HirId>,
|
||||
is_in_loop_condition: bool,
|
||||
is_in_trait_impl: bool,
|
||||
is_in_dyn_type: bool,
|
||||
|
||||
current_hir_id_owner: hir::OwnerId,
|
||||
@ -173,7 +173,6 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
catch_scope: None,
|
||||
loop_scope: None,
|
||||
is_in_loop_condition: false,
|
||||
is_in_trait_impl: false,
|
||||
is_in_dyn_type: false,
|
||||
coroutine_kind: None,
|
||||
task_context: None,
|
||||
@ -536,6 +535,11 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
self.opt_local_def_id(node).unwrap_or_else(|| panic!("no entry for node id: `{node:?}`"))
|
||||
}
|
||||
|
||||
/// Given the id of an owner node in the AST, returns the corresponding `OwnerId`.
|
||||
fn owner_id(&self, node: NodeId) -> hir::OwnerId {
|
||||
hir::OwnerId { def_id: self.local_def_id(node) }
|
||||
}
|
||||
|
||||
/// Freshen the `LoweringContext` and ready it to lower a nested item.
|
||||
/// The lowered item is registered into `self.children`.
|
||||
///
|
||||
@ -547,7 +551,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
owner: NodeId,
|
||||
f: impl FnOnce(&mut Self) -> hir::OwnerNode<'hir>,
|
||||
) {
|
||||
let def_id = self.local_def_id(owner);
|
||||
let owner_id = self.owner_id(owner);
|
||||
|
||||
let current_attrs = std::mem::take(&mut self.attrs);
|
||||
let current_bodies = std::mem::take(&mut self.bodies);
|
||||
@ -558,8 +562,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
#[cfg(debug_assertions)]
|
||||
let current_node_id_to_local_id = std::mem::take(&mut self.node_id_to_local_id);
|
||||
let current_trait_map = std::mem::take(&mut self.trait_map);
|
||||
let current_owner =
|
||||
std::mem::replace(&mut self.current_hir_id_owner, hir::OwnerId { def_id });
|
||||
let current_owner = std::mem::replace(&mut self.current_hir_id_owner, owner_id);
|
||||
let current_local_counter =
|
||||
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);
|
||||
@ -577,7 +580,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
}
|
||||
|
||||
let item = f(self);
|
||||
debug_assert_eq!(def_id, item.def_id().def_id);
|
||||
debug_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());
|
||||
@ -598,8 +601,8 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
self.impl_trait_defs = current_impl_trait_defs;
|
||||
self.impl_trait_bounds = current_impl_trait_bounds;
|
||||
|
||||
debug_assert!(!self.children.iter().any(|(id, _)| id == &def_id));
|
||||
self.children.push((def_id, hir::MaybeOwner::Owner(info)));
|
||||
debug_assert!(!self.children.iter().any(|(id, _)| id == &owner_id.def_id));
|
||||
self.children.push((owner_id.def_id, hir::MaybeOwner::Owner(info)));
|
||||
}
|
||||
|
||||
fn make_owner_info(&mut self, node: hir::OwnerNode<'hir>) -> &'hir hir::OwnerInfo<'hir> {
|
||||
@ -621,7 +624,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
|
||||
// Don't hash unless necessary, because it's expensive.
|
||||
let (opt_hash_including_bodies, attrs_hash) =
|
||||
self.tcx.hash_owner_nodes(node, &bodies, &attrs);
|
||||
self.tcx.hash_owner_nodes(node, &bodies, &attrs, 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 };
|
||||
@ -1438,28 +1441,6 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
// frequently opened issues show.
|
||||
let opaque_ty_span = self.mark_span_with_reason(DesugaringKind::OpaqueTy, span, None);
|
||||
|
||||
// Feature gate for RPITIT + use<..>
|
||||
match origin {
|
||||
rustc_hir::OpaqueTyOrigin::FnReturn { in_trait_or_impl: Some(_), .. } => {
|
||||
if !self.tcx.features().precise_capturing_in_traits()
|
||||
&& let Some(span) = bounds.iter().find_map(|bound| match *bound {
|
||||
ast::GenericBound::Use(_, span) => Some(span),
|
||||
_ => None,
|
||||
})
|
||||
{
|
||||
let mut diag =
|
||||
self.tcx.dcx().create_err(errors::NoPreciseCapturesOnRpitit { span });
|
||||
add_feature_diagnostics(
|
||||
&mut diag,
|
||||
self.tcx.sess,
|
||||
sym::precise_capturing_in_traits,
|
||||
);
|
||||
diag.emit();
|
||||
}
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
|
||||
self.lower_opaque_inner(opaque_ty_node_id, origin, opaque_ty_span, |this| {
|
||||
this.lower_param_bounds(bounds, itctx)
|
||||
})
|
||||
@ -1513,16 +1494,22 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
}))
|
||||
}
|
||||
|
||||
fn lower_fn_params_to_names(&mut self, decl: &FnDecl) -> &'hir [Ident] {
|
||||
fn lower_fn_params_to_names(&mut self, decl: &FnDecl) -> &'hir [Option<Ident>] {
|
||||
self.arena.alloc_from_iter(decl.inputs.iter().map(|param| match param.pat.kind {
|
||||
PatKind::Ident(_, ident, _) => self.lower_ident(ident),
|
||||
PatKind::Wild => Ident::new(kw::Underscore, self.lower_span(param.pat.span)),
|
||||
PatKind::Ident(_, ident, _) => {
|
||||
if ident.name != kw::Empty {
|
||||
Some(self.lower_ident(ident))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
PatKind::Wild => Some(Ident::new(kw::Underscore, self.lower_span(param.pat.span))),
|
||||
_ => {
|
||||
self.dcx().span_delayed_bug(
|
||||
param.pat.span,
|
||||
"non-ident/wild param pat must trigger an error",
|
||||
);
|
||||
Ident::new(kw::Empty, self.lower_span(param.pat.span))
|
||||
None
|
||||
}
|
||||
}))
|
||||
}
|
||||
@ -1769,7 +1756,11 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
}
|
||||
|
||||
fn lower_lifetime(&mut self, l: &Lifetime) -> &'hir hir::Lifetime {
|
||||
self.new_named_lifetime(l.id, l.id, l.ident)
|
||||
self.new_named_lifetime(l.id, l.id, l.ident, IsAnonInPath::No)
|
||||
}
|
||||
|
||||
fn lower_lifetime_anon_in_path(&mut self, id: NodeId, span: Span) -> &'hir hir::Lifetime {
|
||||
self.new_named_lifetime(id, id, Ident::new(kw::UnderscoreLifetime, span), IsAnonInPath::Yes)
|
||||
}
|
||||
|
||||
#[instrument(level = "debug", skip(self))]
|
||||
@ -1778,28 +1769,43 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
id: NodeId,
|
||||
new_id: NodeId,
|
||||
ident: Ident,
|
||||
is_anon_in_path: IsAnonInPath,
|
||||
) -> &'hir hir::Lifetime {
|
||||
debug_assert_ne!(ident.name, kw::Empty);
|
||||
let res = self.resolver.get_lifetime_res(id).unwrap_or(LifetimeRes::Error);
|
||||
let res = match res {
|
||||
LifetimeRes::Param { param, .. } => hir::LifetimeName::Param(param),
|
||||
LifetimeRes::Fresh { param, .. } => {
|
||||
debug_assert_eq!(ident.name, kw::UnderscoreLifetime);
|
||||
let param = self.local_def_id(param);
|
||||
hir::LifetimeName::Param(param)
|
||||
}
|
||||
LifetimeRes::Infer => hir::LifetimeName::Infer,
|
||||
LifetimeRes::Static { .. } => hir::LifetimeName::Static,
|
||||
LifetimeRes::Infer => {
|
||||
debug_assert_eq!(ident.name, kw::UnderscoreLifetime);
|
||||
hir::LifetimeName::Infer
|
||||
}
|
||||
LifetimeRes::Static { .. } => {
|
||||
debug_assert!(matches!(ident.name, kw::StaticLifetime | kw::UnderscoreLifetime));
|
||||
hir::LifetimeName::Static
|
||||
}
|
||||
LifetimeRes::Error => hir::LifetimeName::Error,
|
||||
LifetimeRes::ElidedAnchor { .. } => {
|
||||
panic!("Unexpected `ElidedAnchar` {:?} at {:?}", ident, ident.span);
|
||||
}
|
||||
};
|
||||
|
||||
#[cfg(debug_assertions)]
|
||||
if is_anon_in_path == IsAnonInPath::Yes {
|
||||
debug_assert_eq!(ident.name, kw::UnderscoreLifetime);
|
||||
}
|
||||
|
||||
debug!(?res);
|
||||
self.arena.alloc(hir::Lifetime {
|
||||
hir_id: self.lower_node_id(new_id),
|
||||
ident: self.lower_ident(ident),
|
||||
self.arena.alloc(hir::Lifetime::new(
|
||||
self.lower_node_id(new_id),
|
||||
self.lower_ident(ident),
|
||||
res,
|
||||
})
|
||||
is_anon_in_path,
|
||||
))
|
||||
}
|
||||
|
||||
fn lower_generic_params_mut(
|
||||
@ -2383,11 +2389,12 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
/// when the bound is written, even if it is written with `'_` like in
|
||||
/// `Box<dyn Debug + '_>`. In those cases, `lower_lifetime` is invoked.
|
||||
fn elided_dyn_bound(&mut self, span: Span) -> &'hir hir::Lifetime {
|
||||
let r = hir::Lifetime {
|
||||
hir_id: self.next_id(),
|
||||
ident: Ident::new(kw::Empty, self.lower_span(span)),
|
||||
res: hir::LifetimeName::ImplicitObjectLifetimeDefault,
|
||||
};
|
||||
let r = hir::Lifetime::new(
|
||||
self.next_id(),
|
||||
Ident::new(kw::UnderscoreLifetime, self.lower_span(span)),
|
||||
hir::LifetimeName::ImplicitObjectLifetimeDefault,
|
||||
IsAnonInPath::No,
|
||||
);
|
||||
debug!("elided_dyn_bound: r={:?}", r);
|
||||
self.arena.alloc(r)
|
||||
}
|
||||
|
@ -7,7 +7,7 @@ use rustc_hir::def::{DefKind, PartialRes, Res};
|
||||
use rustc_hir::def_id::DefId;
|
||||
use rustc_middle::span_bug;
|
||||
use rustc_session::parse::add_feature_diagnostics;
|
||||
use rustc_span::{BytePos, DUMMY_SP, DesugaringKind, Ident, Span, Symbol, kw, sym};
|
||||
use rustc_span::{BytePos, DUMMY_SP, DesugaringKind, Ident, Span, Symbol, sym};
|
||||
use smallvec::{SmallVec, smallvec};
|
||||
use tracing::{debug, instrument};
|
||||
|
||||
@ -450,10 +450,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
|
||||
0,
|
||||
(start.as_u32()..end.as_u32()).map(|i| {
|
||||
let id = NodeId::from_u32(i);
|
||||
let l = self.lower_lifetime(&Lifetime {
|
||||
id,
|
||||
ident: Ident::new(kw::Empty, elided_lifetime_span),
|
||||
});
|
||||
let l = self.lower_lifetime_anon_in_path(id, elided_lifetime_span);
|
||||
GenericArg::Lifetime(l)
|
||||
}),
|
||||
);
|
||||
|
@ -334,8 +334,8 @@ impl<'a> AstValidator<'a> {
|
||||
.filter(|attr| {
|
||||
let arr = [
|
||||
sym::allow,
|
||||
sym::cfg,
|
||||
sym::cfg_attr,
|
||||
sym::cfg_trace,
|
||||
sym::cfg_attr_trace,
|
||||
sym::deny,
|
||||
sym::expect,
|
||||
sym::forbid,
|
||||
@ -607,7 +607,7 @@ impl<'a> AstValidator<'a> {
|
||||
|
||||
fn deny_items(&self, trait_items: &[P<AssocItem>], ident: Span) {
|
||||
if !trait_items.is_empty() {
|
||||
let spans: Vec<_> = trait_items.iter().map(|i| i.ident.span).collect();
|
||||
let spans: Vec<_> = trait_items.iter().map(|i| i.kind.ident().unwrap().span).collect();
|
||||
let total = trait_items.first().unwrap().span.to(trait_items.last().unwrap().span);
|
||||
self.dcx().emit_err(errors::AutoTraitItems { spans, total, ident });
|
||||
}
|
||||
@ -817,8 +817,10 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
self.has_proc_macro_decls = true;
|
||||
}
|
||||
|
||||
if attr::contains_name(&item.attrs, sym::no_mangle) {
|
||||
self.check_nomangle_item_asciionly(item.ident, item.span);
|
||||
if let Some(ident) = item.kind.ident()
|
||||
&& attr::contains_name(&item.attrs, sym::no_mangle)
|
||||
{
|
||||
self.check_nomangle_item_asciionly(ident, item.span);
|
||||
}
|
||||
|
||||
match &item.kind {
|
||||
@ -852,14 +854,13 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
|
||||
this.visit_vis(&item.vis);
|
||||
this.visit_ident(&item.ident);
|
||||
let disallowed = matches!(constness, Const::No)
|
||||
.then(|| TildeConstReason::TraitImpl { span: item.span });
|
||||
this.with_tilde_const(disallowed, |this| this.visit_generics(generics));
|
||||
this.visit_trait_ref(t);
|
||||
this.visit_ty(self_ty);
|
||||
|
||||
walk_list!(this, visit_assoc_item, items, AssocCtxt::Impl);
|
||||
walk_list!(this, visit_assoc_item, items, AssocCtxt::Impl { of_trait: true });
|
||||
});
|
||||
walk_list!(self, visit_attribute, &item.attrs);
|
||||
return; // Avoid visiting again.
|
||||
@ -906,20 +907,26 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
|
||||
this.visit_vis(&item.vis);
|
||||
this.visit_ident(&item.ident);
|
||||
this.with_tilde_const(
|
||||
Some(TildeConstReason::Impl { span: item.span }),
|
||||
|this| this.visit_generics(generics),
|
||||
);
|
||||
this.visit_ty(self_ty);
|
||||
walk_list!(this, visit_assoc_item, items, AssocCtxt::Impl);
|
||||
walk_list!(this, visit_assoc_item, items, AssocCtxt::Impl { of_trait: false });
|
||||
});
|
||||
walk_list!(self, visit_attribute, &item.attrs);
|
||||
return; // Avoid visiting again.
|
||||
}
|
||||
ItemKind::Fn(
|
||||
func
|
||||
@ box Fn { defaultness, generics: _, sig, contract: _, body, define_opaque: _ },
|
||||
func @ box Fn {
|
||||
defaultness,
|
||||
ident,
|
||||
generics: _,
|
||||
sig,
|
||||
contract: _,
|
||||
body,
|
||||
define_opaque: _,
|
||||
},
|
||||
) => {
|
||||
self.check_defaultness(item.span, *defaultness);
|
||||
|
||||
@ -949,8 +956,8 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
|
||||
self.visit_vis(&item.vis);
|
||||
self.visit_ident(&item.ident);
|
||||
let kind = FnKind::Fn(FnCtxt::Free, &item.ident, &item.vis, &*func);
|
||||
self.visit_ident(ident);
|
||||
let kind = FnKind::Fn(FnCtxt::Free, &item.vis, &*func);
|
||||
self.visit_fn(kind, item.span, item.id);
|
||||
walk_list!(self, visit_attribute, &item.attrs);
|
||||
return; // Avoid visiting again.
|
||||
@ -986,7 +993,7 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
});
|
||||
return; // Avoid visiting again.
|
||||
}
|
||||
ItemKind::Enum(def, _) => {
|
||||
ItemKind::Enum(_, def, _) => {
|
||||
for variant in &def.variants {
|
||||
self.visibility_not_permitted(
|
||||
&variant.vis,
|
||||
@ -1000,22 +1007,22 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
}
|
||||
}
|
||||
ItemKind::Trait(box Trait { is_auto, generics, bounds, items, .. }) => {
|
||||
ItemKind::Trait(box Trait { is_auto, generics, ident, bounds, items, .. }) => {
|
||||
let is_const_trait =
|
||||
attr::find_by_name(&item.attrs, sym::const_trait).map(|attr| attr.span);
|
||||
self.with_in_trait(item.span, is_const_trait, |this| {
|
||||
if *is_auto == IsAuto::Yes {
|
||||
// Auto traits cannot have generics, super traits nor contain items.
|
||||
this.deny_generic_params(generics, item.ident.span);
|
||||
this.deny_super_traits(bounds, item.ident.span);
|
||||
this.deny_where_clause(&generics.where_clause, item.ident.span);
|
||||
this.deny_items(items, item.ident.span);
|
||||
this.deny_generic_params(generics, ident.span);
|
||||
this.deny_super_traits(bounds, ident.span);
|
||||
this.deny_where_clause(&generics.where_clause, ident.span);
|
||||
this.deny_items(items, ident.span);
|
||||
}
|
||||
|
||||
// Equivalent of `visit::walk_item` for `ItemKind::Trait` that inserts a bound
|
||||
// context for the supertraits.
|
||||
this.visit_vis(&item.vis);
|
||||
this.visit_ident(&item.ident);
|
||||
this.visit_ident(ident);
|
||||
let disallowed = is_const_trait
|
||||
.is_none()
|
||||
.then(|| TildeConstReason::Trait { span: item.span });
|
||||
@ -1028,7 +1035,7 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
walk_list!(self, visit_attribute, &item.attrs);
|
||||
return; // Avoid visiting again
|
||||
}
|
||||
ItemKind::Mod(safety, mod_kind) => {
|
||||
ItemKind::Mod(safety, ident, mod_kind) => {
|
||||
if let &Safety::Unsafe(span) = safety {
|
||||
self.dcx().emit_err(errors::UnsafeItem { span, kind: "module" });
|
||||
}
|
||||
@ -1036,13 +1043,13 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
if !matches!(mod_kind, ModKind::Loaded(_, Inline::Yes, _, _))
|
||||
&& !attr::contains_name(&item.attrs, sym::path)
|
||||
{
|
||||
self.check_mod_file_item_asciionly(item.ident);
|
||||
self.check_mod_file_item_asciionly(*ident);
|
||||
}
|
||||
}
|
||||
ItemKind::Struct(vdata, generics) => match vdata {
|
||||
ItemKind::Struct(ident, vdata, generics) => match vdata {
|
||||
VariantData::Struct { fields, .. } => {
|
||||
self.visit_vis(&item.vis);
|
||||
self.visit_ident(&item.ident);
|
||||
self.visit_ident(ident);
|
||||
self.visit_generics(generics);
|
||||
// Permit `Anon{Struct,Union}` as field type.
|
||||
walk_list!(self, visit_struct_field_def, fields);
|
||||
@ -1051,14 +1058,14 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
_ => {}
|
||||
},
|
||||
ItemKind::Union(vdata, generics) => {
|
||||
ItemKind::Union(ident, vdata, generics) => {
|
||||
if vdata.fields().is_empty() {
|
||||
self.dcx().emit_err(errors::FieldlessUnion { span: item.span });
|
||||
}
|
||||
match vdata {
|
||||
VariantData::Struct { fields, .. } => {
|
||||
self.visit_vis(&item.vis);
|
||||
self.visit_ident(&item.ident);
|
||||
self.visit_ident(ident);
|
||||
self.visit_generics(generics);
|
||||
// Permit `Anon{Struct,Union}` as field type.
|
||||
walk_list!(self, visit_struct_field_def, fields);
|
||||
@ -1121,14 +1128,15 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
|
||||
fn visit_foreign_item(&mut self, fi: &'a ForeignItem) {
|
||||
match &fi.kind {
|
||||
ForeignItemKind::Fn(box Fn { defaultness, sig, body, .. }) => {
|
||||
ForeignItemKind::Fn(box Fn { defaultness, ident, sig, body, .. }) => {
|
||||
self.check_defaultness(fi.span, *defaultness);
|
||||
self.check_foreign_fn_bodyless(fi.ident, body.as_deref());
|
||||
self.check_foreign_fn_bodyless(*ident, body.as_deref());
|
||||
self.check_foreign_fn_headerless(sig.header);
|
||||
self.check_foreign_item_ascii_only(fi.ident);
|
||||
self.check_foreign_item_ascii_only(*ident);
|
||||
}
|
||||
ForeignItemKind::TyAlias(box TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
@ -1136,15 +1144,15 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
..
|
||||
}) => {
|
||||
self.check_defaultness(fi.span, *defaultness);
|
||||
self.check_foreign_kind_bodyless(fi.ident, "type", ty.as_ref().map(|b| b.span));
|
||||
self.check_foreign_kind_bodyless(*ident, "type", ty.as_ref().map(|b| b.span));
|
||||
self.check_type_no_bounds(bounds, "`extern` blocks");
|
||||
self.check_foreign_ty_genericless(generics, where_clauses);
|
||||
self.check_foreign_item_ascii_only(fi.ident);
|
||||
self.check_foreign_item_ascii_only(*ident);
|
||||
}
|
||||
ForeignItemKind::Static(box StaticItem { expr, safety, .. }) => {
|
||||
ForeignItemKind::Static(box StaticItem { ident, safety, expr, .. }) => {
|
||||
self.check_item_safety(fi.span, *safety);
|
||||
self.check_foreign_kind_bodyless(fi.ident, "static", expr.as_ref().map(|b| b.span));
|
||||
self.check_foreign_item_ascii_only(fi.ident);
|
||||
self.check_foreign_kind_bodyless(*ident, "static", expr.as_ref().map(|b| b.span));
|
||||
self.check_foreign_item_ascii_only(*ident);
|
||||
}
|
||||
ForeignItemKind::MacCall(..) => {}
|
||||
}
|
||||
@ -1351,7 +1359,6 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
|
||||
if let FnKind::Fn(
|
||||
_,
|
||||
_,
|
||||
_,
|
||||
Fn {
|
||||
@ -1364,7 +1371,7 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
|
||||
// Functions without bodies cannot have patterns.
|
||||
if let FnKind::Fn(ctxt, _, _, Fn { body: None, sig, .. }) = fk {
|
||||
if let FnKind::Fn(ctxt, _, Fn { body: None, sig, .. }) = fk {
|
||||
Self::check_decl_no_pat(&sig.decl, |span, ident, mut_ident| {
|
||||
if mut_ident && matches!(ctxt, FnCtxt::Assoc(_)) {
|
||||
if let Some(ident) = ident {
|
||||
@ -1398,22 +1405,24 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
.is_some();
|
||||
|
||||
let disallowed = (!tilde_const_allowed).then(|| match fk {
|
||||
FnKind::Fn(_, ident, _, _) => TildeConstReason::Function { ident: ident.span },
|
||||
FnKind::Fn(_, _, f) => TildeConstReason::Function { ident: f.ident.span },
|
||||
FnKind::Closure(..) => TildeConstReason::Closure,
|
||||
});
|
||||
self.with_tilde_const(disallowed, |this| visit::walk_fn(this, fk));
|
||||
}
|
||||
|
||||
fn visit_assoc_item(&mut self, item: &'a AssocItem, ctxt: AssocCtxt) {
|
||||
if attr::contains_name(&item.attrs, sym::no_mangle) {
|
||||
self.check_nomangle_item_asciionly(item.ident, item.span);
|
||||
if let Some(ident) = item.kind.ident()
|
||||
&& attr::contains_name(&item.attrs, sym::no_mangle)
|
||||
{
|
||||
self.check_nomangle_item_asciionly(ident, item.span);
|
||||
}
|
||||
|
||||
if ctxt == AssocCtxt::Trait || self.outer_trait_or_trait_impl.is_none() {
|
||||
self.check_defaultness(item.span, item.kind.defaultness());
|
||||
}
|
||||
|
||||
if ctxt == AssocCtxt::Impl {
|
||||
if let AssocCtxt::Impl { .. } = ctxt {
|
||||
match &item.kind {
|
||||
AssocItemKind::Const(box ConstItem { expr: None, .. }) => {
|
||||
self.dcx().emit_err(errors::AssocConstWithoutBody {
|
||||
@ -1466,8 +1475,8 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
if let AssocItemKind::Const(..) = item.kind {
|
||||
self.check_item_named(item.ident, "const");
|
||||
if let AssocItemKind::Const(ci) = &item.kind {
|
||||
self.check_item_named(ci.ident, "const");
|
||||
}
|
||||
|
||||
let parent_is_const =
|
||||
@ -1480,8 +1489,8 @@ impl<'a> Visitor<'a> for AstValidator<'a> {
|
||||
|| matches!(func.sig.header.constness, Const::Yes(_)) =>
|
||||
{
|
||||
self.visit_vis(&item.vis);
|
||||
self.visit_ident(&item.ident);
|
||||
let kind = FnKind::Fn(FnCtxt::Assoc(ctxt), &item.ident, &item.vis, &*func);
|
||||
self.visit_ident(&func.ident);
|
||||
let kind = FnKind::Fn(FnCtxt::Assoc(ctxt), &item.vis, &*func);
|
||||
walk_list!(self, visit_attribute, &item.attrs);
|
||||
self.visit_fn(kind, item.span, item.id);
|
||||
}
|
||||
|
@ -99,6 +99,13 @@ impl<'a> PostExpansionVisitor<'a> {
|
||||
}
|
||||
visit::walk_ty(self, ty);
|
||||
}
|
||||
|
||||
fn visit_anon_const(&mut self, _: &ast::AnonConst) -> Self::Result {
|
||||
// We don't walk the anon const because it crosses a conceptual boundary: We're no
|
||||
// longer "inside" the original type.
|
||||
// Brittle: We assume that the callers of `check_impl_trait` will later recurse into
|
||||
// the items found in the AnonConst to look for nested TyAliases.
|
||||
}
|
||||
}
|
||||
ImplTraitVisitor { vis: self, in_associated_ty }.visit_ty(ty);
|
||||
}
|
||||
@ -229,7 +236,7 @@ impl<'a> Visitor<'a> for PostExpansionVisitor<'a> {
|
||||
gate!(&self, trait_alias, i.span, "trait aliases are experimental");
|
||||
}
|
||||
|
||||
ast::ItemKind::MacroDef(ast::MacroDef { macro_rules: false, .. }) => {
|
||||
ast::ItemKind::MacroDef(_, ast::MacroDef { macro_rules: false, .. }) => {
|
||||
let msg = "`macro` is experimental";
|
||||
gate!(&self, decl_macro, i.span, msg);
|
||||
}
|
||||
@ -483,7 +490,6 @@ pub fn check_crate(krate: &ast::Crate, sess: &Session, features: &Features) {
|
||||
half_open_range_patterns_in_slices,
|
||||
"half-open range patterns in slices are unstable"
|
||||
);
|
||||
gate_all!(inline_const_pat, "inline-const in pattern position is experimental");
|
||||
gate_all!(associated_const_equality, "associated const equality is incomplete");
|
||||
gate_all!(yeet_expr, "`do yeet` expression is experimental");
|
||||
gate_all!(dyn_star, "`dyn*` trait objects are experimental");
|
||||
|
@ -7,8 +7,11 @@ edition = "2024"
|
||||
# tidy-alphabetical-start
|
||||
itertools = "0.12"
|
||||
rustc_ast = { path = "../rustc_ast" }
|
||||
rustc_data_structures = { path = "../rustc_data_structures" }
|
||||
rustc_lexer = { path = "../rustc_lexer" }
|
||||
rustc_span = { path = "../rustc_span" }
|
||||
# tidy-alphabetical-end
|
||||
|
||||
[dev-dependencies]
|
||||
# tidy-alphabetical-start
|
||||
thin-vec = "0.2.12"
|
||||
# tidy-alphabetical-end
|
||||
|
@ -578,11 +578,12 @@ pub trait PrintState<'a>: std::ops::Deref<Target = pp::Printer> + std::ops::Dere
|
||||
let mut printed = false;
|
||||
for attr in attrs {
|
||||
if attr.style == kind {
|
||||
self.print_attribute_inline(attr, is_inline);
|
||||
if is_inline {
|
||||
self.nbsp();
|
||||
if self.print_attribute_inline(attr, is_inline) {
|
||||
if is_inline {
|
||||
self.nbsp();
|
||||
}
|
||||
printed = true;
|
||||
}
|
||||
printed = true;
|
||||
}
|
||||
}
|
||||
if printed && trailing_hardbreak && !is_inline {
|
||||
@ -591,7 +592,12 @@ pub trait PrintState<'a>: std::ops::Deref<Target = pp::Printer> + std::ops::Dere
|
||||
printed
|
||||
}
|
||||
|
||||
fn print_attribute_inline(&mut self, attr: &ast::Attribute, is_inline: bool) {
|
||||
fn print_attribute_inline(&mut self, attr: &ast::Attribute, is_inline: bool) -> bool {
|
||||
if attr.has_name(sym::cfg_trace) || attr.has_name(sym::cfg_attr_trace) {
|
||||
// It's not a valid identifier, so avoid printing it
|
||||
// to keep the printed code reasonably parse-able.
|
||||
return false;
|
||||
}
|
||||
if !is_inline {
|
||||
self.hardbreak_if_not_bol();
|
||||
}
|
||||
@ -610,6 +616,7 @@ pub trait PrintState<'a>: std::ops::Deref<Target = pp::Printer> + std::ops::Dere
|
||||
self.hardbreak()
|
||||
}
|
||||
}
|
||||
true
|
||||
}
|
||||
|
||||
fn print_attr_item(&mut self, item: &ast::AttrItem, span: Span) {
|
||||
@ -2047,7 +2054,7 @@ impl<'a> State<'a> {
|
||||
}
|
||||
|
||||
fn print_attribute(&mut self, attr: &ast::Attribute) {
|
||||
self.print_attribute_inline(attr, false)
|
||||
self.print_attribute_inline(attr, false);
|
||||
}
|
||||
|
||||
fn print_meta_list_item(&mut self, item: &ast::MetaItemInner) {
|
||||
|
@ -8,7 +8,7 @@ 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, token,
|
||||
FormatDebugHex, FormatSign, FormatTrait, YieldKind, token,
|
||||
};
|
||||
|
||||
use crate::pp::Breaks::Inconsistent;
|
||||
@ -761,7 +761,7 @@ impl<'a> State<'a> {
|
||||
self.print_expr(e, FixupContext::default());
|
||||
self.pclose();
|
||||
}
|
||||
ast::ExprKind::Yield(e) => {
|
||||
ast::ExprKind::Yield(YieldKind::Prefix(e)) => {
|
||||
self.word("yield");
|
||||
|
||||
if let Some(expr) = e {
|
||||
@ -773,6 +773,14 @@ impl<'a> State<'a> {
|
||||
);
|
||||
}
|
||||
}
|
||||
ast::ExprKind::Yield(YieldKind::Postfix(e)) => {
|
||||
self.print_expr_cond_paren(
|
||||
e,
|
||||
e.precedence() < ExprPrecedence::Unambiguous,
|
||||
fixup.leftmost_subexpression_with_dot(),
|
||||
);
|
||||
self.word(".yield");
|
||||
}
|
||||
ast::ExprKind::Try(e) => {
|
||||
self.print_expr_cond_paren(
|
||||
e,
|
||||
|
@ -28,36 +28,43 @@ impl<'a> State<'a> {
|
||||
}
|
||||
|
||||
fn print_foreign_item(&mut self, item: &ast::ForeignItem) {
|
||||
let ast::Item { id, span, ident, ref attrs, ref kind, ref vis, tokens: _ } = *item;
|
||||
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();
|
||||
self.maybe_print_comment(span.lo());
|
||||
self.print_outer_attributes(attrs);
|
||||
match kind {
|
||||
ast::ForeignItemKind::Fn(func) => {
|
||||
self.print_fn_full(ident, vis, attrs, &*func);
|
||||
}
|
||||
ast::ForeignItemKind::Static(box ast::StaticItem { ty, mutability, expr, safety }) => {
|
||||
self.print_item_const(
|
||||
ident,
|
||||
Some(*mutability),
|
||||
&ast::Generics::default(),
|
||||
ty,
|
||||
expr.as_deref(),
|
||||
vis,
|
||||
*safety,
|
||||
ast::Defaultness::Final,
|
||||
)
|
||||
self.print_fn_full(vis, attrs, &*func);
|
||||
}
|
||||
ast::ForeignItemKind::Static(box ast::StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
mutability,
|
||||
expr,
|
||||
safety,
|
||||
define_opaque,
|
||||
}) => self.print_item_const(
|
||||
*ident,
|
||||
Some(*mutability),
|
||||
&ast::Generics::default(),
|
||||
ty,
|
||||
expr.as_deref(),
|
||||
vis,
|
||||
*safety,
|
||||
ast::Defaultness::Final,
|
||||
define_opaque.as_deref(),
|
||||
),
|
||||
ast::ForeignItemKind::TyAlias(box ast::TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
self.print_associated_type(
|
||||
ident,
|
||||
*ident,
|
||||
generics,
|
||||
*where_clauses,
|
||||
bounds,
|
||||
@ -86,7 +93,9 @@ impl<'a> State<'a> {
|
||||
vis: &ast::Visibility,
|
||||
safety: ast::Safety,
|
||||
defaultness: ast::Defaultness,
|
||||
define_opaque: Option<&[(ast::NodeId, ast::Path)]>,
|
||||
) {
|
||||
self.print_define_opaques(define_opaque);
|
||||
self.head("");
|
||||
self.print_visibility(vis);
|
||||
self.print_safety(safety);
|
||||
@ -155,7 +164,7 @@ impl<'a> State<'a> {
|
||||
self.print_outer_attributes(&item.attrs);
|
||||
self.ann.pre(self, AnnNode::Item(item));
|
||||
match &item.kind {
|
||||
ast::ItemKind::ExternCrate(orig_name) => {
|
||||
ast::ItemKind::ExternCrate(orig_name, ident) => {
|
||||
self.head(visibility_qualified(&item.vis, "extern crate"));
|
||||
if let &Some(orig_name) = orig_name {
|
||||
self.print_name(orig_name);
|
||||
@ -163,7 +172,7 @@ impl<'a> State<'a> {
|
||||
self.word("as");
|
||||
self.space();
|
||||
}
|
||||
self.print_ident(item.ident);
|
||||
self.print_ident(*ident);
|
||||
self.word(";");
|
||||
self.end(); // end inner head-block
|
||||
self.end(); // end outer head-block
|
||||
@ -174,10 +183,17 @@ impl<'a> State<'a> {
|
||||
self.print_use_tree(tree);
|
||||
self.word(";");
|
||||
}
|
||||
ast::ItemKind::Static(box StaticItem { ty, safety, mutability: mutbl, expr: body }) => {
|
||||
ast::ItemKind::Static(box StaticItem {
|
||||
ident,
|
||||
ty,
|
||||
safety,
|
||||
mutability: mutbl,
|
||||
expr: body,
|
||||
define_opaque,
|
||||
}) => {
|
||||
self.print_safety(*safety);
|
||||
self.print_item_const(
|
||||
item.ident,
|
||||
*ident,
|
||||
Some(*mutbl),
|
||||
&ast::Generics::default(),
|
||||
ty,
|
||||
@ -185,11 +201,19 @@ impl<'a> State<'a> {
|
||||
&item.vis,
|
||||
ast::Safety::Default,
|
||||
ast::Defaultness::Final,
|
||||
define_opaque.as_deref(),
|
||||
);
|
||||
}
|
||||
ast::ItemKind::Const(box ast::ConstItem { defaultness, generics, ty, expr }) => {
|
||||
ast::ItemKind::Const(box ast::ConstItem {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
self.print_item_const(
|
||||
item.ident,
|
||||
*ident,
|
||||
None,
|
||||
generics,
|
||||
ty,
|
||||
@ -197,18 +221,19 @@ impl<'a> State<'a> {
|
||||
&item.vis,
|
||||
ast::Safety::Default,
|
||||
*defaultness,
|
||||
define_opaque.as_deref(),
|
||||
);
|
||||
}
|
||||
ast::ItemKind::Fn(func) => {
|
||||
self.print_fn_full(item.ident, &item.vis, &item.attrs, &*func);
|
||||
self.print_fn_full(&item.vis, &item.attrs, &*func);
|
||||
}
|
||||
ast::ItemKind::Mod(safety, mod_kind) => {
|
||||
ast::ItemKind::Mod(safety, ident, mod_kind) => {
|
||||
self.head(Self::to_string(|s| {
|
||||
s.print_visibility(&item.vis);
|
||||
s.print_safety(*safety);
|
||||
s.word("mod");
|
||||
}));
|
||||
self.print_ident(item.ident);
|
||||
self.print_ident(*ident);
|
||||
|
||||
match mod_kind {
|
||||
ModKind::Loaded(items, ..) => {
|
||||
@ -252,13 +277,14 @@ impl<'a> State<'a> {
|
||||
}
|
||||
ast::ItemKind::TyAlias(box ast::TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
self.print_associated_type(
|
||||
item.ident,
|
||||
*ident,
|
||||
generics,
|
||||
*where_clauses,
|
||||
bounds,
|
||||
@ -267,16 +293,16 @@ impl<'a> State<'a> {
|
||||
*defaultness,
|
||||
);
|
||||
}
|
||||
ast::ItemKind::Enum(enum_definition, params) => {
|
||||
self.print_enum_def(enum_definition, params, item.ident, item.span, &item.vis);
|
||||
ast::ItemKind::Enum(ident, enum_definition, params) => {
|
||||
self.print_enum_def(enum_definition, params, *ident, item.span, &item.vis);
|
||||
}
|
||||
ast::ItemKind::Struct(struct_def, generics) => {
|
||||
ast::ItemKind::Struct(ident, struct_def, generics) => {
|
||||
self.head(visibility_qualified(&item.vis, "struct"));
|
||||
self.print_struct(struct_def, generics, item.ident, item.span, true);
|
||||
self.print_struct(struct_def, generics, *ident, item.span, true);
|
||||
}
|
||||
ast::ItemKind::Union(struct_def, generics) => {
|
||||
ast::ItemKind::Union(ident, struct_def, generics) => {
|
||||
self.head(visibility_qualified(&item.vis, "union"));
|
||||
self.print_struct(struct_def, generics, item.ident, item.span, true);
|
||||
self.print_struct(struct_def, generics, *ident, item.span, true);
|
||||
}
|
||||
ast::ItemKind::Impl(box ast::Impl {
|
||||
safety,
|
||||
@ -326,19 +352,19 @@ impl<'a> State<'a> {
|
||||
self.bclose(item.span, empty);
|
||||
}
|
||||
ast::ItemKind::Trait(box ast::Trait {
|
||||
is_auto,
|
||||
safety,
|
||||
is_auto,
|
||||
ident,
|
||||
generics,
|
||||
bounds,
|
||||
items,
|
||||
..
|
||||
}) => {
|
||||
self.head("");
|
||||
self.print_visibility(&item.vis);
|
||||
self.print_safety(*safety);
|
||||
self.print_is_auto(*is_auto);
|
||||
self.word_nbsp("trait");
|
||||
self.print_ident(item.ident);
|
||||
self.print_ident(*ident);
|
||||
self.print_generic_params(&generics.params);
|
||||
if !bounds.is_empty() {
|
||||
self.word_nbsp(":");
|
||||
@ -354,9 +380,9 @@ impl<'a> State<'a> {
|
||||
let empty = item.attrs.is_empty() && items.is_empty();
|
||||
self.bclose(item.span, empty);
|
||||
}
|
||||
ast::ItemKind::TraitAlias(generics, bounds) => {
|
||||
ast::ItemKind::TraitAlias(ident, generics, bounds) => {
|
||||
self.head(visibility_qualified(&item.vis, "trait"));
|
||||
self.print_ident(item.ident);
|
||||
self.print_ident(*ident);
|
||||
self.print_generic_params(&generics.params);
|
||||
self.nbsp();
|
||||
if !bounds.is_empty() {
|
||||
@ -374,8 +400,8 @@ impl<'a> State<'a> {
|
||||
self.word(";");
|
||||
}
|
||||
}
|
||||
ast::ItemKind::MacroDef(macro_def) => {
|
||||
self.print_mac_def(macro_def, &item.ident, item.span, |state| {
|
||||
ast::ItemKind::MacroDef(ident, macro_def) => {
|
||||
self.print_mac_def(macro_def, &ident, item.span, |state| {
|
||||
state.print_visibility(&item.vis)
|
||||
});
|
||||
}
|
||||
@ -528,18 +554,25 @@ impl<'a> State<'a> {
|
||||
}
|
||||
|
||||
fn print_assoc_item(&mut self, item: &ast::AssocItem) {
|
||||
let ast::Item { id, span, ident, ref attrs, ref kind, ref vis, tokens: _ } = *item;
|
||||
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();
|
||||
self.maybe_print_comment(span.lo());
|
||||
self.print_outer_attributes(attrs);
|
||||
match kind {
|
||||
ast::AssocItemKind::Fn(func) => {
|
||||
self.print_fn_full(ident, vis, attrs, &*func);
|
||||
self.print_fn_full(vis, attrs, &*func);
|
||||
}
|
||||
ast::AssocItemKind::Const(box ast::ConstItem { defaultness, generics, ty, expr }) => {
|
||||
ast::AssocItemKind::Const(box ast::ConstItem {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
ty,
|
||||
expr,
|
||||
define_opaque,
|
||||
}) => {
|
||||
self.print_item_const(
|
||||
ident,
|
||||
*ident,
|
||||
None,
|
||||
generics,
|
||||
ty,
|
||||
@ -547,17 +580,19 @@ impl<'a> State<'a> {
|
||||
vis,
|
||||
ast::Safety::Default,
|
||||
*defaultness,
|
||||
define_opaque.as_deref(),
|
||||
);
|
||||
}
|
||||
ast::AssocItemKind::Type(box ast::TyAlias {
|
||||
defaultness,
|
||||
ident,
|
||||
generics,
|
||||
where_clauses,
|
||||
bounds,
|
||||
ty,
|
||||
}) => {
|
||||
self.print_associated_type(
|
||||
ident,
|
||||
*ident,
|
||||
generics,
|
||||
*where_clauses,
|
||||
bounds,
|
||||
@ -643,29 +678,17 @@ impl<'a> State<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn print_fn_full(
|
||||
&mut self,
|
||||
name: Ident,
|
||||
vis: &ast::Visibility,
|
||||
attrs: &[ast::Attribute],
|
||||
func: &ast::Fn,
|
||||
) {
|
||||
let ast::Fn { defaultness, generics, sig, contract, body, define_opaque } = func;
|
||||
fn print_fn_full(&mut self, vis: &ast::Visibility, attrs: &[ast::Attribute], func: &ast::Fn) {
|
||||
let ast::Fn { defaultness, ident, generics, sig, contract, body, define_opaque } = func;
|
||||
|
||||
if let Some(define_opaque) = define_opaque {
|
||||
for (_, path) in define_opaque {
|
||||
self.word("define opaques from ");
|
||||
self.print_path(path, false, 0);
|
||||
self.word(",");
|
||||
}
|
||||
}
|
||||
self.print_define_opaques(define_opaque.as_deref());
|
||||
|
||||
if body.is_some() {
|
||||
self.head("");
|
||||
}
|
||||
self.print_visibility(vis);
|
||||
self.print_defaultness(*defaultness);
|
||||
self.print_fn(&sig.decl, sig.header, Some(name), generics);
|
||||
self.print_fn(&sig.decl, sig.header, Some(*ident), generics);
|
||||
if let Some(contract) = &contract {
|
||||
self.nbsp();
|
||||
self.print_contract(contract);
|
||||
@ -678,6 +701,21 @@ impl<'a> State<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn print_define_opaques(&mut self, define_opaque: Option<&[(ast::NodeId, ast::Path)]>) {
|
||||
if let Some(define_opaque) = define_opaque {
|
||||
self.word("#[define_opaque(");
|
||||
for (i, (_, path)) in define_opaque.iter().enumerate() {
|
||||
if i != 0 {
|
||||
self.word_space(",");
|
||||
}
|
||||
|
||||
self.print_path(path, false, 0);
|
||||
}
|
||||
self.word(")]");
|
||||
}
|
||||
self.hardbreak_if_not_bol();
|
||||
}
|
||||
|
||||
fn print_contract(&mut self, contract: &ast::FnContract) {
|
||||
if let Some(pred) = &contract.requires {
|
||||
self.word("rustc_requires");
|
||||
@ -697,13 +735,13 @@ impl<'a> State<'a> {
|
||||
&mut self,
|
||||
decl: &ast::FnDecl,
|
||||
header: ast::FnHeader,
|
||||
name: Option<Ident>,
|
||||
ident: Option<Ident>,
|
||||
generics: &ast::Generics,
|
||||
) {
|
||||
self.print_fn_header_info(header);
|
||||
if let Some(name) = name {
|
||||
if let Some(ident) = ident {
|
||||
self.nbsp();
|
||||
self.print_ident(name);
|
||||
self.print_ident(ident);
|
||||
}
|
||||
self.print_generic_params(&generics.params);
|
||||
self.print_fn_params_and_ret(decl, false);
|
||||
|
@ -191,6 +191,7 @@ pub enum AttributeKind {
|
||||
},
|
||||
MacroTransparency(Transparency),
|
||||
Repr(ThinVec<(ReprAttr, Span)>),
|
||||
RustcMacroEdition2021,
|
||||
Stability {
|
||||
stability: Stability,
|
||||
/// Span of the `#[stable(...)]` or `#[unstable(...)]` attribute
|
||||
|
@ -182,21 +182,18 @@ macro_rules! find_attr {
|
||||
}};
|
||||
|
||||
($attributes_list: expr, $pattern: pat $(if $guard: expr)? => $e: expr) => {{
|
||||
fn check_attribute_iterator<'a>(_: &'_ impl IntoIterator<Item = &'a rustc_hir::Attribute>) {}
|
||||
check_attribute_iterator(&$attributes_list);
|
||||
|
||||
let find_attribute = |iter| {
|
||||
'done: {
|
||||
for i in $attributes_list {
|
||||
let i: &rustc_hir::Attribute = i;
|
||||
match i {
|
||||
rustc_hir::Attribute::Parsed($pattern) $(if $guard)? => {
|
||||
return Some($e);
|
||||
break 'done Some($e);
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
None
|
||||
};
|
||||
find_attribute($attributes_list)
|
||||
}
|
||||
}};
|
||||
}
|
||||
|
@ -9,15 +9,12 @@ rustc_abi = { path = "../rustc_abi" }
|
||||
rustc_ast = { path = "../rustc_ast" }
|
||||
rustc_ast_pretty = { path = "../rustc_ast_pretty" }
|
||||
rustc_attr_data_structures = { path = "../rustc_attr_data_structures" }
|
||||
rustc_data_structures = { path = "../rustc_data_structures" }
|
||||
rustc_errors = { path = "../rustc_errors" }
|
||||
rustc_feature = { path = "../rustc_feature" }
|
||||
rustc_fluent_macro = { path = "../rustc_fluent_macro" }
|
||||
rustc_hir = { path = "../rustc_hir" }
|
||||
rustc_lexer = { path = "../rustc_lexer" }
|
||||
rustc_macros = { path = "../rustc_macros" }
|
||||
rustc_middle = { path = "../rustc_middle" }
|
||||
rustc_serialize = { path = "../rustc_serialize" }
|
||||
rustc_session = { path = "../rustc_session" }
|
||||
rustc_span = { path = "../rustc_span" }
|
||||
thin-vec = "0.2.12"
|
||||
|
@ -28,6 +28,7 @@ pub(crate) mod cfg;
|
||||
pub(crate) mod confusables;
|
||||
pub(crate) mod deprecation;
|
||||
pub(crate) mod repr;
|
||||
pub(crate) mod rustc;
|
||||
pub(crate) mod stability;
|
||||
pub(crate) mod transparency;
|
||||
pub(crate) mod util;
|
||||
|
19
compiler/rustc_attr_parsing/src/attributes/rustc.rs
Normal file
19
compiler/rustc_attr_parsing/src/attributes/rustc.rs
Normal file
@ -0,0 +1,19 @@
|
||||
use rustc_attr_data_structures::AttributeKind;
|
||||
use rustc_span::sym;
|
||||
|
||||
use super::{AcceptContext, SingleAttributeParser};
|
||||
use crate::parser::ArgParser;
|
||||
|
||||
pub(crate) struct RustcMacroEdition2021Parser;
|
||||
|
||||
// FIXME(jdonszelmann): make these proper diagnostics
|
||||
impl SingleAttributeParser for RustcMacroEdition2021Parser {
|
||||
const PATH: &'static [rustc_span::Symbol] = &[sym::rustc_macro_edition_2021];
|
||||
|
||||
fn on_duplicate(_cx: &crate::context::AcceptContext<'_>, _first_span: rustc_span::Span) {}
|
||||
|
||||
fn convert(_cx: &AcceptContext<'_>, args: &ArgParser<'_>) -> Option<AttributeKind> {
|
||||
assert!(args.no_args());
|
||||
Some(AttributeKind::RustcMacroEdition2021)
|
||||
}
|
||||
}
|
@ -5,7 +5,7 @@ use rustc_attr_data_structures::{
|
||||
StableSince, UnstableReason, VERSION_PLACEHOLDER,
|
||||
};
|
||||
use rustc_errors::ErrorGuaranteed;
|
||||
use rustc_span::{Span, Symbol, kw, sym};
|
||||
use rustc_span::{Span, Symbol, sym};
|
||||
|
||||
use super::util::parse_version;
|
||||
use super::{AcceptMapping, AttributeParser, SingleAttributeParser};
|
||||
@ -61,11 +61,7 @@ impl AttributeParser for StabilityParser {
|
||||
}),
|
||||
(&[sym::rustc_allowed_through_unstable_modules], |this, cx, args| {
|
||||
reject_outside_std!(cx);
|
||||
this.allowed_through_unstable_modules =
|
||||
Some(match args.name_value().and_then(|i| i.value_as_str()) {
|
||||
Some(msg) => msg,
|
||||
None => kw::Empty,
|
||||
});
|
||||
this.allowed_through_unstable_modules = args.name_value().and_then(|i| i.value_as_str())
|
||||
}),
|
||||
];
|
||||
|
||||
|
@ -15,6 +15,7 @@ use crate::attributes::allow_unstable::{AllowConstFnUnstableParser, AllowInterna
|
||||
use crate::attributes::confusables::ConfusablesParser;
|
||||
use crate::attributes::deprecation::DeprecationParser;
|
||||
use crate::attributes::repr::ReprParser;
|
||||
use crate::attributes::rustc::RustcMacroEdition2021Parser;
|
||||
use crate::attributes::stability::{
|
||||
BodyStabilityParser, ConstStabilityIndirectParser, ConstStabilityParser, StabilityParser,
|
||||
};
|
||||
@ -76,6 +77,7 @@ attribute_groups!(
|
||||
// tidy-alphabetical-start
|
||||
Single<ConstStabilityIndirectParser>,
|
||||
Single<DeprecationParser>,
|
||||
Single<RustcMacroEdition2021Parser>,
|
||||
Single<TransparencyParser>,
|
||||
// tidy-alphabetical-end
|
||||
];
|
||||
|
@ -1,7 +1,7 @@
|
||||
//! This file provides API for compiler consumers.
|
||||
|
||||
use rustc_hir::def_id::LocalDefId;
|
||||
use rustc_index::{IndexSlice, IndexVec};
|
||||
use rustc_index::IndexVec;
|
||||
use rustc_middle::mir::{Body, Promoted};
|
||||
use rustc_middle::ty::TyCtxt;
|
||||
|
||||
@ -100,8 +100,5 @@ pub fn get_body_with_borrowck_facts(
|
||||
def: LocalDefId,
|
||||
options: ConsumerOptions,
|
||||
) -> BodyWithBorrowckFacts<'_> {
|
||||
let (input_body, promoted) = tcx.mir_promoted(def);
|
||||
let input_body: &Body<'_> = &input_body.borrow();
|
||||
let promoted: &IndexSlice<_, _> = &promoted.borrow();
|
||||
*super::do_mir_borrowck(tcx, input_body, promoted, Some(options)).1.unwrap()
|
||||
*super::do_mir_borrowck(tcx, def, Some(options)).1.unwrap()
|
||||
}
|
||||
|
@ -2514,12 +2514,12 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
let ty::Tuple(params) = tupled_params.kind() else { return };
|
||||
|
||||
// Find the first argument with a matching type, get its name
|
||||
let Some((_, this_name)) =
|
||||
params.iter().zip(tcx.hir_body_param_names(closure.body)).find(|(param_ty, name)| {
|
||||
let Some(this_name) = params.iter().zip(tcx.hir_body_param_names(closure.body)).find_map(
|
||||
|(param_ty, name)| {
|
||||
// FIXME: also support deref for stuff like `Rc` arguments
|
||||
param_ty.peel_refs() == local_ty && name != &Ident::empty()
|
||||
})
|
||||
else {
|
||||
if param_ty.peel_refs() == local_ty { name } else { None }
|
||||
},
|
||||
) else {
|
||||
return;
|
||||
};
|
||||
|
||||
@ -3787,7 +3787,7 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
method_args,
|
||||
*fn_span,
|
||||
call_source.from_hir_call(),
|
||||
Some(self.infcx.tcx.fn_arg_names(method_did)[0]),
|
||||
self.infcx.tcx.fn_arg_names(method_did)[0],
|
||||
)
|
||||
{
|
||||
err.note(format!("borrow occurs due to deref coercion to `{deref_target_ty}`"));
|
||||
|
@ -1029,7 +1029,7 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
method_args,
|
||||
*fn_span,
|
||||
call_source.from_hir_call(),
|
||||
Some(self.infcx.tcx.fn_arg_names(method_did)[0]),
|
||||
self.infcx.tcx.fn_arg_names(method_did)[0],
|
||||
);
|
||||
|
||||
return FnSelfUse {
|
||||
|
@ -691,7 +691,9 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
true,
|
||||
td.is_local(),
|
||||
td.as_local().and_then(|tld| match self.infcx.tcx.hir_node_by_def_id(tld) {
|
||||
Node::Item(hir::Item { kind: hir::ItemKind::Trait(_, _, _, _, items), .. }) => {
|
||||
Node::Item(hir::Item {
|
||||
kind: hir::ItemKind::Trait(_, _, _, _, _, items), ..
|
||||
}) => {
|
||||
let mut f_in_trait_opt = None;
|
||||
for hir::TraitItemRef { id: fi, kind: k, .. } in *items {
|
||||
let hi = fi.hir_id();
|
||||
@ -980,7 +982,7 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
let arg = match tcx.hir_get_if_local(callee_def_id) {
|
||||
Some(
|
||||
hir::Node::Item(hir::Item {
|
||||
ident, kind: hir::ItemKind::Fn { sig, .. }, ..
|
||||
kind: hir::ItemKind::Fn { ident, sig, .. }, ..
|
||||
})
|
||||
| hir::Node::TraitItem(hir::TraitItem {
|
||||
ident,
|
||||
@ -1021,7 +1023,7 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
// return type.
|
||||
match tcx.hir_node_by_def_id(tcx.hir_get_parent_item(fn_call_id).def_id) {
|
||||
hir::Node::Item(hir::Item {
|
||||
ident, kind: hir::ItemKind::Fn { sig, .. }, ..
|
||||
kind: hir::ItemKind::Fn { ident, sig, .. }, ..
|
||||
})
|
||||
| hir::Node::TraitItem(hir::TraitItem {
|
||||
ident,
|
||||
|
@ -513,14 +513,14 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
ty::VarianceDiagInfo::Invariant { ty, param_index } => {
|
||||
let (desc, note) = match ty.kind() {
|
||||
ty::RawPtr(ty, mutbl) => {
|
||||
assert_eq!(*mutbl, rustc_hir::Mutability::Mut);
|
||||
assert_eq!(*mutbl, hir::Mutability::Mut);
|
||||
(
|
||||
format!("a mutable pointer to `{}`", ty),
|
||||
"mutable pointers are invariant over their type parameter".to_string(),
|
||||
)
|
||||
}
|
||||
ty::Ref(_, inner_ty, mutbl) => {
|
||||
assert_eq!(*mutbl, rustc_hir::Mutability::Mut);
|
||||
assert_eq!(*mutbl, hir::Mutability::Mut);
|
||||
(
|
||||
format!("a mutable reference to `{inner_ty}`"),
|
||||
"mutable references are invariant over their type parameter"
|
||||
@ -887,7 +887,7 @@ impl<'infcx, 'tcx> MirBorrowckCtxt<'_, 'infcx, 'tcx> {
|
||||
// Skip `async` desugaring `impl Future`.
|
||||
}
|
||||
if let TyKind::TraitObject(_, lt) = alias_ty.kind {
|
||||
if lt.ident.name == kw::Empty {
|
||||
if lt.res == hir::LifetimeName::ImplicitObjectLifetimeDefault {
|
||||
spans_suggs.push((lt.ident.span.shrink_to_hi(), " + 'a".to_string()));
|
||||
} else {
|
||||
spans_suggs.push((lt.ident.span, "'a".to_string()));
|
||||
|
@ -73,6 +73,7 @@ mod def_use;
|
||||
mod diagnostics;
|
||||
mod member_constraints;
|
||||
mod nll;
|
||||
mod opaque_types;
|
||||
mod path_utils;
|
||||
mod place_ext;
|
||||
mod places_conflict;
|
||||
@ -102,11 +103,8 @@ pub fn provide(providers: &mut Providers) {
|
||||
}
|
||||
|
||||
fn mir_borrowck(tcx: TyCtxt<'_>, def: LocalDefId) -> &BorrowCheckResult<'_> {
|
||||
let (input_body, promoted) = tcx.mir_promoted(def);
|
||||
debug!("run query mir_borrowck: {}", tcx.def_path_str(def));
|
||||
|
||||
let (input_body, _) = tcx.mir_promoted(def);
|
||||
let input_body: &Body<'_> = &input_body.borrow();
|
||||
|
||||
if input_body.should_skip() || input_body.tainted_by_errors.is_some() {
|
||||
debug!("Skipping borrowck because of injected body or tainted body");
|
||||
// Let's make up a borrowck result! Fun times!
|
||||
@ -119,7 +117,7 @@ fn mir_borrowck(tcx: TyCtxt<'_>, def: LocalDefId) -> &BorrowCheckResult<'_> {
|
||||
return tcx.arena.alloc(result);
|
||||
}
|
||||
|
||||
let borrowck_result = do_mir_borrowck(tcx, input_body, &*promoted.borrow(), None).0;
|
||||
let borrowck_result = do_mir_borrowck(tcx, def, None).0;
|
||||
debug!("mir_borrowck done");
|
||||
|
||||
tcx.arena.alloc(borrowck_result)
|
||||
@ -130,15 +128,16 @@ fn mir_borrowck(tcx: TyCtxt<'_>, def: LocalDefId) -> &BorrowCheckResult<'_> {
|
||||
/// Use `consumer_options: None` for the default behavior of returning
|
||||
/// [`BorrowCheckResult`] only. Otherwise, return [`BodyWithBorrowckFacts`] according
|
||||
/// to the given [`ConsumerOptions`].
|
||||
#[instrument(skip(tcx, input_body, input_promoted), fields(id=?input_body.source.def_id()), level = "debug")]
|
||||
#[instrument(skip(tcx), level = "debug")]
|
||||
fn do_mir_borrowck<'tcx>(
|
||||
tcx: TyCtxt<'tcx>,
|
||||
input_body: &Body<'tcx>,
|
||||
input_promoted: &IndexSlice<Promoted, Body<'tcx>>,
|
||||
def: LocalDefId,
|
||||
consumer_options: Option<ConsumerOptions>,
|
||||
) -> (BorrowCheckResult<'tcx>, Option<Box<BodyWithBorrowckFacts<'tcx>>>) {
|
||||
let def = input_body.source.def_id().expect_local();
|
||||
let infcx = BorrowckInferCtxt::new(tcx, def);
|
||||
let (input_body, promoted) = tcx.mir_promoted(def);
|
||||
let input_body: &Body<'_> = &input_body.borrow();
|
||||
let input_promoted: &IndexSlice<_, _> = &promoted.borrow();
|
||||
if let Some(e) = input_body.tainted_by_errors {
|
||||
infcx.set_tainted_by_errors(e);
|
||||
}
|
||||
@ -192,7 +191,7 @@ fn do_mir_borrowck<'tcx>(
|
||||
// Compute non-lexical lifetimes.
|
||||
let nll::NllOutput {
|
||||
regioncx,
|
||||
opaque_type_values,
|
||||
concrete_opaque_types,
|
||||
polonius_input,
|
||||
polonius_output,
|
||||
opt_closure_req,
|
||||
@ -222,7 +221,7 @@ fn do_mir_borrowck<'tcx>(
|
||||
body,
|
||||
®ioncx,
|
||||
&opt_closure_req,
|
||||
&opaque_type_values,
|
||||
&concrete_opaque_types,
|
||||
diags_buffer,
|
||||
);
|
||||
|
||||
@ -357,7 +356,7 @@ fn do_mir_borrowck<'tcx>(
|
||||
let tainted_by_errors = mbcx.emit_errors();
|
||||
|
||||
let result = BorrowCheckResult {
|
||||
concrete_opaque_types: opaque_type_values,
|
||||
concrete_opaque_types: concrete_opaque_types.into_inner(),
|
||||
closure_requirements: opt_closure_req,
|
||||
used_mut_upvars: mbcx.used_mut_upvars,
|
||||
tainted_by_errors,
|
||||
@ -498,7 +497,8 @@ impl<'tcx> BorrowckInferCtxt<'tcx> {
|
||||
)
|
||||
});
|
||||
|
||||
self.inject_new_hidden_type_unchecked(key, hidden_ty);
|
||||
let prev = self.register_hidden_type_in_storage(key, hidden_ty);
|
||||
assert_eq!(prev, None);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,13 +1,11 @@
|
||||
//! The entry point of the NLL borrow checker.
|
||||
|
||||
use std::io;
|
||||
use std::path::PathBuf;
|
||||
use std::rc::Rc;
|
||||
use std::str::FromStr;
|
||||
use std::{env, io};
|
||||
|
||||
use polonius_engine::{Algorithm, Output};
|
||||
use rustc_data_structures::fx::FxIndexMap;
|
||||
use rustc_hir::def_id::LocalDefId;
|
||||
use rustc_index::IndexSlice;
|
||||
use rustc_middle::mir::pretty::{PrettyPrintMirOptions, dump_mir_with_options};
|
||||
use rustc_middle::mir::{
|
||||
@ -15,7 +13,7 @@ use rustc_middle::mir::{
|
||||
dump_enabled, dump_mir,
|
||||
};
|
||||
use rustc_middle::ty::print::with_no_trimmed_paths;
|
||||
use rustc_middle::ty::{self, OpaqueHiddenType, TyCtxt};
|
||||
use rustc_middle::ty::{self, TyCtxt};
|
||||
use rustc_mir_dataflow::ResultsCursor;
|
||||
use rustc_mir_dataflow::impls::MaybeInitializedPlaces;
|
||||
use rustc_mir_dataflow::move_paths::MoveData;
|
||||
@ -27,6 +25,7 @@ use tracing::{debug, instrument};
|
||||
use crate::borrow_set::BorrowSet;
|
||||
use crate::consumers::ConsumerOptions;
|
||||
use crate::diagnostics::{BorrowckDiagnosticsBuffer, RegionErrors};
|
||||
use crate::opaque_types::ConcreteOpaqueTypes;
|
||||
use crate::polonius::PoloniusDiagnosticsContext;
|
||||
use crate::polonius::legacy::{
|
||||
PoloniusFacts, PoloniusFactsExt, PoloniusLocationTable, PoloniusOutput,
|
||||
@ -40,7 +39,7 @@ use crate::{BorrowckInferCtxt, polonius, renumber};
|
||||
/// closure requirements to propagate, and any generated errors.
|
||||
pub(crate) struct NllOutput<'tcx> {
|
||||
pub regioncx: RegionInferenceContext<'tcx>,
|
||||
pub opaque_type_values: FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>>,
|
||||
pub concrete_opaque_types: ConcreteOpaqueTypes<'tcx>,
|
||||
pub polonius_input: Option<Box<PoloniusFacts>>,
|
||||
pub polonius_output: Option<Box<PoloniusOutput>>,
|
||||
pub opt_closure_req: Option<ClosureRegionRequirements<'tcx>>,
|
||||
@ -99,6 +98,8 @@ pub(crate) fn compute_regions<'a, 'tcx>(
|
||||
|
||||
let location_map = Rc::new(DenseLocationMap::new(body));
|
||||
|
||||
let mut concrete_opaque_types = ConcreteOpaqueTypes::default();
|
||||
|
||||
// Run the MIR type-checker.
|
||||
let MirTypeckResults {
|
||||
constraints,
|
||||
@ -116,6 +117,7 @@ pub(crate) fn compute_regions<'a, 'tcx>(
|
||||
flow_inits,
|
||||
move_data,
|
||||
Rc::clone(&location_map),
|
||||
&mut concrete_opaque_types,
|
||||
);
|
||||
|
||||
// Create the region inference context, taking ownership of the
|
||||
@ -160,9 +162,8 @@ pub(crate) fn compute_regions<'a, 'tcx>(
|
||||
}
|
||||
|
||||
if polonius_output {
|
||||
let algorithm =
|
||||
env::var("POLONIUS_ALGORITHM").unwrap_or_else(|_| String::from("Hybrid"));
|
||||
let algorithm = Algorithm::from_str(&algorithm).unwrap();
|
||||
let algorithm = infcx.tcx.env_var("POLONIUS_ALGORITHM").unwrap_or("Hybrid");
|
||||
let algorithm = Algorithm::from_str(algorithm).unwrap();
|
||||
debug!("compute_regions: using polonius algorithm {:?}", algorithm);
|
||||
let _prof_timer = infcx.tcx.prof.generic_activity("polonius_analysis");
|
||||
Some(Box::new(Output::compute(polonius_facts, algorithm, false)))
|
||||
@ -180,11 +181,11 @@ pub(crate) fn compute_regions<'a, 'tcx>(
|
||||
infcx.set_tainted_by_errors(guar);
|
||||
}
|
||||
|
||||
let remapped_opaque_tys = regioncx.infer_opaque_types(infcx, opaque_type_values);
|
||||
regioncx.infer_opaque_types(infcx, opaque_type_values, &mut concrete_opaque_types);
|
||||
|
||||
NllOutput {
|
||||
regioncx,
|
||||
opaque_type_values: remapped_opaque_tys,
|
||||
concrete_opaque_types,
|
||||
polonius_input: polonius_facts.map(Box::new),
|
||||
polonius_output,
|
||||
opt_closure_req: closure_region_requirements,
|
||||
@ -300,7 +301,7 @@ pub(super) fn dump_annotation<'tcx, 'infcx>(
|
||||
body: &Body<'tcx>,
|
||||
regioncx: &RegionInferenceContext<'tcx>,
|
||||
closure_region_requirements: &Option<ClosureRegionRequirements<'tcx>>,
|
||||
opaque_type_values: &FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>>,
|
||||
concrete_opaque_types: &ConcreteOpaqueTypes<'tcx>,
|
||||
diagnostics_buffer: &mut BorrowckDiagnosticsBuffer<'infcx, 'tcx>,
|
||||
) {
|
||||
let tcx = infcx.tcx;
|
||||
@ -343,8 +344,8 @@ pub(super) fn dump_annotation<'tcx, 'infcx>(
|
||||
err
|
||||
};
|
||||
|
||||
if !opaque_type_values.is_empty() {
|
||||
err.note(format!("Inferred opaque type values:\n{opaque_type_values:#?}"));
|
||||
if !concrete_opaque_types.is_empty() {
|
||||
err.note(format!("Inferred opaque type values:\n{concrete_opaque_types:#?}"));
|
||||
}
|
||||
|
||||
diagnostics_buffer.buffer_non_error(err);
|
||||
|
55
compiler/rustc_borrowck/src/opaque_types.rs
Normal file
55
compiler/rustc_borrowck/src/opaque_types.rs
Normal file
@ -0,0 +1,55 @@
|
||||
use rustc_data_structures::fx::FxIndexMap;
|
||||
use rustc_hir::def_id::LocalDefId;
|
||||
use rustc_middle::ty::{OpaqueHiddenType, Ty, TyCtxt};
|
||||
|
||||
#[derive(Debug, Default)]
|
||||
pub(super) struct ConcreteOpaqueTypes<'tcx> {
|
||||
concrete_opaque_types: FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>>,
|
||||
}
|
||||
|
||||
impl<'tcx> ConcreteOpaqueTypes<'tcx> {
|
||||
pub(super) fn is_empty(&self) -> bool {
|
||||
self.concrete_opaque_types.is_empty()
|
||||
}
|
||||
|
||||
pub(super) fn into_inner(self) -> FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>> {
|
||||
self.concrete_opaque_types
|
||||
}
|
||||
|
||||
/// Insert an opaque type into the list of opaque types defined by this function
|
||||
/// after mapping the hidden type to the generic parameters of the opaque type
|
||||
/// definition.
|
||||
pub(super) fn insert(
|
||||
&mut self,
|
||||
tcx: TyCtxt<'tcx>,
|
||||
def_id: LocalDefId,
|
||||
hidden_ty: OpaqueHiddenType<'tcx>,
|
||||
) {
|
||||
// Sometimes two opaque types are the same only after we remap the generic parameters
|
||||
// back to the opaque type definition. E.g. we may have `OpaqueType<X, Y>` mapped to
|
||||
// `(X, Y)` and `OpaqueType<Y, X>` mapped to `(Y, X)`, and those are the same, but we
|
||||
// only know that once we convert the generic parameters to those of the opaque type.
|
||||
if let Some(prev) = self.concrete_opaque_types.get_mut(&def_id) {
|
||||
if prev.ty != hidden_ty.ty {
|
||||
let (Ok(guar) | Err(guar)) =
|
||||
prev.build_mismatch_error(&hidden_ty, tcx).map(|d| d.emit());
|
||||
prev.ty = Ty::new_error(tcx, guar);
|
||||
}
|
||||
// Pick a better span if there is one.
|
||||
// FIXME(oli-obk): collect multiple spans for better diagnostics down the road.
|
||||
prev.span = prev.span.substitute_dummy(hidden_ty.span);
|
||||
} else {
|
||||
self.concrete_opaque_types.insert(def_id, hidden_ty);
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) fn extend_from_nested_body(
|
||||
&mut self,
|
||||
tcx: TyCtxt<'tcx>,
|
||||
nested_body: &FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>>,
|
||||
) {
|
||||
for (&def_id, &hidden_ty) in nested_body {
|
||||
self.insert(tcx, def_id, hidden_ty);
|
||||
}
|
||||
}
|
||||
}
|
@ -15,6 +15,7 @@ use rustc_trait_selection::traits::ObligationCtxt;
|
||||
use tracing::{debug, instrument};
|
||||
|
||||
use super::RegionInferenceContext;
|
||||
use crate::opaque_types::ConcreteOpaqueTypes;
|
||||
use crate::session_diagnostics::{LifetimeMismatchOpaqueParam, NonGenericOpaqueTypeParam};
|
||||
use crate::universal_regions::RegionClassification;
|
||||
|
||||
@ -67,8 +68,8 @@ impl<'tcx> RegionInferenceContext<'tcx> {
|
||||
&self,
|
||||
infcx: &InferCtxt<'tcx>,
|
||||
opaque_ty_decls: FxIndexMap<OpaqueTypeKey<'tcx>, OpaqueHiddenType<'tcx>>,
|
||||
) -> FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>> {
|
||||
let mut result: FxIndexMap<LocalDefId, OpaqueHiddenType<'tcx>> = FxIndexMap::default();
|
||||
concrete_opaque_types: &mut ConcreteOpaqueTypes<'tcx>,
|
||||
) {
|
||||
let mut decls_modulo_regions: FxIndexMap<OpaqueTypeKey<'tcx>, (OpaqueTypeKey<'tcx>, Span)> =
|
||||
FxIndexMap::default();
|
||||
|
||||
@ -143,33 +144,12 @@ impl<'tcx> RegionInferenceContext<'tcx> {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
// Sometimes two opaque types are the same only after we remap the generic parameters
|
||||
// back to the opaque type definition. E.g. we may have `OpaqueType<X, Y>` mapped to
|
||||
// `(X, Y)` and `OpaqueType<Y, X>` mapped to `(Y, X)`, and those are the same, but we
|
||||
// only know that once we convert the generic parameters to those of the opaque type.
|
||||
if let Some(prev) = result.get_mut(&opaque_type_key.def_id) {
|
||||
if prev.ty != ty {
|
||||
let guar = ty.error_reported().err().unwrap_or_else(|| {
|
||||
let (Ok(e) | Err(e)) = prev
|
||||
.build_mismatch_error(
|
||||
&OpaqueHiddenType { ty, span: concrete_type.span },
|
||||
infcx.tcx,
|
||||
)
|
||||
.map(|d| d.emit());
|
||||
e
|
||||
});
|
||||
prev.ty = Ty::new_error(infcx.tcx, guar);
|
||||
}
|
||||
// Pick a better span if there is one.
|
||||
// FIXME(oli-obk): collect multiple spans for better diagnostics down the road.
|
||||
prev.span = prev.span.substitute_dummy(concrete_type.span);
|
||||
} else {
|
||||
result.insert(
|
||||
opaque_type_key.def_id,
|
||||
OpaqueHiddenType { ty, span: concrete_type.span },
|
||||
);
|
||||
}
|
||||
|
||||
concrete_opaque_types.insert(
|
||||
infcx.tcx,
|
||||
opaque_type_key.def_id,
|
||||
OpaqueHiddenType { ty, span: concrete_type.span },
|
||||
);
|
||||
// Check that all opaque types have the same region parameters if they have the same
|
||||
// non-region parameters. This is necessary because within the new solver we perform
|
||||
// various query operations modulo regions, and thus could unsoundly select some impls
|
||||
@ -193,7 +173,6 @@ impl<'tcx> RegionInferenceContext<'tcx> {
|
||||
});
|
||||
}
|
||||
}
|
||||
result
|
||||
}
|
||||
|
||||
/// Map the regions in the type to named regions. This is similar to what
|
||||
|
@ -45,6 +45,7 @@ use crate::borrow_set::BorrowSet;
|
||||
use crate::constraints::{OutlivesConstraint, OutlivesConstraintSet};
|
||||
use crate::diagnostics::UniverseInfo;
|
||||
use crate::member_constraints::MemberConstraintSet;
|
||||
use crate::opaque_types::ConcreteOpaqueTypes;
|
||||
use crate::polonius::legacy::{PoloniusFacts, PoloniusLocationTable};
|
||||
use crate::polonius::{PoloniusContext, PoloniusLivenessContext};
|
||||
use crate::region_infer::TypeTest;
|
||||
@ -111,6 +112,7 @@ pub(crate) fn type_check<'a, 'tcx>(
|
||||
flow_inits: ResultsCursor<'a, 'tcx, MaybeInitializedPlaces<'a, 'tcx>>,
|
||||
move_data: &MoveData<'tcx>,
|
||||
location_map: Rc<DenseLocationMap>,
|
||||
concrete_opaque_types: &mut ConcreteOpaqueTypes<'tcx>,
|
||||
) -> MirTypeckResults<'tcx> {
|
||||
let implicit_region_bound = ty::Region::new_var(infcx.tcx, universal_regions.fr_fn_body);
|
||||
let mut constraints = MirTypeckRegionConstraints {
|
||||
@ -165,6 +167,7 @@ pub(crate) fn type_check<'a, 'tcx>(
|
||||
polonius_facts,
|
||||
borrow_set,
|
||||
constraints: &mut constraints,
|
||||
concrete_opaque_types,
|
||||
polonius_liveness,
|
||||
};
|
||||
|
||||
@ -230,6 +233,7 @@ struct TypeChecker<'a, 'tcx> {
|
||||
polonius_facts: &'a mut Option<PoloniusFacts>,
|
||||
borrow_set: &'a BorrowSet<'tcx>,
|
||||
constraints: &'a mut MirTypeckRegionConstraints<'tcx>,
|
||||
concrete_opaque_types: &'a mut ConcreteOpaqueTypes<'tcx>,
|
||||
/// When using `-Zpolonius=next`, the liveness helper data used to create polonius constraints.
|
||||
polonius_liveness: Option<PoloniusLivenessContext>,
|
||||
}
|
||||
@ -2499,7 +2503,11 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
||||
args: GenericArgsRef<'tcx>,
|
||||
locations: Locations,
|
||||
) -> ty::InstantiatedPredicates<'tcx> {
|
||||
if let Some(closure_requirements) = &tcx.mir_borrowck(def_id).closure_requirements {
|
||||
let closure_borrowck_results = tcx.mir_borrowck(def_id);
|
||||
self.concrete_opaque_types
|
||||
.extend_from_nested_body(tcx, &closure_borrowck_results.concrete_opaque_types);
|
||||
|
||||
if let Some(closure_requirements) = &closure_borrowck_results.closure_requirements {
|
||||
constraint_conversion::ConstraintConversion::new(
|
||||
self.infcx,
|
||||
self.universal_regions,
|
||||
|
@ -21,15 +21,15 @@ pub(crate) fn expand(
|
||||
|
||||
// Allow using `#[alloc_error_handler]` on an item statement
|
||||
// FIXME - if we get deref patterns, use them to reduce duplication here
|
||||
let (item, is_stmt, sig_span) = if let Annotatable::Item(item) = &item
|
||||
let (item, ident, is_stmt, sig_span) = if let Annotatable::Item(item) = &item
|
||||
&& let ItemKind::Fn(fn_kind) = &item.kind
|
||||
{
|
||||
(item, false, ecx.with_def_site_ctxt(fn_kind.sig.span))
|
||||
(item, fn_kind.ident, false, ecx.with_def_site_ctxt(fn_kind.sig.span))
|
||||
} else if let Annotatable::Stmt(stmt) = &item
|
||||
&& let StmtKind::Item(item) = &stmt.kind
|
||||
&& let ItemKind::Fn(fn_kind) = &item.kind
|
||||
{
|
||||
(item, true, ecx.with_def_site_ctxt(fn_kind.sig.span))
|
||||
(item, fn_kind.ident, true, ecx.with_def_site_ctxt(fn_kind.sig.span))
|
||||
} else {
|
||||
ecx.dcx().emit_err(errors::AllocErrorMustBeFn { span: item.span() });
|
||||
return vec![orig_item];
|
||||
@ -39,7 +39,7 @@ pub(crate) fn expand(
|
||||
let span = ecx.with_def_site_ctxt(item.span);
|
||||
|
||||
// Generate item statements for the allocator methods.
|
||||
let stmts = thin_vec![generate_handler(ecx, item.ident, span, sig_span)];
|
||||
let stmts = thin_vec![generate_handler(ecx, ident, span, sig_span)];
|
||||
|
||||
// Generate anonymous constant serving as container for the allocator methods.
|
||||
let const_ty = ecx.ty(sig_span, TyKind::Tup(ThinVec::new()));
|
||||
@ -85,6 +85,7 @@ fn generate_handler(cx: &ExtCtxt<'_>, handler: Ident, span: Span, sig_span: Span
|
||||
let kind = ItemKind::Fn(Box::new(Fn {
|
||||
defaultness: ast::Defaultness::Final,
|
||||
sig,
|
||||
ident: Ident::from_str_and_span("__rg_oom", span),
|
||||
generics: Generics::default(),
|
||||
contract: None,
|
||||
body,
|
||||
@ -93,6 +94,6 @@ fn generate_handler(cx: &ExtCtxt<'_>, handler: Ident, span: Span, sig_span: Span
|
||||
|
||||
let attrs = thin_vec![cx.attr_word(sym::rustc_std_internal_symbol, span)];
|
||||
|
||||
let item = cx.item(span, Ident::from_str_and_span("__rg_oom", span), attrs, kind);
|
||||
let item = cx.item(span, attrs, kind);
|
||||
cx.stmt_item(sig_span, item)
|
||||
}
|
||||
|
@ -10,7 +10,7 @@ use rustc_index::bit_set::GrowableBitSet;
|
||||
use rustc_parse::exp;
|
||||
use rustc_parse::parser::{ExpKeywordPair, Parser};
|
||||
use rustc_session::lint;
|
||||
use rustc_span::{ErrorGuaranteed, Ident, InnerSpan, Span, Symbol, kw};
|
||||
use rustc_span::{ErrorGuaranteed, InnerSpan, Span, Symbol, kw};
|
||||
use rustc_target::asm::InlineAsmArch;
|
||||
use smallvec::smallvec;
|
||||
use {rustc_ast as ast, rustc_parse_format as parse};
|
||||
@ -888,7 +888,6 @@ pub(super) fn expand_global_asm<'cx>(
|
||||
};
|
||||
match mac {
|
||||
Ok(inline_asm) => MacEager::items(smallvec![P(ast::Item {
|
||||
ident: Ident::empty(),
|
||||
attrs: ast::AttrVec::new(),
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
kind: ast::ItemKind::GlobalAsm(Box::new(inline_asm)),
|
||||
|
@ -112,7 +112,6 @@ impl<'cx, 'a> Context<'cx, 'a> {
|
||||
self.span,
|
||||
self.cx.item(
|
||||
self.span,
|
||||
Ident::empty(),
|
||||
thin_vec![self.cx.attr_nested_word(sym::allow, sym::unused_imports, self.span)],
|
||||
ItemKind::Use(UseTree {
|
||||
prefix: self.cx.path(self.span, self.cx.std_path(&[sym::asserting])),
|
||||
|
@ -26,6 +26,16 @@ mod llvm_enzyme {
|
||||
|
||||
use crate::errors;
|
||||
|
||||
pub(crate) fn outer_normal_attr(
|
||||
kind: &P<rustc_ast::NormalAttr>,
|
||||
id: rustc_ast::AttrId,
|
||||
span: Span,
|
||||
) -> rustc_ast::Attribute {
|
||||
let style = rustc_ast::AttrStyle::Outer;
|
||||
let kind = rustc_ast::AttrKind::Normal(kind.clone());
|
||||
rustc_ast::Attribute { kind, id, style, span }
|
||||
}
|
||||
|
||||
// If we have a default `()` return type or explicitley `()` return type,
|
||||
// then we often can skip doing some work.
|
||||
fn has_ret(ty: &FnRetTy) -> bool {
|
||||
@ -136,26 +146,26 @@ mod llvm_enzyme {
|
||||
}
|
||||
let dcx = ecx.sess.dcx();
|
||||
// first get the annotable item:
|
||||
let (sig, is_impl): (FnSig, bool) = match &item {
|
||||
let (primal, sig, is_impl): (Ident, FnSig, bool) = match &item {
|
||||
Annotatable::Item(iitem) => {
|
||||
let sig = match &iitem.kind {
|
||||
ItemKind::Fn(box ast::Fn { sig, .. }) => sig,
|
||||
let (ident, sig) = match &iitem.kind {
|
||||
ItemKind::Fn(box ast::Fn { ident, sig, .. }) => (ident, sig),
|
||||
_ => {
|
||||
dcx.emit_err(errors::AutoDiffInvalidApplication { span: item.span() });
|
||||
return vec![item];
|
||||
}
|
||||
};
|
||||
(sig.clone(), false)
|
||||
(*ident, sig.clone(), false)
|
||||
}
|
||||
Annotatable::AssocItem(assoc_item, _) => {
|
||||
let sig = match &assoc_item.kind {
|
||||
ast::AssocItemKind::Fn(box ast::Fn { sig, .. }) => sig,
|
||||
Annotatable::AssocItem(assoc_item, Impl { of_trait: false }) => {
|
||||
let (ident, sig) = match &assoc_item.kind {
|
||||
ast::AssocItemKind::Fn(box ast::Fn { ident, sig, .. }) => (ident, sig),
|
||||
_ => {
|
||||
dcx.emit_err(errors::AutoDiffInvalidApplication { span: item.span() });
|
||||
return vec![item];
|
||||
}
|
||||
};
|
||||
(sig.clone(), true)
|
||||
(*ident, sig.clone(), true)
|
||||
}
|
||||
_ => {
|
||||
dcx.emit_err(errors::AutoDiffInvalidApplication { span: item.span() });
|
||||
@ -174,11 +184,9 @@ mod llvm_enzyme {
|
||||
let has_ret = has_ret(&sig.decl.output);
|
||||
let sig_span = ecx.with_call_site_ctxt(sig.span);
|
||||
|
||||
let (vis, primal) = match &item {
|
||||
Annotatable::Item(iitem) => (iitem.vis.clone(), iitem.ident.clone()),
|
||||
Annotatable::AssocItem(assoc_item, _) => {
|
||||
(assoc_item.vis.clone(), assoc_item.ident.clone())
|
||||
}
|
||||
let vis = match &item {
|
||||
Annotatable::Item(iitem) => iitem.vis.clone(),
|
||||
Annotatable::AssocItem(assoc_item, _) => assoc_item.vis.clone(),
|
||||
_ => {
|
||||
dcx.emit_err(errors::AutoDiffInvalidApplication { span: item.span() });
|
||||
return vec![item];
|
||||
@ -224,27 +232,15 @@ mod llvm_enzyme {
|
||||
.filter(|a| **a == DiffActivity::Active || **a == DiffActivity::ActiveOnly)
|
||||
.count() as u32;
|
||||
let (d_sig, new_args, idents, errored) = gen_enzyme_decl(ecx, &sig, &x, span);
|
||||
let new_decl_span = d_sig.span;
|
||||
let d_body = gen_enzyme_body(
|
||||
ecx,
|
||||
&x,
|
||||
n_active,
|
||||
&sig,
|
||||
&d_sig,
|
||||
primal,
|
||||
&new_args,
|
||||
span,
|
||||
sig_span,
|
||||
new_decl_span,
|
||||
idents,
|
||||
errored,
|
||||
ecx, &x, n_active, &sig, &d_sig, primal, &new_args, span, sig_span, idents, errored,
|
||||
);
|
||||
let d_ident = first_ident(&meta_item_vec[0]);
|
||||
|
||||
// The first element of it is the name of the function to be generated
|
||||
let asdf = Box::new(ast::Fn {
|
||||
defaultness: ast::Defaultness::Final,
|
||||
sig: d_sig,
|
||||
ident: first_ident(&meta_item_vec[0]),
|
||||
generics: Generics::default(),
|
||||
contract: None,
|
||||
body: Some(d_body),
|
||||
@ -270,36 +266,39 @@ mod llvm_enzyme {
|
||||
};
|
||||
let inline_never_attr = P(ast::NormalAttr { item: inline_item, tokens: None });
|
||||
let new_id = ecx.sess.psess.attr_id_generator.mk_attr_id();
|
||||
let attr: ast::Attribute = ast::Attribute {
|
||||
kind: ast::AttrKind::Normal(rustc_ad_attr.clone()),
|
||||
id: new_id,
|
||||
style: ast::AttrStyle::Outer,
|
||||
span,
|
||||
};
|
||||
let attr = outer_normal_attr(&rustc_ad_attr, new_id, span);
|
||||
let new_id = ecx.sess.psess.attr_id_generator.mk_attr_id();
|
||||
let inline_never: ast::Attribute = ast::Attribute {
|
||||
kind: ast::AttrKind::Normal(inline_never_attr),
|
||||
id: new_id,
|
||||
style: ast::AttrStyle::Outer,
|
||||
span,
|
||||
};
|
||||
let inline_never = outer_normal_attr(&inline_never_attr, new_id, span);
|
||||
|
||||
// We're avoid duplicating the attributes `#[rustc_autodiff]` and `#[inline(never)]`.
|
||||
fn same_attribute(attr: &ast::AttrKind, item: &ast::AttrKind) -> bool {
|
||||
match (attr, item) {
|
||||
(ast::AttrKind::Normal(a), ast::AttrKind::Normal(b)) => {
|
||||
let a = &a.item.path;
|
||||
let b = &b.item.path;
|
||||
a.segments.len() == b.segments.len()
|
||||
&& a.segments.iter().zip(b.segments.iter()).all(|(a, b)| a.ident == b.ident)
|
||||
}
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
// Don't add it multiple times:
|
||||
let orig_annotatable: Annotatable = match item {
|
||||
Annotatable::Item(ref mut iitem) => {
|
||||
if !iitem.attrs.iter().any(|a| a.id == attr.id) {
|
||||
if !iitem.attrs.iter().any(|a| same_attribute(&a.kind, &attr.kind)) {
|
||||
iitem.attrs.push(attr);
|
||||
}
|
||||
if !iitem.attrs.iter().any(|a| a.id == inline_never.id) {
|
||||
if !iitem.attrs.iter().any(|a| same_attribute(&a.kind, &inline_never.kind)) {
|
||||
iitem.attrs.push(inline_never.clone());
|
||||
}
|
||||
Annotatable::Item(iitem.clone())
|
||||
}
|
||||
Annotatable::AssocItem(ref mut assoc_item, i @ Impl) => {
|
||||
if !assoc_item.attrs.iter().any(|a| a.id == attr.id) {
|
||||
Annotatable::AssocItem(ref mut assoc_item, i @ Impl { of_trait: false }) => {
|
||||
if !assoc_item.attrs.iter().any(|a| same_attribute(&a.kind, &attr.kind)) {
|
||||
assoc_item.attrs.push(attr);
|
||||
}
|
||||
if !assoc_item.attrs.iter().any(|a| a.id == inline_never.id) {
|
||||
if !assoc_item.attrs.iter().any(|a| same_attribute(&a.kind, &inline_never.kind)) {
|
||||
assoc_item.attrs.push(inline_never.clone());
|
||||
}
|
||||
Annotatable::AssocItem(assoc_item.clone(), i)
|
||||
@ -314,13 +313,7 @@ mod llvm_enzyme {
|
||||
delim: rustc_ast::token::Delimiter::Parenthesis,
|
||||
tokens: ts,
|
||||
});
|
||||
let d_attr: ast::Attribute = ast::Attribute {
|
||||
kind: ast::AttrKind::Normal(rustc_ad_attr.clone()),
|
||||
id: new_id,
|
||||
style: ast::AttrStyle::Outer,
|
||||
span,
|
||||
};
|
||||
|
||||
let d_attr = outer_normal_attr(&rustc_ad_attr, new_id, span);
|
||||
let d_annotatable = if is_impl {
|
||||
let assoc_item: AssocItemKind = ast::AssocItemKind::Fn(asdf);
|
||||
let d_fn = P(ast::AssocItem {
|
||||
@ -328,14 +321,12 @@ mod llvm_enzyme {
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
span,
|
||||
vis,
|
||||
ident: d_ident,
|
||||
kind: assoc_item,
|
||||
tokens: None,
|
||||
});
|
||||
Annotatable::AssocItem(d_fn, Impl)
|
||||
Annotatable::AssocItem(d_fn, Impl { of_trait: false })
|
||||
} else {
|
||||
let mut d_fn =
|
||||
ecx.item(span, d_ident, thin_vec![d_attr, inline_never], ItemKind::Fn(asdf));
|
||||
let mut d_fn = ecx.item(span, thin_vec![d_attr, inline_never], ItemKind::Fn(asdf));
|
||||
d_fn.vis = vis;
|
||||
Annotatable::Item(d_fn)
|
||||
};
|
||||
@ -361,30 +352,27 @@ mod llvm_enzyme {
|
||||
ty
|
||||
}
|
||||
|
||||
/// We only want this function to type-check, since we will replace the body
|
||||
/// later on llvm level. Using `loop {}` does not cover all return types anymore,
|
||||
/// so instead we build something that should pass. We also add a inline_asm
|
||||
/// line, as one more barrier for rustc to prevent inlining of this function.
|
||||
/// FIXME(ZuseZ4): We still have cases of incorrect inlining across modules, see
|
||||
/// <https://github.com/EnzymeAD/rust/issues/173>, so this isn't sufficient.
|
||||
/// It also triggers an Enzyme crash if we due to a bug ever try to differentiate
|
||||
/// this function (which should never happen, since it is only a placeholder).
|
||||
/// Finally, we also add back_box usages of all input arguments, to prevent rustc
|
||||
/// from optimizing any arguments away.
|
||||
fn gen_enzyme_body(
|
||||
// Will generate a body of the type:
|
||||
// ```
|
||||
// {
|
||||
// unsafe {
|
||||
// asm!("NOP");
|
||||
// }
|
||||
// ::core::hint::black_box(primal(args));
|
||||
// ::core::hint::black_box((args, ret));
|
||||
// <This part remains to be done by following function>
|
||||
// }
|
||||
// ```
|
||||
fn init_body_helper(
|
||||
ecx: &ExtCtxt<'_>,
|
||||
x: &AutoDiffAttrs,
|
||||
n_active: u32,
|
||||
sig: &ast::FnSig,
|
||||
d_sig: &ast::FnSig,
|
||||
span: Span,
|
||||
primal: Ident,
|
||||
new_names: &[String],
|
||||
span: Span,
|
||||
sig_span: Span,
|
||||
new_decl_span: Span,
|
||||
idents: Vec<Ident>,
|
||||
idents: &[Ident],
|
||||
errored: bool,
|
||||
) -> P<ast::Block> {
|
||||
) -> (P<ast::Block>, P<ast::Expr>, P<ast::Expr>, P<ast::Expr>) {
|
||||
let blackbox_path = ecx.std_path(&[sym::hint, sym::black_box]);
|
||||
let noop = ast::InlineAsm {
|
||||
asm_macro: ast::AsmMacro::Asm,
|
||||
@ -403,7 +391,6 @@ mod llvm_enzyme {
|
||||
tokens: None,
|
||||
rules: unsf,
|
||||
span,
|
||||
could_be_bare_literal: false,
|
||||
};
|
||||
let unsf_expr = ecx.expr_block(P(unsf_block));
|
||||
let blackbox_call_expr = ecx.expr_path(ecx.path(span, blackbox_path));
|
||||
@ -433,6 +420,51 @@ mod llvm_enzyme {
|
||||
}
|
||||
body.stmts.push(ecx.stmt_semi(black_box_remaining_args));
|
||||
|
||||
(body, primal_call, black_box_primal_call, blackbox_call_expr)
|
||||
}
|
||||
|
||||
/// We only want this function to type-check, since we will replace the body
|
||||
/// later on llvm level. Using `loop {}` does not cover all return types anymore,
|
||||
/// so instead we manually build something that should pass the type checker.
|
||||
/// We also add a inline_asm line, as one more barrier for rustc to prevent inlining
|
||||
/// or const propagation. inline_asm will also triggers an Enzyme crash if due to another
|
||||
/// bug would ever try to accidentially differentiate this placeholder function body.
|
||||
/// Finally, we also add back_box usages of all input arguments, to prevent rustc
|
||||
/// from optimizing any arguments away.
|
||||
fn gen_enzyme_body(
|
||||
ecx: &ExtCtxt<'_>,
|
||||
x: &AutoDiffAttrs,
|
||||
n_active: u32,
|
||||
sig: &ast::FnSig,
|
||||
d_sig: &ast::FnSig,
|
||||
primal: Ident,
|
||||
new_names: &[String],
|
||||
span: Span,
|
||||
sig_span: Span,
|
||||
idents: Vec<Ident>,
|
||||
errored: bool,
|
||||
) -> P<ast::Block> {
|
||||
let new_decl_span = d_sig.span;
|
||||
|
||||
// Just adding some default inline-asm and black_box usages to prevent early inlining
|
||||
// and optimizations which alter the function signature.
|
||||
//
|
||||
// The bb_primal_call is the black_box call of the primal function. We keep it around,
|
||||
// since it has the convenient property of returning the type of the primal function,
|
||||
// Remember, we only care to match types here.
|
||||
// No matter which return we pick, we always wrap it into a std::hint::black_box call,
|
||||
// to prevent rustc from propagating it into the caller.
|
||||
let (mut body, primal_call, bb_primal_call, bb_call_expr) = init_body_helper(
|
||||
ecx,
|
||||
span,
|
||||
primal,
|
||||
new_names,
|
||||
sig_span,
|
||||
new_decl_span,
|
||||
&idents,
|
||||
errored,
|
||||
);
|
||||
|
||||
if !has_ret(&d_sig.decl.output) {
|
||||
// there is no return type that we have to match, () works fine.
|
||||
return body;
|
||||
@ -444,7 +476,7 @@ mod llvm_enzyme {
|
||||
|
||||
if primal_ret && n_active == 0 && x.mode.is_rev() {
|
||||
// We only have the primal ret.
|
||||
body.stmts.push(ecx.stmt_expr(black_box_primal_call));
|
||||
body.stmts.push(ecx.stmt_expr(bb_primal_call));
|
||||
return body;
|
||||
}
|
||||
|
||||
@ -536,11 +568,11 @@ mod llvm_enzyme {
|
||||
return body;
|
||||
}
|
||||
[arg] => {
|
||||
ret = ecx.expr_call(new_decl_span, blackbox_call_expr, thin_vec![arg.clone()]);
|
||||
ret = ecx.expr_call(new_decl_span, bb_call_expr, thin_vec![arg.clone()]);
|
||||
}
|
||||
args => {
|
||||
let ret_tuple: P<ast::Expr> = ecx.expr_tuple(span, args.into());
|
||||
ret = ecx.expr_call(new_decl_span, blackbox_call_expr, thin_vec![ret_tuple]);
|
||||
ret = ecx.expr_call(new_decl_span, bb_call_expr, thin_vec![ret_tuple]);
|
||||
}
|
||||
}
|
||||
assert!(has_ret(&d_sig.decl.output));
|
||||
@ -553,7 +585,7 @@ mod llvm_enzyme {
|
||||
ecx: &ExtCtxt<'_>,
|
||||
span: Span,
|
||||
primal: Ident,
|
||||
idents: Vec<Ident>,
|
||||
idents: &[Ident],
|
||||
) -> P<ast::Expr> {
|
||||
let has_self = idents.len() > 0 && idents[0].name == kw::SelfLower;
|
||||
if has_self {
|
||||
|
@ -121,18 +121,11 @@ impl CfgEval<'_> {
|
||||
let item = parser.parse_item(ForceCollect::Yes)?.unwrap();
|
||||
Annotatable::Item(self.flat_map_item(item).pop().unwrap())
|
||||
}
|
||||
Annotatable::AssocItem(_, AssocCtxt::Trait) => {
|
||||
Annotatable::AssocItem(_, ctxt) => {
|
||||
let item = parser.parse_trait_item(ForceCollect::Yes)?.unwrap().unwrap();
|
||||
Annotatable::AssocItem(
|
||||
self.flat_map_assoc_item(item, AssocCtxt::Trait).pop().unwrap(),
|
||||
AssocCtxt::Trait,
|
||||
)
|
||||
}
|
||||
Annotatable::AssocItem(_, AssocCtxt::Impl) => {
|
||||
let item = parser.parse_impl_item(ForceCollect::Yes)?.unwrap().unwrap();
|
||||
Annotatable::AssocItem(
|
||||
self.flat_map_assoc_item(item, AssocCtxt::Impl).pop().unwrap(),
|
||||
AssocCtxt::Impl,
|
||||
self.flat_map_assoc_item(item, ctxt).pop().unwrap(),
|
||||
ctxt,
|
||||
)
|
||||
}
|
||||
Annotatable::ForeignItem(_) => {
|
||||
|
@ -11,15 +11,20 @@ pub(crate) fn expand(
|
||||
let define_opaque = match &mut item {
|
||||
Annotatable::Item(p) => match &mut p.kind {
|
||||
ast::ItemKind::Fn(f) => Some(&mut f.define_opaque),
|
||||
ast::ItemKind::Const(ct) => Some(&mut ct.define_opaque),
|
||||
ast::ItemKind::Static(si) => Some(&mut si.define_opaque),
|
||||
_ => None,
|
||||
},
|
||||
Annotatable::AssocItem(i, _assoc_ctxt) => match &mut i.kind {
|
||||
ast::AssocItemKind::Fn(func) => Some(&mut func.define_opaque),
|
||||
ast::AssocItemKind::Const(ct) => Some(&mut ct.define_opaque),
|
||||
_ => None,
|
||||
},
|
||||
Annotatable::Stmt(s) => match &mut s.kind {
|
||||
ast::StmtKind::Item(p) => match &mut p.kind {
|
||||
ast::ItemKind::Fn(f) => Some(&mut f.define_opaque),
|
||||
ast::ItemKind::Const(ct) => Some(&mut ct.define_opaque),
|
||||
ast::ItemKind::Static(si) => Some(&mut si.define_opaque),
|
||||
_ => None,
|
||||
},
|
||||
_ => None,
|
||||
@ -47,7 +52,10 @@ pub(crate) fn expand(
|
||||
.collect(),
|
||||
);
|
||||
} else {
|
||||
ecx.dcx().span_err(meta_item.span, "only functions and methods can define opaque types");
|
||||
ecx.dcx().span_err(
|
||||
meta_item.span,
|
||||
"only functions, statics, and consts can define opaque types",
|
||||
);
|
||||
}
|
||||
|
||||
vec![item]
|
||||
|
@ -103,7 +103,7 @@ impl MultiItemModifier for Expander {
|
||||
fn dummy_annotatable() -> Annotatable {
|
||||
Annotatable::GenericParam(ast::GenericParam {
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
ident: Ident::empty(),
|
||||
ident: Ident::dummy(),
|
||||
attrs: Default::default(),
|
||||
bounds: Default::default(),
|
||||
is_placeholder: false,
|
||||
|
@ -34,8 +34,8 @@ pub(crate) fn expand_deriving_clone(
|
||||
let is_simple;
|
||||
match item {
|
||||
Annotatable::Item(annitem) => match &annitem.kind {
|
||||
ItemKind::Struct(_, Generics { params, .. })
|
||||
| ItemKind::Enum(_, Generics { params, .. }) => {
|
||||
ItemKind::Struct(_, _, Generics { params, .. })
|
||||
| ItemKind::Enum(_, _, Generics { params, .. }) => {
|
||||
let container_id = cx.current_expansion.id.expn_data().parent.expect_local();
|
||||
let has_derive_copy = cx.resolver.has_derive_copy(container_id);
|
||||
if has_derive_copy
|
||||
|
@ -21,7 +21,7 @@ pub(crate) fn expand_deriving_partial_ord(
|
||||
|
||||
// Order in which to perform matching
|
||||
let discr_then_data = if let Annotatable::Item(item) = item
|
||||
&& let ItemKind::Enum(def, _) = &item.kind
|
||||
&& let ItemKind::Enum(_, def, _) = &item.kind
|
||||
{
|
||||
let dataful: Vec<bool> = def.variants.iter().map(|v| !v.data.fields().is_empty()).collect();
|
||||
match dataful.iter().filter(|&&b| b).count() {
|
||||
|
@ -30,7 +30,7 @@ pub(crate) fn expand_deriving_coerce_pointee(
|
||||
item.visit_with(&mut DetectNonGenericPointeeAttr { cx });
|
||||
|
||||
let (name_ident, generics) = if let Annotatable::Item(aitem) = item
|
||||
&& let ItemKind::Struct(struct_data, g) = &aitem.kind
|
||||
&& let ItemKind::Struct(ident, struct_data, g) = &aitem.kind
|
||||
{
|
||||
if !matches!(
|
||||
struct_data,
|
||||
@ -40,7 +40,7 @@ pub(crate) fn expand_deriving_coerce_pointee(
|
||||
cx.dcx().emit_err(RequireOneField { span });
|
||||
return;
|
||||
}
|
||||
(aitem.ident, g)
|
||||
(*ident, g)
|
||||
} else {
|
||||
cx.dcx().emit_err(RequireTransparent { span });
|
||||
return;
|
||||
@ -108,7 +108,6 @@ pub(crate) fn expand_deriving_coerce_pointee(
|
||||
push(Annotatable::Item(
|
||||
cx.item(
|
||||
span,
|
||||
Ident::empty(),
|
||||
attrs.clone(),
|
||||
ast::ItemKind::Impl(Box::new(ast::Impl {
|
||||
safety: ast::Safety::Default,
|
||||
@ -153,7 +152,6 @@ pub(crate) fn expand_deriving_coerce_pointee(
|
||||
let trait_ref = cx.trait_ref(trait_path);
|
||||
let item = cx.item(
|
||||
span,
|
||||
Ident::empty(),
|
||||
attrs.clone(),
|
||||
ast::ItemKind::Impl(Box::new(ast::Impl {
|
||||
safety: ast::Safety::Default,
|
||||
|
@ -487,28 +487,28 @@ impl<'a> TraitDef<'a> {
|
||||
);
|
||||
|
||||
let newitem = match &item.kind {
|
||||
ast::ItemKind::Struct(struct_def, generics) => self.expand_struct_def(
|
||||
ast::ItemKind::Struct(ident, struct_def, generics) => self.expand_struct_def(
|
||||
cx,
|
||||
struct_def,
|
||||
item.ident,
|
||||
*ident,
|
||||
generics,
|
||||
from_scratch,
|
||||
is_packed,
|
||||
),
|
||||
ast::ItemKind::Enum(enum_def, generics) => {
|
||||
ast::ItemKind::Enum(ident, enum_def, generics) => {
|
||||
// We ignore `is_packed` here, because `repr(packed)`
|
||||
// enums cause an error later on.
|
||||
//
|
||||
// This can only cause further compilation errors
|
||||
// downstream in blatantly illegal code, so it is fine.
|
||||
self.expand_enum_def(cx, enum_def, item.ident, generics, from_scratch)
|
||||
self.expand_enum_def(cx, enum_def, *ident, generics, from_scratch)
|
||||
}
|
||||
ast::ItemKind::Union(struct_def, generics) => {
|
||||
ast::ItemKind::Union(ident, struct_def, generics) => {
|
||||
if self.supports_unions {
|
||||
self.expand_struct_def(
|
||||
cx,
|
||||
struct_def,
|
||||
item.ident,
|
||||
*ident,
|
||||
generics,
|
||||
from_scratch,
|
||||
is_packed,
|
||||
@ -596,7 +596,6 @@ impl<'a> TraitDef<'a> {
|
||||
P(ast::AssocItem {
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
span: self.span,
|
||||
ident,
|
||||
vis: ast::Visibility {
|
||||
span: self.span.shrink_to_lo(),
|
||||
kind: ast::VisibilityKind::Inherited,
|
||||
@ -605,6 +604,7 @@ impl<'a> TraitDef<'a> {
|
||||
attrs: ast::AttrVec::new(),
|
||||
kind: ast::AssocItemKind::Type(Box::new(ast::TyAlias {
|
||||
defaultness: ast::Defaultness::Final,
|
||||
ident,
|
||||
generics: Generics::default(),
|
||||
where_clauses: ast::TyAliasWhereClauses::default(),
|
||||
bounds: Vec::new(),
|
||||
@ -789,7 +789,6 @@ impl<'a> TraitDef<'a> {
|
||||
|
||||
cx.item(
|
||||
self.span,
|
||||
Ident::empty(),
|
||||
attrs,
|
||||
ast::ItemKind::Impl(Box::new(ast::Impl {
|
||||
safety: ast::Safety::Default,
|
||||
@ -1033,10 +1032,10 @@ impl<'a> MethodDef<'a> {
|
||||
kind: ast::VisibilityKind::Inherited,
|
||||
tokens: None,
|
||||
},
|
||||
ident: method_ident,
|
||||
kind: ast::AssocItemKind::Fn(Box::new(ast::Fn {
|
||||
defaultness,
|
||||
sig,
|
||||
ident: method_ident,
|
||||
generics: fn_generics,
|
||||
contract: None,
|
||||
body: Some(body_block),
|
||||
|
@ -110,7 +110,6 @@ fn call_unreachable(cx: &ExtCtxt<'_>, span: Span) -> P<ast::Expr> {
|
||||
rules: ast::BlockCheckMode::Unsafe(ast::CompilerGenerated),
|
||||
span,
|
||||
tokens: None,
|
||||
could_be_bare_literal: false,
|
||||
}))
|
||||
}
|
||||
|
||||
|
@ -74,11 +74,11 @@ pub(crate) fn use_panic_2021(mut span: Span) -> bool {
|
||||
// (To avoid using the edition of e.g. the assert!() or debug_assert!() definition.)
|
||||
loop {
|
||||
let expn = span.ctxt().outer_expn_data();
|
||||
if let Some(features) = expn.allow_internal_unstable {
|
||||
if features.iter().any(|&f| f == sym::edition_panic) {
|
||||
span = expn.call_site;
|
||||
continue;
|
||||
}
|
||||
if let Some(features) = expn.allow_internal_unstable
|
||||
&& features.contains(&sym::edition_panic)
|
||||
{
|
||||
span = expn.call_site;
|
||||
continue;
|
||||
}
|
||||
break expn.edition >= Edition::Edition2021;
|
||||
}
|
||||
|
@ -25,15 +25,15 @@ pub(crate) fn expand(
|
||||
|
||||
// Allow using `#[global_allocator]` on an item statement
|
||||
// FIXME - if we get deref patterns, use them to reduce duplication here
|
||||
let (item, is_stmt, ty_span) = if let Annotatable::Item(item) = &item
|
||||
&& let ItemKind::Static(box ast::StaticItem { ty, .. }) = &item.kind
|
||||
let (item, ident, is_stmt, ty_span) = if let Annotatable::Item(item) = &item
|
||||
&& let ItemKind::Static(box ast::StaticItem { ident, ty, .. }) = &item.kind
|
||||
{
|
||||
(item, false, ecx.with_def_site_ctxt(ty.span))
|
||||
(item, *ident, false, ecx.with_def_site_ctxt(ty.span))
|
||||
} else if let Annotatable::Stmt(stmt) = &item
|
||||
&& let StmtKind::Item(item) = &stmt.kind
|
||||
&& let ItemKind::Static(box ast::StaticItem { ty, .. }) = &item.kind
|
||||
&& let ItemKind::Static(box ast::StaticItem { ident, ty, .. }) = &item.kind
|
||||
{
|
||||
(item, true, ecx.with_def_site_ctxt(ty.span))
|
||||
(item, *ident, true, ecx.with_def_site_ctxt(ty.span))
|
||||
} else {
|
||||
ecx.dcx().emit_err(errors::AllocMustStatics { span: item.span() });
|
||||
return vec![orig_item];
|
||||
@ -41,7 +41,7 @@ pub(crate) fn expand(
|
||||
|
||||
// Generate a bunch of new items using the AllocFnFactory
|
||||
let span = ecx.with_def_site_ctxt(item.span);
|
||||
let f = AllocFnFactory { span, ty_span, global: item.ident, cx: ecx };
|
||||
let f = AllocFnFactory { span, ty_span, global: ident, cx: ecx };
|
||||
|
||||
// Generate item statements for the allocator methods.
|
||||
let stmts = ALLOCATOR_METHODS.iter().map(|method| f.allocator_fn(method)).collect();
|
||||
@ -80,17 +80,13 @@ impl AllocFnFactory<'_, '_> {
|
||||
let kind = ItemKind::Fn(Box::new(Fn {
|
||||
defaultness: ast::Defaultness::Final,
|
||||
sig,
|
||||
ident: Ident::from_str_and_span(&global_fn_name(method.name), self.span),
|
||||
generics: Generics::default(),
|
||||
contract: None,
|
||||
body,
|
||||
define_opaque: None,
|
||||
}));
|
||||
let item = self.cx.item(
|
||||
self.span,
|
||||
Ident::from_str_and_span(&global_fn_name(method.name), self.span),
|
||||
self.attrs(),
|
||||
kind,
|
||||
);
|
||||
let item = self.cx.item(self.span, self.attrs(), kind);
|
||||
self.cx.stmt_item(self.ty_span, item)
|
||||
}
|
||||
|
||||
|
@ -23,6 +23,8 @@
|
||||
|
||||
extern crate proc_macro;
|
||||
|
||||
use std::sync::Arc;
|
||||
|
||||
use rustc_expand::base::{MacroExpanderFn, ResolverExpand, SyntaxExtensionKind};
|
||||
use rustc_expand::proc_macro::BangProcMacro;
|
||||
use rustc_span::sym;
|
||||
@ -67,13 +69,13 @@ rustc_fluent_macro::fluent_messages! { "../messages.ftl" }
|
||||
pub fn register_builtin_macros(resolver: &mut dyn ResolverExpand) {
|
||||
let mut register = |name, kind| resolver.register_builtin_macro(name, kind);
|
||||
macro register_bang($($name:ident: $f:expr,)*) {
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyBang(Box::new($f as MacroExpanderFn)));)*
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyBang(Arc::new($f as MacroExpanderFn)));)*
|
||||
}
|
||||
macro register_attr($($name:ident: $f:expr,)*) {
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyAttr(Box::new($f)));)*
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyAttr(Arc::new($f)));)*
|
||||
}
|
||||
macro register_derive($($name:ident: $f:expr,)*) {
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyDerive(Box::new(BuiltinDerive($f))));)*
|
||||
$(register(sym::$name, SyntaxExtensionKind::LegacyDerive(Arc::new(BuiltinDerive($f))));)*
|
||||
}
|
||||
|
||||
register_bang! {
|
||||
@ -139,9 +141,9 @@ pub fn register_builtin_macros(resolver: &mut dyn ResolverExpand) {
|
||||
}
|
||||
|
||||
let client = proc_macro::bridge::client::Client::expand1(proc_macro::quote);
|
||||
register(sym::quote, SyntaxExtensionKind::Bang(Box::new(BangProcMacro { client })));
|
||||
let requires = SyntaxExtensionKind::Attr(Box::new(contracts::ExpandRequires));
|
||||
register(sym::quote, SyntaxExtensionKind::Bang(Arc::new(BangProcMacro { client })));
|
||||
let requires = SyntaxExtensionKind::Attr(Arc::new(contracts::ExpandRequires));
|
||||
register(sym::contracts_requires, requires);
|
||||
let ensures = SyntaxExtensionKind::Attr(Box::new(contracts::ExpandEnsures));
|
||||
let ensures = SyntaxExtensionKind::Attr(Arc::new(contracts::ExpandEnsures));
|
||||
register(sym::contracts_ensures, ensures);
|
||||
}
|
||||
|
@ -92,7 +92,12 @@ impl<'a> CollectProcMacros<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn collect_custom_derive(&mut self, item: &'a ast::Item, attr: &'a ast::Attribute) {
|
||||
fn collect_custom_derive(
|
||||
&mut self,
|
||||
item: &'a ast::Item,
|
||||
function_name: Ident,
|
||||
attr: &'a ast::Attribute,
|
||||
) {
|
||||
let Some((trait_name, proc_attrs)) =
|
||||
parse_macro_name_and_helper_attrs(self.dcx, attr, "derive")
|
||||
else {
|
||||
@ -104,7 +109,7 @@ impl<'a> CollectProcMacros<'a> {
|
||||
id: item.id,
|
||||
span: item.span,
|
||||
trait_name,
|
||||
function_name: item.ident,
|
||||
function_name,
|
||||
attrs: proc_attrs,
|
||||
}));
|
||||
} else {
|
||||
@ -118,12 +123,12 @@ impl<'a> CollectProcMacros<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn collect_attr_proc_macro(&mut self, item: &'a ast::Item) {
|
||||
fn collect_attr_proc_macro(&mut self, item: &'a ast::Item, function_name: Ident) {
|
||||
if self.in_root && item.vis.kind.is_pub() {
|
||||
self.macros.push(ProcMacro::Attr(ProcMacroDef {
|
||||
id: item.id,
|
||||
span: item.span,
|
||||
function_name: item.ident,
|
||||
function_name,
|
||||
}));
|
||||
} else {
|
||||
let msg = if !self.in_root {
|
||||
@ -136,12 +141,12 @@ impl<'a> CollectProcMacros<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn collect_bang_proc_macro(&mut self, item: &'a ast::Item) {
|
||||
fn collect_bang_proc_macro(&mut self, item: &'a ast::Item, function_name: Ident) {
|
||||
if self.in_root && item.vis.kind.is_pub() {
|
||||
self.macros.push(ProcMacro::Bang(ProcMacroDef {
|
||||
id: item.id,
|
||||
span: item.span,
|
||||
function_name: item.ident,
|
||||
function_name,
|
||||
}));
|
||||
} else {
|
||||
let msg = if !self.in_root {
|
||||
@ -165,12 +170,6 @@ impl<'a> Visitor<'a> for CollectProcMacros<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
// First up, make sure we're checking a bare function. If we're not then
|
||||
// we're just not interested in this item.
|
||||
//
|
||||
// If we find one, try to locate a `#[proc_macro_derive]` attribute on it.
|
||||
let is_fn = matches!(item.kind, ast::ItemKind::Fn(..));
|
||||
|
||||
let mut found_attr: Option<&'a ast::Attribute> = None;
|
||||
|
||||
for attr in &item.attrs {
|
||||
@ -214,7 +213,11 @@ impl<'a> Visitor<'a> for CollectProcMacros<'a> {
|
||||
return;
|
||||
};
|
||||
|
||||
if !is_fn {
|
||||
// Make sure we're checking a bare function. If we're not then we're
|
||||
// just not interested any further in this item.
|
||||
let fn_ident = if let ast::ItemKind::Fn(fn_) = &item.kind {
|
||||
fn_.ident
|
||||
} else {
|
||||
self.dcx
|
||||
.create_err(errors::AttributeOnlyBeUsedOnBareFunctions {
|
||||
span: attr.span,
|
||||
@ -222,7 +225,7 @@ impl<'a> Visitor<'a> for CollectProcMacros<'a> {
|
||||
})
|
||||
.emit();
|
||||
return;
|
||||
}
|
||||
};
|
||||
|
||||
if self.is_test_crate {
|
||||
return;
|
||||
@ -238,12 +241,13 @@ impl<'a> Visitor<'a> for CollectProcMacros<'a> {
|
||||
return;
|
||||
}
|
||||
|
||||
// Try to locate a `#[proc_macro_derive]` attribute.
|
||||
if attr.has_name(sym::proc_macro_derive) {
|
||||
self.collect_custom_derive(item, attr);
|
||||
self.collect_custom_derive(item, fn_ident, attr);
|
||||
} else if attr.has_name(sym::proc_macro_attribute) {
|
||||
self.collect_attr_proc_macro(item);
|
||||
self.collect_attr_proc_macro(item, fn_ident);
|
||||
} else if attr.has_name(sym::proc_macro) {
|
||||
self.collect_bang_proc_macro(item);
|
||||
self.collect_bang_proc_macro(item, fn_ident);
|
||||
};
|
||||
|
||||
let prev_in_root = mem::replace(&mut self.in_root, false);
|
||||
@ -278,7 +282,7 @@ fn mk_decls(cx: &mut ExtCtxt<'_>, macros: &[ProcMacro]) -> P<ast::Item> {
|
||||
let span = DUMMY_SP.with_def_site_ctxt(expn_id.to_expn_id());
|
||||
|
||||
let proc_macro = Ident::new(sym::proc_macro, span);
|
||||
let krate = cx.item(span, proc_macro, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None));
|
||||
let krate = cx.item(span, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None, proc_macro));
|
||||
|
||||
let bridge = Ident::new(sym::bridge, span);
|
||||
let client = Ident::new(sym::client, span);
|
||||
|
@ -43,9 +43,8 @@ pub fn inject(
|
||||
|
||||
let item = cx.item(
|
||||
span,
|
||||
Ident::new(name, ident_span),
|
||||
thin_vec![cx.attr_word(sym::macro_use, span)],
|
||||
ast::ItemKind::ExternCrate(None),
|
||||
ast::ItemKind::ExternCrate(None, Ident::new(name, ident_span)),
|
||||
);
|
||||
|
||||
krate.items.insert(0, item);
|
||||
@ -68,7 +67,6 @@ pub fn inject(
|
||||
// Inject the relevant crate's prelude.
|
||||
let use_item = cx.item(
|
||||
span,
|
||||
Ident::empty(),
|
||||
thin_vec![cx.attr_word(sym::prelude_import, span)],
|
||||
ast::ItemKind::Use(ast::UseTree {
|
||||
prefix: cx.path(span, import_path),
|
||||
|
@ -51,21 +51,28 @@ pub(crate) fn expand_test_case(
|
||||
return vec![];
|
||||
}
|
||||
};
|
||||
item = item.map(|mut item| {
|
||||
let test_path_symbol = Symbol::intern(&item_path(
|
||||
// skip the name of the root module
|
||||
&ecx.current_expansion.module.mod_path[1..],
|
||||
&item.ident,
|
||||
));
|
||||
item.vis = ast::Visibility {
|
||||
span: item.vis.span,
|
||||
kind: ast::VisibilityKind::Public,
|
||||
tokens: None,
|
||||
};
|
||||
item.ident.span = item.ident.span.with_ctxt(sp.ctxt());
|
||||
item.attrs.push(ecx.attr_name_value_str(sym::rustc_test_marker, test_path_symbol, sp));
|
||||
item
|
||||
});
|
||||
|
||||
// `#[test_case]` is valid on functions, consts, and statics. Only modify
|
||||
// the item in those cases.
|
||||
match &mut item.kind {
|
||||
ast::ItemKind::Fn(box ast::Fn { ident, .. })
|
||||
| ast::ItemKind::Const(box ast::ConstItem { ident, .. })
|
||||
| ast::ItemKind::Static(box ast::StaticItem { ident, .. }) => {
|
||||
ident.span = ident.span.with_ctxt(sp.ctxt());
|
||||
let test_path_symbol = Symbol::intern(&item_path(
|
||||
// skip the name of the root module
|
||||
&ecx.current_expansion.module.mod_path[1..],
|
||||
ident,
|
||||
));
|
||||
item.vis = ast::Visibility {
|
||||
span: item.vis.span,
|
||||
kind: ast::VisibilityKind::Public,
|
||||
tokens: None,
|
||||
};
|
||||
item.attrs.push(ecx.attr_name_value_str(sym::rustc_test_marker, test_path_symbol, sp));
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
|
||||
let ret = if is_stmt {
|
||||
Annotatable::Stmt(P(ecx.stmt_item(item.span, item)))
|
||||
@ -162,17 +169,17 @@ pub(crate) fn expand_test_or_bench(
|
||||
let ret_ty_sp = cx.with_def_site_ctxt(fn_.sig.decl.output.span());
|
||||
let attr_sp = cx.with_def_site_ctxt(attr_sp);
|
||||
|
||||
let test_id = Ident::new(sym::test, attr_sp);
|
||||
let test_ident = Ident::new(sym::test, attr_sp);
|
||||
|
||||
// creates test::$name
|
||||
let test_path = |name| cx.path(ret_ty_sp, vec![test_id, Ident::from_str_and_span(name, sp)]);
|
||||
let test_path = |name| cx.path(ret_ty_sp, vec![test_ident, Ident::from_str_and_span(name, sp)]);
|
||||
|
||||
// creates test::ShouldPanic::$name
|
||||
let should_panic_path = |name| {
|
||||
cx.path(
|
||||
sp,
|
||||
vec![
|
||||
test_id,
|
||||
test_ident,
|
||||
Ident::from_str_and_span("ShouldPanic", sp),
|
||||
Ident::from_str_and_span(name, sp),
|
||||
],
|
||||
@ -184,7 +191,7 @@ pub(crate) fn expand_test_or_bench(
|
||||
cx.path(
|
||||
sp,
|
||||
vec![
|
||||
test_id,
|
||||
test_ident,
|
||||
Ident::from_str_and_span("TestType", sp),
|
||||
Ident::from_str_and_span(name, sp),
|
||||
],
|
||||
@ -223,7 +230,7 @@ pub(crate) fn expand_test_or_bench(
|
||||
// super::$test_fn(b)
|
||||
cx.expr_call(
|
||||
ret_ty_sp,
|
||||
cx.expr_path(cx.path(sp, vec![item.ident])),
|
||||
cx.expr_path(cx.path(sp, vec![fn_.ident])),
|
||||
thin_vec![cx.expr_ident(sp, b)],
|
||||
),
|
||||
],
|
||||
@ -249,7 +256,7 @@ pub(crate) fn expand_test_or_bench(
|
||||
// $test_fn()
|
||||
cx.expr_call(
|
||||
ret_ty_sp,
|
||||
cx.expr_path(cx.path(sp, vec![item.ident])),
|
||||
cx.expr_path(cx.path(sp, vec![fn_.ident])),
|
||||
ThinVec::new(),
|
||||
), // )
|
||||
],
|
||||
@ -262,15 +269,14 @@ pub(crate) fn expand_test_or_bench(
|
||||
let test_path_symbol = Symbol::intern(&item_path(
|
||||
// skip the name of the root module
|
||||
&cx.current_expansion.module.mod_path[1..],
|
||||
&item.ident,
|
||||
&fn_.ident,
|
||||
));
|
||||
|
||||
let location_info = get_location_info(cx, &item);
|
||||
let location_info = get_location_info(cx, &fn_);
|
||||
|
||||
let mut test_const =
|
||||
cx.item(
|
||||
sp,
|
||||
Ident::new(item.ident.name, sp),
|
||||
thin_vec![
|
||||
// #[cfg(test)]
|
||||
cx.attr_nested_word(sym::cfg, sym::test, attr_sp),
|
||||
@ -283,8 +289,10 @@ pub(crate) fn expand_test_or_bench(
|
||||
ast::ItemKind::Const(
|
||||
ast::ConstItem {
|
||||
defaultness: ast::Defaultness::Final,
|
||||
ident: Ident::new(fn_.ident.name, sp),
|
||||
generics: ast::Generics::default(),
|
||||
ty: cx.ty(sp, ast::TyKind::Path(None, test_path("TestDescAndFn"))),
|
||||
define_opaque: None,
|
||||
// test::TestDescAndFn {
|
||||
expr: Some(
|
||||
cx.expr_struct(
|
||||
@ -379,7 +387,8 @@ pub(crate) fn expand_test_or_bench(
|
||||
});
|
||||
|
||||
// extern crate test
|
||||
let test_extern = cx.item(sp, test_id, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None));
|
||||
let test_extern =
|
||||
cx.item(sp, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None, test_ident));
|
||||
|
||||
debug!("synthetic test item:\n{}\n", pprust::item_to_string(&test_const));
|
||||
|
||||
@ -433,8 +442,8 @@ fn not_testable_error(cx: &ExtCtxt<'_>, attr_sp: Span, item: Option<&ast::Item>)
|
||||
.emit();
|
||||
}
|
||||
|
||||
fn get_location_info(cx: &ExtCtxt<'_>, item: &ast::Item) -> (Symbol, usize, usize, usize, usize) {
|
||||
let span = item.ident.span;
|
||||
fn get_location_info(cx: &ExtCtxt<'_>, fn_: &ast::Fn) -> (Symbol, usize, usize, usize, usize) {
|
||||
let span = fn_.ident.span;
|
||||
let (source_file, lo_line, lo_col, hi_line, hi_col) =
|
||||
cx.sess.source_map().span_to_location_info(span);
|
||||
|
||||
|
@ -134,27 +134,21 @@ impl<'a> MutVisitor for TestHarnessGenerator<'a> {
|
||||
if let Some(name) = get_test_name(&item) {
|
||||
debug!("this is a test item");
|
||||
|
||||
let test = Test { span: item.span, ident: item.ident, name };
|
||||
// `unwrap` is ok because only functions, consts, and static should reach here.
|
||||
let test = Test { span: item.span, ident: item.kind.ident().unwrap(), name };
|
||||
self.tests.push(test);
|
||||
}
|
||||
|
||||
// We don't want to recurse into anything other than mods, since
|
||||
// mods or tests inside of functions will break things
|
||||
if let ast::ItemKind::Mod(
|
||||
_,
|
||||
_,
|
||||
ModKind::Loaded(.., ast::ModSpans { inner_span: span, .. }, _),
|
||||
) = item.kind
|
||||
{
|
||||
let prev_tests = mem::take(&mut self.tests);
|
||||
walk_item_kind(
|
||||
&mut item.kind,
|
||||
item.span,
|
||||
item.id,
|
||||
&mut item.ident,
|
||||
&mut item.vis,
|
||||
(),
|
||||
self,
|
||||
);
|
||||
walk_item_kind(&mut item.kind, item.span, item.id, &mut item.vis, (), self);
|
||||
self.add_test_cases(item.id, span, prev_tests);
|
||||
} else {
|
||||
// But in those cases, we emit a lint to warn the user of these missing tests.
|
||||
@ -181,9 +175,9 @@ impl<'a> Visitor<'a> for InnerItemLinter<'_> {
|
||||
}
|
||||
|
||||
fn entry_point_type(item: &ast::Item, at_root: bool) -> EntryPointType {
|
||||
match item.kind {
|
||||
ast::ItemKind::Fn(..) => {
|
||||
rustc_ast::entry::entry_point_type(&item.attrs, at_root, Some(item.ident.name))
|
||||
match &item.kind {
|
||||
ast::ItemKind::Fn(fn_) => {
|
||||
rustc_ast::entry::entry_point_type(&item.attrs, at_root, Some(fn_.ident.name))
|
||||
}
|
||||
_ => EntryPointType::None,
|
||||
}
|
||||
@ -295,7 +289,7 @@ fn generate_test_harness(
|
||||
fn mk_main(cx: &mut TestCtxt<'_>) -> P<ast::Item> {
|
||||
let sp = cx.def_site;
|
||||
let ecx = &cx.ext_cx;
|
||||
let test_id = Ident::new(sym::test, sp);
|
||||
let test_ident = Ident::new(sym::test, sp);
|
||||
|
||||
let runner_name = match cx.panic_strategy {
|
||||
PanicStrategy::Unwind => "test_main_static",
|
||||
@ -303,10 +297,9 @@ fn mk_main(cx: &mut TestCtxt<'_>) -> P<ast::Item> {
|
||||
};
|
||||
|
||||
// test::test_main_static(...)
|
||||
let mut test_runner = cx
|
||||
.test_runner
|
||||
.clone()
|
||||
.unwrap_or_else(|| ecx.path(sp, vec![test_id, Ident::from_str_and_span(runner_name, sp)]));
|
||||
let mut test_runner = cx.test_runner.clone().unwrap_or_else(|| {
|
||||
ecx.path(sp, vec![test_ident, Ident::from_str_and_span(runner_name, sp)])
|
||||
});
|
||||
|
||||
test_runner.span = sp;
|
||||
|
||||
@ -317,7 +310,7 @@ fn mk_main(cx: &mut TestCtxt<'_>) -> P<ast::Item> {
|
||||
// extern crate test
|
||||
let test_extern_stmt = ecx.stmt_item(
|
||||
sp,
|
||||
ecx.item(sp, test_id, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None)),
|
||||
ecx.item(sp, ast::AttrVec::new(), ast::ItemKind::ExternCrate(None, test_ident)),
|
||||
);
|
||||
|
||||
// #[rustc_main]
|
||||
@ -340,23 +333,24 @@ fn mk_main(cx: &mut TestCtxt<'_>) -> P<ast::Item> {
|
||||
let decl = ecx.fn_decl(ThinVec::new(), ast::FnRetTy::Ty(main_ret_ty));
|
||||
let sig = ast::FnSig { decl, header: ast::FnHeader::default(), span: sp };
|
||||
let defaultness = ast::Defaultness::Final;
|
||||
|
||||
// Honor the reexport_test_harness_main attribute
|
||||
let main_ident = match cx.reexport_test_harness_main {
|
||||
Some(sym) => Ident::new(sym, sp.with_ctxt(SyntaxContext::root())),
|
||||
None => Ident::new(sym::main, sp),
|
||||
};
|
||||
|
||||
let main = ast::ItemKind::Fn(Box::new(ast::Fn {
|
||||
defaultness,
|
||||
sig,
|
||||
ident: main_ident,
|
||||
generics: ast::Generics::default(),
|
||||
contract: None,
|
||||
body: Some(main_body),
|
||||
define_opaque: None,
|
||||
}));
|
||||
|
||||
// Honor the reexport_test_harness_main attribute
|
||||
let main_id = match cx.reexport_test_harness_main {
|
||||
Some(sym) => Ident::new(sym, sp.with_ctxt(SyntaxContext::root())),
|
||||
None => Ident::new(sym::main, sp),
|
||||
};
|
||||
|
||||
let main = P(ast::Item {
|
||||
ident: main_id,
|
||||
attrs: thin_vec![main_attr, coverage_attr, doc_hidden_attr],
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
kind: main,
|
||||
|
@ -1,20 +1,21 @@
|
||||
task:
|
||||
name: freebsd
|
||||
freebsd_instance:
|
||||
image: freebsd-13-2-release-amd64
|
||||
setup_rust_script:
|
||||
- pkg install -y git-tiny binutils
|
||||
- curl https://sh.rustup.rs -sSf --output rustup.sh
|
||||
- sh rustup.sh --default-toolchain none -y --profile=minimal
|
||||
target_cache:
|
||||
folder: build/cg_clif
|
||||
prepare_script:
|
||||
- . $HOME/.cargo/env
|
||||
- ./y.sh prepare
|
||||
test_script:
|
||||
- . $HOME/.cargo/env
|
||||
# Disabling incr comp reduces cache size and incr comp doesn't save as much
|
||||
# on CI anyway.
|
||||
- export CARGO_BUILD_INCREMENTAL=false
|
||||
# Skip rand as it fails on FreeBSD due to rust-random/rand#1355
|
||||
- ./y.sh test --skip-test test.rust-random/rand
|
||||
# FIXME re-enable once https://github.com/rust-lang/rust/issues/134863 is fixed.
|
||||
# task:
|
||||
# name: freebsd
|
||||
# freebsd_instance:
|
||||
# image: freebsd-13-2-release-amd64
|
||||
# setup_rust_script:
|
||||
# - pkg install -y git-tiny binutils
|
||||
# - curl https://sh.rustup.rs -sSf --output rustup.sh
|
||||
# - sh rustup.sh --default-toolchain none -y --profile=minimal
|
||||
# target_cache:
|
||||
# folder: build/cg_clif
|
||||
# prepare_script:
|
||||
# - . $HOME/.cargo/env
|
||||
# - ./y.sh prepare
|
||||
# test_script:
|
||||
# - . $HOME/.cargo/env
|
||||
# # Disabling incr comp reduces cache size and incr comp doesn't save as much
|
||||
# # on CI anyway.
|
||||
# - export CARGO_BUILD_INCREMENTAL=false
|
||||
# # Skip rand as it fails on FreeBSD due to rust-random/rand#1355
|
||||
# - ./y.sh test --skip-test test.rust-random/rand
|
||||
|
@ -1,18 +0,0 @@
|
||||
# github-release
|
||||
|
||||
An action used to publish GitHub releases for `wasmtime`.
|
||||
|
||||
As of the time of this writing there's a few actions floating around which
|
||||
perform github releases but they all tend to have their set of drawbacks.
|
||||
Additionally nothing handles deleting releases which we need for our rolling
|
||||
`dev` release.
|
||||
|
||||
To handle all this this action rolls-its-own implementation using the
|
||||
actions/toolkit repository and packages published there. These run in a Docker
|
||||
container and take various inputs to orchestrate the release from the build.
|
||||
|
||||
More comments can be found in `main.js`.
|
||||
|
||||
Testing this is really hard. If you want to try though run `npm install` and
|
||||
then `node main.js`. You'll have to configure a bunch of env vars though to get
|
||||
anything reasonably working.
|
@ -1,13 +0,0 @@
|
||||
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
name: 'rustc_codegen_cranelift github releases'
|
||||
description: 'rustc_codegen_cranelift github releases'
|
||||
inputs:
|
||||
token:
|
||||
description: ''
|
||||
required: true
|
||||
files:
|
||||
description: ''
|
||||
required: true
|
||||
runs:
|
||||
using: 'node16'
|
||||
main: 'main.js'
|
@ -1,162 +0,0 @@
|
||||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
||||
|
||||
const core = require('@actions/core');
|
||||
const path = require("path");
|
||||
const fs = require("fs");
|
||||
const github = require('@actions/github');
|
||||
const glob = require('glob');
|
||||
|
||||
function sleep(milliseconds) {
|
||||
return new Promise(resolve => setTimeout(resolve, milliseconds))
|
||||
}
|
||||
|
||||
async function runOnce() {
|
||||
// Load all our inputs and env vars. Note that `getInput` reads from `INPUT_*`
|
||||
const files = core.getInput('files');
|
||||
const token = core.getInput('token');
|
||||
const slug = process.env.GITHUB_REPOSITORY;
|
||||
const owner = slug.split('/')[0];
|
||||
const repo = slug.split('/')[1];
|
||||
const sha = process.env.GITHUB_SHA;
|
||||
let name = 'dev';
|
||||
if (process.env.GITHUB_REF.startsWith('refs/tags/v')) {
|
||||
name = process.env.GITHUB_REF.substring(10);
|
||||
}
|
||||
|
||||
core.info(`files: ${files}`);
|
||||
core.info(`name: ${name}`);
|
||||
core.info(`token: ${token}`);
|
||||
|
||||
const octokit = github.getOctokit(token);
|
||||
|
||||
// For the `dev` release we may need to update the tag to point to the new
|
||||
// commit on this branch. All other names should already have tags associated
|
||||
// with them.
|
||||
if (name == 'dev') {
|
||||
let tag = null;
|
||||
try {
|
||||
tag = await octokit.request("GET /repos/:owner/:repo/git/refs/tags/:name", { owner, repo, name });
|
||||
core.info(`found existing tag`);
|
||||
console.log("tag: ", JSON.stringify(tag.data, null, 2));
|
||||
} catch (e) {
|
||||
// ignore if this tag doesn't exist
|
||||
core.info(`no existing tag found`);
|
||||
}
|
||||
|
||||
if (tag === null || tag.data.object.sha !== sha) {
|
||||
core.info(`updating existing tag or creating new one`);
|
||||
|
||||
try {
|
||||
core.info(`updating dev tag`);
|
||||
await octokit.rest.git.updateRef({
|
||||
owner,
|
||||
repo,
|
||||
ref: 'tags/dev',
|
||||
sha,
|
||||
force: true,
|
||||
});
|
||||
} catch (e) {
|
||||
console.log("ERROR: ", JSON.stringify(e.response, null, 2));
|
||||
core.info(`creating dev tag`);
|
||||
try {
|
||||
await octokit.rest.git.createRef({
|
||||
owner,
|
||||
repo,
|
||||
ref: 'refs/tags/dev',
|
||||
sha,
|
||||
});
|
||||
} catch (e) {
|
||||
// we might race with others, so assume someone else has created the
|
||||
// tag by this point.
|
||||
console.log("failed to create tag: ", JSON.stringify(e.response, null, 2));
|
||||
}
|
||||
}
|
||||
|
||||
console.log("double-checking tag is correct");
|
||||
tag = await octokit.request("GET /repos/:owner/:repo/git/refs/tags/:name", { owner, repo, name });
|
||||
if (tag.data.object.sha !== sha) {
|
||||
console.log("tag: ", JSON.stringify(tag.data, null, 2));
|
||||
throw new Error("tag didn't work");
|
||||
}
|
||||
} else {
|
||||
core.info(`existing tag works`);
|
||||
}
|
||||
}
|
||||
|
||||
// Delete a previous release
|
||||
try {
|
||||
core.info(`fetching release`);
|
||||
let release = await octokit.rest.repos.getReleaseByTag({ owner, repo, tag: name });
|
||||
console.log("found release: ", JSON.stringify(release.data, null, 2));
|
||||
await octokit.rest.repos.deleteRelease({
|
||||
owner,
|
||||
repo,
|
||||
release_id: release.data.id,
|
||||
});
|
||||
console.log("deleted release");
|
||||
} catch (e) {
|
||||
console.log("ERROR: ", JSON.stringify(e, null, 2));
|
||||
}
|
||||
|
||||
console.log("creating a release");
|
||||
let release = await octokit.rest.repos.createRelease({
|
||||
owner,
|
||||
repo,
|
||||
tag_name: name,
|
||||
prerelease: name === 'dev',
|
||||
});
|
||||
|
||||
// Delete all assets from a previous run
|
||||
for (const asset of release.data.assets) {
|
||||
console.log(`deleting prior asset ${asset.id}`);
|
||||
await octokit.rest.repos.deleteReleaseAsset({
|
||||
owner,
|
||||
repo,
|
||||
asset_id: asset.id,
|
||||
});
|
||||
}
|
||||
|
||||
// Upload all the relevant assets for this release as just general blobs.
|
||||
for (const file of glob.sync(files)) {
|
||||
const size = fs.statSync(file).size;
|
||||
const name = path.basename(file);
|
||||
core.info(`upload ${file}`);
|
||||
await octokit.rest.repos.uploadReleaseAsset({
|
||||
data: fs.createReadStream(file),
|
||||
headers: { 'content-length': size, 'content-type': 'application/octet-stream' },
|
||||
name,
|
||||
url: release.data.upload_url,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
async function run() {
|
||||
const retries = 10;
|
||||
for (let i = 0; i < retries; i++) {
|
||||
try {
|
||||
await runOnce();
|
||||
break;
|
||||
} catch (e) {
|
||||
if (i === retries - 1)
|
||||
throw e;
|
||||
logError(e);
|
||||
console.log("RETRYING after 10s");
|
||||
await sleep(10000)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function logError(e) {
|
||||
console.log("ERROR: ", e.message);
|
||||
try {
|
||||
console.log(JSON.stringify(e, null, 2));
|
||||
} catch (e) {
|
||||
// ignore json errors for now
|
||||
}
|
||||
console.log(e.stack);
|
||||
}
|
||||
|
||||
run().catch(err => {
|
||||
logError(err);
|
||||
core.setFailed(err.message);
|
||||
});
|
571
compiler/rustc_codegen_cranelift/.github/actions/github-release/package-lock.json
generated
vendored
571
compiler/rustc_codegen_cranelift/.github/actions/github-release/package-lock.json
generated
vendored
@ -1,571 +0,0 @@
|
||||
{
|
||||
"name": "rustc_codegen_cranelift-github-release",
|
||||
"version": "0.0.0",
|
||||
"lockfileVersion": 2,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"name": "rustc_codegen_cranelift-github-release",
|
||||
"version": "0.0.0",
|
||||
"dependencies": {
|
||||
"@actions/core": "^1.9.1",
|
||||
"@actions/github": "^5.1.0",
|
||||
"glob": "^7.1.5"
|
||||
}
|
||||
},
|
||||
"node_modules/@actions/core": {
|
||||
"version": "1.9.1",
|
||||
"resolved": "https://registry.npmjs.org/@actions/core/-/core-1.9.1.tgz",
|
||||
"integrity": "sha512-5ad+U2YGrmmiw6du20AQW5XuWo7UKN2052FjSV7MX+Wfjf8sCqcsZe62NfgHys4QI4/Y+vQvLKYL8jWtA1ZBTA==",
|
||||
"dependencies": {
|
||||
"@actions/http-client": "^2.0.1",
|
||||
"uuid": "^8.3.2"
|
||||
}
|
||||
},
|
||||
"node_modules/@actions/github": {
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@actions/github/-/github-5.1.0.tgz",
|
||||
"integrity": "sha512-tuI80F7JQIhg77ZTTgUAPpVD7ZnP9oHSPN8xw7LOwtA4vEMbAjWJNbmLBfV7xua7r016GyjzWLuec5cs8f/a8A==",
|
||||
"dependencies": {
|
||||
"@actions/http-client": "^2.0.1",
|
||||
"@octokit/core": "^3.6.0",
|
||||
"@octokit/plugin-paginate-rest": "^2.17.0",
|
||||
"@octokit/plugin-rest-endpoint-methods": "^5.13.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@actions/http-client": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/@actions/http-client/-/http-client-2.0.1.tgz",
|
||||
"integrity": "sha512-PIXiMVtz6VvyaRsGY268qvj57hXQEpsYogYOu2nrQhlf+XCGmZstmuZBbAybUl1nQGnvS1k1eEsQ69ZoD7xlSw==",
|
||||
"dependencies": {
|
||||
"tunnel": "^0.0.6"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/auth-token": {
|
||||
"version": "2.5.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-2.5.0.tgz",
|
||||
"integrity": "sha512-r5FVUJCOLl19AxiuZD2VRZ/ORjp/4IN98Of6YJoJOkY75CIBuYfmiNHGrDwXr+aLGG55igl9QrxX3hbiXlLb+g==",
|
||||
"dependencies": {
|
||||
"@octokit/types": "^6.0.3"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/core": {
|
||||
"version": "3.6.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/core/-/core-3.6.0.tgz",
|
||||
"integrity": "sha512-7RKRKuA4xTjMhY+eG3jthb3hlZCsOwg3rztWh75Xc+ShDWOfDDATWbeZpAHBNRpm4Tv9WgBMOy1zEJYXG6NJ7Q==",
|
||||
"dependencies": {
|
||||
"@octokit/auth-token": "^2.4.4",
|
||||
"@octokit/graphql": "^4.5.8",
|
||||
"@octokit/request": "^5.6.3",
|
||||
"@octokit/request-error": "^2.0.5",
|
||||
"@octokit/types": "^6.0.3",
|
||||
"before-after-hook": "^2.2.0",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/endpoint": {
|
||||
"version": "6.0.12",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-6.0.12.tgz",
|
||||
"integrity": "sha512-lF3puPwkQWGfkMClXb4k/eUT/nZKQfxinRWJrdZaJO85Dqwo/G0yOC434Jr2ojwafWJMYqFGFa5ms4jJUgujdA==",
|
||||
"dependencies": {
|
||||
"@octokit/types": "^6.0.3",
|
||||
"is-plain-object": "^5.0.0",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/graphql": {
|
||||
"version": "4.8.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-4.8.0.tgz",
|
||||
"integrity": "sha512-0gv+qLSBLKF0z8TKaSKTsS39scVKF9dbMxJpj3U0vC7wjNWFuIpL/z76Qe2fiuCbDRcJSavkXsVtMS6/dtQQsg==",
|
||||
"dependencies": {
|
||||
"@octokit/request": "^5.6.0",
|
||||
"@octokit/types": "^6.0.3",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/openapi-types": {
|
||||
"version": "12.11.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-12.11.0.tgz",
|
||||
"integrity": "sha512-VsXyi8peyRq9PqIz/tpqiL2w3w80OgVMwBHltTml3LmVvXiphgeqmY9mvBw9Wu7e0QWk/fqD37ux8yP5uVekyQ=="
|
||||
},
|
||||
"node_modules/@octokit/plugin-paginate-rest": {
|
||||
"version": "2.21.3",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-2.21.3.tgz",
|
||||
"integrity": "sha512-aCZTEf0y2h3OLbrgKkrfFdjRL6eSOo8komneVQJnYecAxIej7Bafor2xhuDJOIFau4pk0i/P28/XgtbyPF0ZHw==",
|
||||
"dependencies": {
|
||||
"@octokit/types": "^6.40.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@octokit/core": ">=2"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/plugin-rest-endpoint-methods": {
|
||||
"version": "5.16.2",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-5.16.2.tgz",
|
||||
"integrity": "sha512-8QFz29Fg5jDuTPXVtey05BLm7OB+M8fnvE64RNegzX7U+5NUXcOcnpTIK0YfSHBg8gYd0oxIq3IZTe9SfPZiRw==",
|
||||
"dependencies": {
|
||||
"@octokit/types": "^6.39.0",
|
||||
"deprecation": "^2.3.1"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@octokit/core": ">=3"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/request": {
|
||||
"version": "5.6.3",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.6.3.tgz",
|
||||
"integrity": "sha512-bFJl0I1KVc9jYTe9tdGGpAMPy32dLBXXo1dS/YwSCTL/2nd9XeHsY616RE3HPXDVk+a+dBuzyz5YdlXwcDTr2A==",
|
||||
"dependencies": {
|
||||
"@octokit/endpoint": "^6.0.1",
|
||||
"@octokit/request-error": "^2.1.0",
|
||||
"@octokit/types": "^6.16.1",
|
||||
"is-plain-object": "^5.0.0",
|
||||
"node-fetch": "^2.6.7",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/request-error": {
|
||||
"version": "2.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz",
|
||||
"integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==",
|
||||
"dependencies": {
|
||||
"@octokit/types": "^6.0.3",
|
||||
"deprecation": "^2.0.0",
|
||||
"once": "^1.4.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@octokit/types": {
|
||||
"version": "6.41.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/types/-/types-6.41.0.tgz",
|
||||
"integrity": "sha512-eJ2jbzjdijiL3B4PrSQaSjuF2sPEQPVCPzBvTHJD9Nz+9dw2SGH4K4xeQJ77YfTq5bRQ+bD8wT11JbeDPmxmGg==",
|
||||
"dependencies": {
|
||||
"@octokit/openapi-types": "^12.11.0"
|
||||
}
|
||||
},
|
||||
"node_modules/balanced-match": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz",
|
||||
"integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="
|
||||
},
|
||||
"node_modules/before-after-hook": {
|
||||
"version": "2.2.3",
|
||||
"resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.3.tgz",
|
||||
"integrity": "sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ=="
|
||||
},
|
||||
"node_modules/brace-expansion": {
|
||||
"version": "1.1.11",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
|
||||
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
|
||||
"dependencies": {
|
||||
"balanced-match": "^1.0.0",
|
||||
"concat-map": "0.0.1"
|
||||
}
|
||||
},
|
||||
"node_modules/concat-map": {
|
||||
"version": "0.0.1",
|
||||
"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
|
||||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg=="
|
||||
},
|
||||
"node_modules/deprecation": {
|
||||
"version": "2.3.1",
|
||||
"resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz",
|
||||
"integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ=="
|
||||
},
|
||||
"node_modules/fs.realpath": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
|
||||
"integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw=="
|
||||
},
|
||||
"node_modules/glob": {
|
||||
"version": "7.2.3",
|
||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz",
|
||||
"integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==",
|
||||
"dependencies": {
|
||||
"fs.realpath": "^1.0.0",
|
||||
"inflight": "^1.0.4",
|
||||
"inherits": "2",
|
||||
"minimatch": "^3.1.1",
|
||||
"once": "^1.3.0",
|
||||
"path-is-absolute": "^1.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": "*"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/isaacs"
|
||||
}
|
||||
},
|
||||
"node_modules/inflight": {
|
||||
"version": "1.0.6",
|
||||
"resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
|
||||
"integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==",
|
||||
"dependencies": {
|
||||
"once": "^1.3.0",
|
||||
"wrappy": "1"
|
||||
}
|
||||
},
|
||||
"node_modules/inherits": {
|
||||
"version": "2.0.4",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
|
||||
"integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="
|
||||
},
|
||||
"node_modules/is-plain-object": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-5.0.0.tgz",
|
||||
"integrity": "sha512-VRSzKkbMm5jMDoKLbltAkFQ5Qr7VDiTFGXxYFXXowVj387GeGNOCsOH6Msy00SGZ3Fp84b1Naa1psqgcCIEP5Q==",
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/minimatch": {
|
||||
"version": "3.1.2",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz",
|
||||
"integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==",
|
||||
"dependencies": {
|
||||
"brace-expansion": "^1.1.7"
|
||||
},
|
||||
"engines": {
|
||||
"node": "*"
|
||||
}
|
||||
},
|
||||
"node_modules/node-fetch": {
|
||||
"version": "2.6.7",
|
||||
"resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz",
|
||||
"integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==",
|
||||
"dependencies": {
|
||||
"whatwg-url": "^5.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": "4.x || >=6.0.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"encoding": "^0.1.0"
|
||||
},
|
||||
"peerDependenciesMeta": {
|
||||
"encoding": {
|
||||
"optional": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/once": {
|
||||
"version": "1.4.0",
|
||||
"resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
|
||||
"integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==",
|
||||
"dependencies": {
|
||||
"wrappy": "1"
|
||||
}
|
||||
},
|
||||
"node_modules/path-is-absolute": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
|
||||
"integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==",
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/tr46": {
|
||||
"version": "0.0.3",
|
||||
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
||||
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw=="
|
||||
},
|
||||
"node_modules/tunnel": {
|
||||
"version": "0.0.6",
|
||||
"resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz",
|
||||
"integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==",
|
||||
"engines": {
|
||||
"node": ">=0.6.11 <=0.7.0 || >=0.7.3"
|
||||
}
|
||||
},
|
||||
"node_modules/universal-user-agent": {
|
||||
"version": "6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz",
|
||||
"integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w=="
|
||||
},
|
||||
"node_modules/uuid": {
|
||||
"version": "8.3.2",
|
||||
"resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz",
|
||||
"integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==",
|
||||
"bin": {
|
||||
"uuid": "dist/bin/uuid"
|
||||
}
|
||||
},
|
||||
"node_modules/webidl-conversions": {
|
||||
"version": "3.0.1",
|
||||
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz",
|
||||
"integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ=="
|
||||
},
|
||||
"node_modules/whatwg-url": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz",
|
||||
"integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==",
|
||||
"dependencies": {
|
||||
"tr46": "~0.0.3",
|
||||
"webidl-conversions": "^3.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/wrappy": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
|
||||
"integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@actions/core": {
|
||||
"version": "1.9.1",
|
||||
"resolved": "https://registry.npmjs.org/@actions/core/-/core-1.9.1.tgz",
|
||||
"integrity": "sha512-5ad+U2YGrmmiw6du20AQW5XuWo7UKN2052FjSV7MX+Wfjf8sCqcsZe62NfgHys4QI4/Y+vQvLKYL8jWtA1ZBTA==",
|
||||
"requires": {
|
||||
"@actions/http-client": "^2.0.1",
|
||||
"uuid": "^8.3.2"
|
||||
}
|
||||
},
|
||||
"@actions/github": {
|
||||
"version": "5.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@actions/github/-/github-5.1.0.tgz",
|
||||
"integrity": "sha512-tuI80F7JQIhg77ZTTgUAPpVD7ZnP9oHSPN8xw7LOwtA4vEMbAjWJNbmLBfV7xua7r016GyjzWLuec5cs8f/a8A==",
|
||||
"requires": {
|
||||
"@actions/http-client": "^2.0.1",
|
||||
"@octokit/core": "^3.6.0",
|
||||
"@octokit/plugin-paginate-rest": "^2.17.0",
|
||||
"@octokit/plugin-rest-endpoint-methods": "^5.13.0"
|
||||
}
|
||||
},
|
||||
"@actions/http-client": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/@actions/http-client/-/http-client-2.0.1.tgz",
|
||||
"integrity": "sha512-PIXiMVtz6VvyaRsGY268qvj57hXQEpsYogYOu2nrQhlf+XCGmZstmuZBbAybUl1nQGnvS1k1eEsQ69ZoD7xlSw==",
|
||||
"requires": {
|
||||
"tunnel": "^0.0.6"
|
||||
}
|
||||
},
|
||||
"@octokit/auth-token": {
|
||||
"version": "2.5.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/auth-token/-/auth-token-2.5.0.tgz",
|
||||
"integrity": "sha512-r5FVUJCOLl19AxiuZD2VRZ/ORjp/4IN98Of6YJoJOkY75CIBuYfmiNHGrDwXr+aLGG55igl9QrxX3hbiXlLb+g==",
|
||||
"requires": {
|
||||
"@octokit/types": "^6.0.3"
|
||||
}
|
||||
},
|
||||
"@octokit/core": {
|
||||
"version": "3.6.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/core/-/core-3.6.0.tgz",
|
||||
"integrity": "sha512-7RKRKuA4xTjMhY+eG3jthb3hlZCsOwg3rztWh75Xc+ShDWOfDDATWbeZpAHBNRpm4Tv9WgBMOy1zEJYXG6NJ7Q==",
|
||||
"requires": {
|
||||
"@octokit/auth-token": "^2.4.4",
|
||||
"@octokit/graphql": "^4.5.8",
|
||||
"@octokit/request": "^5.6.3",
|
||||
"@octokit/request-error": "^2.0.5",
|
||||
"@octokit/types": "^6.0.3",
|
||||
"before-after-hook": "^2.2.0",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"@octokit/endpoint": {
|
||||
"version": "6.0.12",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-6.0.12.tgz",
|
||||
"integrity": "sha512-lF3puPwkQWGfkMClXb4k/eUT/nZKQfxinRWJrdZaJO85Dqwo/G0yOC434Jr2ojwafWJMYqFGFa5ms4jJUgujdA==",
|
||||
"requires": {
|
||||
"@octokit/types": "^6.0.3",
|
||||
"is-plain-object": "^5.0.0",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"@octokit/graphql": {
|
||||
"version": "4.8.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/graphql/-/graphql-4.8.0.tgz",
|
||||
"integrity": "sha512-0gv+qLSBLKF0z8TKaSKTsS39scVKF9dbMxJpj3U0vC7wjNWFuIpL/z76Qe2fiuCbDRcJSavkXsVtMS6/dtQQsg==",
|
||||
"requires": {
|
||||
"@octokit/request": "^5.6.0",
|
||||
"@octokit/types": "^6.0.3",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"@octokit/openapi-types": {
|
||||
"version": "12.11.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-12.11.0.tgz",
|
||||
"integrity": "sha512-VsXyi8peyRq9PqIz/tpqiL2w3w80OgVMwBHltTml3LmVvXiphgeqmY9mvBw9Wu7e0QWk/fqD37ux8yP5uVekyQ=="
|
||||
},
|
||||
"@octokit/plugin-paginate-rest": {
|
||||
"version": "2.21.3",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-2.21.3.tgz",
|
||||
"integrity": "sha512-aCZTEf0y2h3OLbrgKkrfFdjRL6eSOo8komneVQJnYecAxIej7Bafor2xhuDJOIFau4pk0i/P28/XgtbyPF0ZHw==",
|
||||
"requires": {
|
||||
"@octokit/types": "^6.40.0"
|
||||
}
|
||||
},
|
||||
"@octokit/plugin-rest-endpoint-methods": {
|
||||
"version": "5.16.2",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-5.16.2.tgz",
|
||||
"integrity": "sha512-8QFz29Fg5jDuTPXVtey05BLm7OB+M8fnvE64RNegzX7U+5NUXcOcnpTIK0YfSHBg8gYd0oxIq3IZTe9SfPZiRw==",
|
||||
"requires": {
|
||||
"@octokit/types": "^6.39.0",
|
||||
"deprecation": "^2.3.1"
|
||||
}
|
||||
},
|
||||
"@octokit/request": {
|
||||
"version": "5.6.3",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.6.3.tgz",
|
||||
"integrity": "sha512-bFJl0I1KVc9jYTe9tdGGpAMPy32dLBXXo1dS/YwSCTL/2nd9XeHsY616RE3HPXDVk+a+dBuzyz5YdlXwcDTr2A==",
|
||||
"requires": {
|
||||
"@octokit/endpoint": "^6.0.1",
|
||||
"@octokit/request-error": "^2.1.0",
|
||||
"@octokit/types": "^6.16.1",
|
||||
"is-plain-object": "^5.0.0",
|
||||
"node-fetch": "^2.6.7",
|
||||
"universal-user-agent": "^6.0.0"
|
||||
}
|
||||
},
|
||||
"@octokit/request-error": {
|
||||
"version": "2.1.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz",
|
||||
"integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==",
|
||||
"requires": {
|
||||
"@octokit/types": "^6.0.3",
|
||||
"deprecation": "^2.0.0",
|
||||
"once": "^1.4.0"
|
||||
}
|
||||
},
|
||||
"@octokit/types": {
|
||||
"version": "6.41.0",
|
||||
"resolved": "https://registry.npmjs.org/@octokit/types/-/types-6.41.0.tgz",
|
||||
"integrity": "sha512-eJ2jbzjdijiL3B4PrSQaSjuF2sPEQPVCPzBvTHJD9Nz+9dw2SGH4K4xeQJ77YfTq5bRQ+bD8wT11JbeDPmxmGg==",
|
||||
"requires": {
|
||||
"@octokit/openapi-types": "^12.11.0"
|
||||
}
|
||||
},
|
||||
"balanced-match": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz",
|
||||
"integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw=="
|
||||
},
|
||||
"before-after-hook": {
|
||||
"version": "2.2.3",
|
||||
"resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.2.3.tgz",
|
||||
"integrity": "sha512-NzUnlZexiaH/46WDhANlyR2bXRopNg4F/zuSA3OpZnllCUgRaOF2znDioDWrmbNVsuZk6l9pMquQB38cfBZwkQ=="
|
||||
},
|
||||
"brace-expansion": {
|
||||
"version": "1.1.11",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
|
||||
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
|
||||
"requires": {
|
||||
"balanced-match": "^1.0.0",
|
||||
"concat-map": "0.0.1"
|
||||
}
|
||||
},
|
||||
"concat-map": {
|
||||
"version": "0.0.1",
|
||||
"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
|
||||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg=="
|
||||
},
|
||||
"deprecation": {
|
||||
"version": "2.3.1",
|
||||
"resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz",
|
||||
"integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ=="
|
||||
},
|
||||
"fs.realpath": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
|
||||
"integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw=="
|
||||
},
|
||||
"glob": {
|
||||
"version": "7.2.3",
|
||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz",
|
||||
"integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==",
|
||||
"requires": {
|
||||
"fs.realpath": "^1.0.0",
|
||||
"inflight": "^1.0.4",
|
||||
"inherits": "2",
|
||||
"minimatch": "^3.1.1",
|
||||
"once": "^1.3.0",
|
||||
"path-is-absolute": "^1.0.0"
|
||||
}
|
||||
},
|
||||
"inflight": {
|
||||
"version": "1.0.6",
|
||||
"resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
|
||||
"integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==",
|
||||
"requires": {
|
||||
"once": "^1.3.0",
|
||||
"wrappy": "1"
|
||||
}
|
||||
},
|
||||
"inherits": {
|
||||
"version": "2.0.4",
|
||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
|
||||
"integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ=="
|
||||
},
|
||||
"is-plain-object": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-5.0.0.tgz",
|
||||
"integrity": "sha512-VRSzKkbMm5jMDoKLbltAkFQ5Qr7VDiTFGXxYFXXowVj387GeGNOCsOH6Msy00SGZ3Fp84b1Naa1psqgcCIEP5Q=="
|
||||
},
|
||||
"minimatch": {
|
||||
"version": "3.1.2",
|
||||
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz",
|
||||
"integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==",
|
||||
"requires": {
|
||||
"brace-expansion": "^1.1.7"
|
||||
}
|
||||
},
|
||||
"node-fetch": {
|
||||
"version": "2.6.7",
|
||||
"resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz",
|
||||
"integrity": "sha512-ZjMPFEfVx5j+y2yF35Kzx5sF7kDzxuDj6ziH4FFbOp87zKDZNx8yExJIb05OGF4Nlt9IHFIMBkRl41VdvcNdbQ==",
|
||||
"requires": {
|
||||
"whatwg-url": "^5.0.0"
|
||||
}
|
||||
},
|
||||
"once": {
|
||||
"version": "1.4.0",
|
||||
"resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
|
||||
"integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==",
|
||||
"requires": {
|
||||
"wrappy": "1"
|
||||
}
|
||||
},
|
||||
"path-is-absolute": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
|
||||
"integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg=="
|
||||
},
|
||||
"tr46": {
|
||||
"version": "0.0.3",
|
||||
"resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
|
||||
"integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw=="
|
||||
},
|
||||
"tunnel": {
|
||||
"version": "0.0.6",
|
||||
"resolved": "https://registry.npmjs.org/tunnel/-/tunnel-0.0.6.tgz",
|
||||
"integrity": "sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg=="
|
||||
},
|
||||
"universal-user-agent": {
|
||||
"version": "6.0.0",
|
||||
"resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-6.0.0.tgz",
|
||||
"integrity": "sha512-isyNax3wXoKaulPDZWHQqbmIx1k2tb9fb3GGDBRxCscfYV2Ch7WxPArBsFEG8s/safwXTT7H4QGhaIkTp9447w=="
|
||||
},
|
||||
"uuid": {
|
||||
"version": "8.3.2",
|
||||
"resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz",
|
||||
"integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg=="
|
||||
},
|
||||
"webidl-conversions": {
|
||||
"version": "3.0.1",
|
||||
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz",
|
||||
"integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ=="
|
||||
},
|
||||
"whatwg-url": {
|
||||
"version": "5.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz",
|
||||
"integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==",
|
||||
"requires": {
|
||||
"tr46": "~0.0.3",
|
||||
"webidl-conversions": "^3.0.0"
|
||||
}
|
||||
},
|
||||
"wrappy": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
|
||||
"integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="
|
||||
}
|
||||
}
|
||||
}
|
@ -1,11 +0,0 @@
|
||||
{
|
||||
"name": "rustc_codegen_cranelift-github-release",
|
||||
"version": "0.0.0",
|
||||
"license": "Apache-2.0 WITH LLVM-exception",
|
||||
"main": "main.js",
|
||||
"dependencies": {
|
||||
"@actions/core": "^1.9.1",
|
||||
"@actions/github": "^5.1.0",
|
||||
"glob": "^7.1.5"
|
||||
}
|
||||
}
|
@ -25,7 +25,10 @@ jobs:
|
||||
- os: ubuntu-latest
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-unknown-linux-gnu
|
||||
- os: macos-latest
|
||||
- os: ubuntu-24.04-arm
|
||||
env:
|
||||
TARGET_TRIPLE: aarch64-unknown-linux-gnu
|
||||
- os: macos-13
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-apple-darwin
|
||||
- os: macos-latest
|
||||
@ -56,13 +59,6 @@ jobs:
|
||||
if: matrix.env.TARGET_TRIPLE == 'x86_64-pc-windows-gnu'
|
||||
run: rustup set default-host x86_64-pc-windows-gnu
|
||||
|
||||
- name: Use x86_64 compiler on macOS
|
||||
if: matrix.os == 'macos-latest' && matrix.env.TARGET_TRIPLE == 'x86_64-apple-darwin'
|
||||
run: rustup set default-host x86_64-apple-darwin
|
||||
|
||||
- name: Prepare dependencies
|
||||
run: ./y.sh prepare
|
||||
|
||||
- name: Build
|
||||
run: ./y.sh build --sysroot none
|
||||
|
||||
|
@ -53,13 +53,12 @@ jobs:
|
||||
- os: ubuntu-latest
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-unknown-linux-gnu
|
||||
- os: macos-latest
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-apple-darwin
|
||||
- os: ubuntu-latest
|
||||
- os: ubuntu-24.04-arm
|
||||
env:
|
||||
TARGET_TRIPLE: aarch64-unknown-linux-gnu
|
||||
apt_deps: gcc-aarch64-linux-gnu qemu-user
|
||||
- os: macos-13
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-apple-darwin
|
||||
- os: macos-latest
|
||||
env:
|
||||
TARGET_TRIPLE: aarch64-apple-darwin
|
||||
@ -95,10 +94,6 @@ jobs:
|
||||
if: matrix.os == 'windows-latest' && matrix.env.TARGET_TRIPLE == 'x86_64-pc-windows-gnu'
|
||||
run: rustup set default-host x86_64-pc-windows-gnu
|
||||
|
||||
- name: Use x86_64 compiler on macOS
|
||||
if: matrix.os == 'macos-latest' && matrix.env.TARGET_TRIPLE == 'x86_64-apple-darwin'
|
||||
run: rustup set default-host x86_64-apple-darwin
|
||||
|
||||
- name: Install toolchain and emulator
|
||||
if: matrix.apt_deps != null
|
||||
run: |
|
||||
@ -170,9 +165,6 @@ jobs:
|
||||
sudo apt update
|
||||
sudo apt install -y hyperfine
|
||||
|
||||
- name: Prepare dependencies
|
||||
run: ./y.sh prepare
|
||||
|
||||
- name: Build
|
||||
run: ./y.sh build --sysroot none
|
||||
|
||||
@ -192,7 +184,10 @@ jobs:
|
||||
- os: ubuntu-22.04
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-unknown-linux-gnu
|
||||
- os: macos-latest
|
||||
- os: ubuntu-24.04-arm
|
||||
env:
|
||||
TARGET_TRIPLE: aarch64-unknown-linux-gnu
|
||||
- os: macos-13
|
||||
env:
|
||||
TARGET_TRIPLE: x86_64-apple-darwin
|
||||
- os: macos-latest
|
||||
@ -218,13 +213,6 @@ jobs:
|
||||
if: matrix.os == 'windows-latest' && matrix.env.TARGET_TRIPLE == 'x86_64-pc-windows-gnu'
|
||||
run: rustup set default-host x86_64-pc-windows-gnu
|
||||
|
||||
- name: Use x86_64 compiler on macOS
|
||||
if: matrix.os == 'macos-latest' && matrix.env.TARGET_TRIPLE == 'x86_64-apple-darwin'
|
||||
run: rustup set default-host x86_64-apple-darwin
|
||||
|
||||
- name: Prepare dependencies
|
||||
run: ./y.sh prepare
|
||||
|
||||
- name: Build backend
|
||||
run: ./y.sh build --sysroot none
|
||||
|
||||
@ -273,12 +261,9 @@ jobs:
|
||||
rmdir artifacts/ # verify all artifacts are represented in release/
|
||||
ls -R release/
|
||||
|
||||
- run: npm install --production
|
||||
working-directory: .github/actions/github-release
|
||||
|
||||
- name: Publish Release
|
||||
uses: ./.github/actions/github-release
|
||||
with:
|
||||
files: "release/*"
|
||||
token: ${{ github.token }}
|
||||
continue-on-error: true
|
||||
- name: Publish release
|
||||
env:
|
||||
GH_TOKEN: ${{ github.token }}
|
||||
run: |
|
||||
gh release delete --cleanup-tag -y dev || true
|
||||
gh release create --target $GITHUB_SHA --prerelease dev release/*
|
||||
|
@ -22,9 +22,6 @@ jobs:
|
||||
path: build/cg_clif
|
||||
key: ${{ runner.os }}-rustc-test-cargo-build-target-${{ hashFiles('rust-toolchain', 'Cargo.lock') }}
|
||||
|
||||
- name: Prepare dependencies
|
||||
run: ./y.sh prepare
|
||||
|
||||
- name: Test
|
||||
run: ./scripts/test_bootstrap.sh
|
||||
|
||||
@ -50,8 +47,5 @@ jobs:
|
||||
sudo apt update
|
||||
sudo apt install -y ripgrep
|
||||
|
||||
- name: Prepare dependencies
|
||||
run: ./y.sh prepare
|
||||
|
||||
- name: Test
|
||||
run: ./scripts/test_rustc_tests.sh
|
||||
|
@ -1,41 +1,40 @@
|
||||
{
|
||||
"editor.formatOnSave": true,
|
||||
|
||||
// in case rustc.source is disabled for performance reasons; disable the errors about this
|
||||
"rust-analyzer.diagnostics.disabled": ["unresolved-extern-crate", "unresolved-macro-call"],
|
||||
"rust-analyzer.diagnostics.disabled": [
|
||||
"unresolved-extern-crate",
|
||||
"unresolved-macro-call"
|
||||
],
|
||||
"rust-analyzer.rustc.source": "discover",
|
||||
"rust-analyzer.imports.granularity.enforce": true,
|
||||
"rust-analyzer.imports.granularity.group": "module",
|
||||
"rust-analyzer.imports.prefix": "crate",
|
||||
"rust-analyzer.cargo.features": ["unstable-features"],
|
||||
"rust-analyzer.cargo.features": [
|
||||
"unstable-features"
|
||||
],
|
||||
"rust-analyzer.linkedProjects": [
|
||||
"./Cargo.toml",
|
||||
"./build_system/Cargo.toml",
|
||||
{
|
||||
"sysroot_src": "./build/stdlib/library",
|
||||
"crates": [
|
||||
{
|
||||
"root_module": "./example/mini_core.rs",
|
||||
"edition": "2018",
|
||||
"edition": "2015",
|
||||
"deps": [],
|
||||
"cfg": [],
|
||||
},
|
||||
{
|
||||
"root_module": "./example/mini_core_hello_world.rs",
|
||||
"edition": "2018",
|
||||
"deps": [{ "crate": 0, "name": "mini_core" }],
|
||||
"edition": "2015",
|
||||
"deps": [
|
||||
{
|
||||
"crate": 0,
|
||||
"name": "mini_core"
|
||||
}
|
||||
],
|
||||
"cfg": [],
|
||||
},
|
||||
{
|
||||
"root_module": "./example/mod_bench.rs",
|
||||
"edition": "2018",
|
||||
"deps": [],
|
||||
"cfg": [],
|
||||
},
|
||||
]
|
||||
},
|
||||
{
|
||||
"sysroot_src": "./build/stdlib/library",
|
||||
"crates": [
|
||||
{
|
||||
"root_module": "./example/std_example.rs",
|
||||
"edition": "2015",
|
||||
|
@ -5,7 +5,10 @@
|
||||
"initialization_options": {
|
||||
"diagnostics": {
|
||||
// in case rustc.source is disabled for performance reasons; disable the errors about this
|
||||
"disabled": ["unresolved-extern-crate", "unresolved-macro-call"]
|
||||
"disabled": [
|
||||
"unresolved-extern-crate",
|
||||
"unresolved-macro-call"
|
||||
]
|
||||
},
|
||||
"rustc": {
|
||||
"source": "discover"
|
||||
@ -18,22 +21,25 @@
|
||||
"prefix": "crate"
|
||||
},
|
||||
"cargo": {
|
||||
"features": ["unstable-features"]
|
||||
"features": [
|
||||
"unstable-features"
|
||||
]
|
||||
},
|
||||
"linkedProjects": [
|
||||
"./Cargo.toml",
|
||||
"./build_system/Cargo.toml",
|
||||
{
|
||||
"sysroot_src": "./build/stdlib/library",
|
||||
"crates": [
|
||||
{
|
||||
"root_module": "./example/mini_core.rs",
|
||||
"edition": "2018",
|
||||
"edition": "2015",
|
||||
"deps": [],
|
||||
"cfg": []
|
||||
},
|
||||
{
|
||||
"root_module": "./example/mini_core_hello_world.rs",
|
||||
"edition": "2018",
|
||||
"edition": "2015",
|
||||
"deps": [
|
||||
{
|
||||
"crate": 0,
|
||||
@ -42,17 +48,6 @@
|
||||
],
|
||||
"cfg": []
|
||||
},
|
||||
{
|
||||
"root_module": "./example/mod_bench.rs",
|
||||
"edition": "2018",
|
||||
"deps": [],
|
||||
"cfg": []
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"sysroot_src": "./build/stdlib/library",
|
||||
"crates": [
|
||||
{
|
||||
"root_module": "./example/std_example.rs",
|
||||
"edition": "2015",
|
||||
|
@ -42,27 +42,43 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-bforest"
|
||||
version = "0.116.1"
|
||||
name = "cranelift-assembler-x64"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e15d04a0ce86cb36ead88ad68cf693ffd6cda47052b9e0ac114bc47fd9cd23c4"
|
||||
checksum = "3e4b56ebe316895d3fa37775d0a87b0c889cc933f5c8b253dbcc7c7bcb7fe7e4"
|
||||
dependencies = [
|
||||
"cranelift-assembler-x64-meta",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-assembler-x64-meta"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "95cabbc01dfbd7dcd6c329ca44f0212910309c221797ac736a67a5bc8857fe1b"
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-bforest"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "76ffe46df300a45f1dc6f609dc808ce963f0e3a2e971682c479a2d13e3b9b8ef"
|
||||
dependencies = [
|
||||
"cranelift-entity",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-bitset"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7c6e3969a7ce267259ce244b7867c5d3bc9e65b0a87e81039588dfdeaede9f34"
|
||||
checksum = "b265bed7c51e1921fdae6419791d31af77d33662ee56d7b0fa0704dc8d231cab"
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-codegen"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2c22032c4cb42558371cf516bb47f26cdad1819d3475c133e93c49f50ebf304e"
|
||||
checksum = "e606230a7e3a6897d603761baee0d19f88d077f17b996bb5089488a29ae96e41"
|
||||
dependencies = [
|
||||
"bumpalo",
|
||||
"cranelift-assembler-x64",
|
||||
"cranelift-bforest",
|
||||
"cranelift-bitset",
|
||||
"cranelift-codegen-meta",
|
||||
@ -71,7 +87,7 @@ dependencies = [
|
||||
"cranelift-entity",
|
||||
"cranelift-isle",
|
||||
"gimli",
|
||||
"hashbrown 0.14.5",
|
||||
"hashbrown",
|
||||
"log",
|
||||
"regalloc2",
|
||||
"rustc-hash",
|
||||
@ -82,42 +98,43 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-codegen-meta"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c904bc71c61b27fc57827f4a1379f29de64fe95653b620a3db77d59655eee0b8"
|
||||
checksum = "8a63bffafc23bc60969ad528e138788495999d935f0adcfd6543cb151ca8637d"
|
||||
dependencies = [
|
||||
"cranelift-assembler-x64",
|
||||
"cranelift-codegen-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-codegen-shared"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "40180f5497572f644ce88c255480981ae2ec1d7bb4d8e0c0136a13b87a2f2ceb"
|
||||
checksum = "af50281b67324b58e843170a6a5943cf6d387c06f7eeacc9f5696e4ab7ae7d7e"
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-control"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26d132c6d0bd8a489563472afc171759da0707804a65ece7ceb15a8c6d7dd5ef"
|
||||
checksum = "8c20c1b38d1abfbcebb0032e497e71156c0e3b8dcb3f0a92b9863b7bcaec290c"
|
||||
dependencies = [
|
||||
"arbitrary",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-entity"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4b2d0d9618275474fbf679dd018ac6e009acbd6ae6850f6a67be33fb3b00b323"
|
||||
checksum = "0c2c67d95507c51b4a1ff3f3555fe4bfec36b9e13c1b684ccc602736f5d5f4a2"
|
||||
dependencies = [
|
||||
"cranelift-bitset",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-frontend"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4fac41e16729107393174b0c9e3730fb072866100e1e64e80a1a963b2e484d57"
|
||||
checksum = "4e002691cc69c38b54fc7ec93e5be5b744f627d027031d991cc845d1d512d0ce"
|
||||
dependencies = [
|
||||
"cranelift-codegen",
|
||||
"log",
|
||||
@ -127,15 +144,15 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-isle"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1ca20d576e5070044d0a72a9effc2deacf4d6aa650403189d8ea50126483944d"
|
||||
checksum = "e93588ed1796cbcb0e2ad160403509e2c5d330d80dd6e0014ac6774c7ebac496"
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-jit"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5e65c42755a719b09662b00c700daaf76cc35d5ace1f5c002ad404b591ff1978"
|
||||
checksum = "17f6682f0b193d6b7873cc8e7ed67e8776a8a26f50eeabf88534e9be618b9a03"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"cranelift-codegen",
|
||||
@ -153,9 +170,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-module"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4d55612bebcf16ff7306c8a6f5bdb6d45662b8aa1ee058ecce8807ad87db719b"
|
||||
checksum = "ff19784c6de05116e63e6a34791012bd927b2a4eac56233039c46f1b6a4edac8"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"cranelift-codegen",
|
||||
@ -164,9 +181,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-native"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b8dee82f3f1f2c4cba9177f1cc5e350fe98764379bcd29340caa7b01f85076c7"
|
||||
checksum = "e5b09bdd6407bf5d89661b80cf926ce731c9e8cc184bf49102267a2369a8358e"
|
||||
dependencies = [
|
||||
"cranelift-codegen",
|
||||
"libc",
|
||||
@ -175,9 +192,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "cranelift-object"
|
||||
version = "0.116.1"
|
||||
version = "0.118.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "aad5a6d3e379493c3f8b35dc61c93d0bf5f27003bbe20614e0200b0ec372ef52"
|
||||
checksum = "685e8661a30d1cb69509f589ac643adeee79c5f63c0da316431b9fad29e6d3b4"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"cranelift-codegen",
|
||||
@ -226,12 +243,6 @@ dependencies = [
|
||||
"stable_deref_trait",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.14.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1"
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.15.2"
|
||||
@ -248,7 +259,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "62f822373a4fe84d4bb149bf54e584a7f4abec90e072ed49cda0edea5b95471f"
|
||||
dependencies = [
|
||||
"equivalent",
|
||||
"hashbrown 0.15.2",
|
||||
"hashbrown",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -295,7 +306,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "62948e14d923ea95ea2c7c86c71013138b66525b86bdc08d2dcc262bdb497b87"
|
||||
dependencies = [
|
||||
"crc32fast",
|
||||
"hashbrown 0.15.2",
|
||||
"hashbrown",
|
||||
"indexmap",
|
||||
"memchr",
|
||||
]
|
||||
@ -326,7 +337,7 @@ checksum = "145c1c267e14f20fb0f88aa76a1c5ffec42d592c1d28b3cd9148ae35916158d3"
|
||||
dependencies = [
|
||||
"allocator-api2",
|
||||
"bumpalo",
|
||||
"hashbrown 0.15.2",
|
||||
"hashbrown",
|
||||
"log",
|
||||
"rustc-hash",
|
||||
"smallvec",
|
||||
@ -425,9 +436,9 @@ checksum = "adb9e6ca4f869e1180728b7950e35922a7fc6397f7b641499e8f3ef06e50dc83"
|
||||
|
||||
[[package]]
|
||||
name = "wasmtime-jit-icache-coherence"
|
||||
version = "29.0.1"
|
||||
version = "31.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ec5e8552e01692e6c2e5293171704fed8abdec79d1a6995a0870ab190e5747d1"
|
||||
checksum = "a54f6c6c7e9d7eeee32dfcc10db7f29d505ee7dd28d00593ea241d5f70698e64"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"cfg-if",
|
||||
|
@ -8,12 +8,12 @@ crate-type = ["dylib"]
|
||||
|
||||
[dependencies]
|
||||
# These have to be in sync with each other
|
||||
cranelift-codegen = { version = "0.116.0", default-features = false, features = ["std", "unwind", "all-native-arch"] }
|
||||
cranelift-frontend = { version = "0.116.0" }
|
||||
cranelift-module = { version = "0.116.0" }
|
||||
cranelift-native = { version = "0.116.0" }
|
||||
cranelift-jit = { version = "0.116.0", optional = true }
|
||||
cranelift-object = { version = "0.116.0" }
|
||||
cranelift-codegen = { version = "0.118.0", default-features = false, features = ["std", "timing", "unwind", "all-native-arch"] }
|
||||
cranelift-frontend = { version = "0.118.0" }
|
||||
cranelift-module = { version = "0.118.0" }
|
||||
cranelift-native = { version = "0.118.0" }
|
||||
cranelift-jit = { version = "0.118.0", optional = true }
|
||||
cranelift-object = { version = "0.118.0" }
|
||||
target-lexicon = "0.13"
|
||||
gimli = { version = "0.31", default-features = false, features = ["write"] }
|
||||
object = { version = "0.36", default-features = false, features = ["std", "read_core", "write", "archive", "coff", "elf", "macho", "pe"] }
|
||||
@ -24,12 +24,12 @@ smallvec = "1.8.1"
|
||||
|
||||
[patch.crates-io]
|
||||
# Uncomment to use an unreleased version of cranelift
|
||||
#cranelift-codegen = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-frontend = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-module = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-native = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-jit = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-object = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-29.0.0", version = "0.116.0" }
|
||||
#cranelift-codegen = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
#cranelift-frontend = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
#cranelift-module = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
#cranelift-native = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
#cranelift-jit = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
#cranelift-object = { git = "https://github.com/bytecodealliance/wasmtime.git", branch = "release-31.0.0", version = "0.118.0" }
|
||||
|
||||
# Uncomment to use local checkout of cranelift
|
||||
#cranelift-codegen = { path = "../wasmtime/cranelift/codegen" }
|
||||
|
@ -49,13 +49,13 @@ If you want to build the backend manually, you can download it from GitHub and b
|
||||
```bash
|
||||
$ git clone https://github.com/rust-lang/rustc_codegen_cranelift
|
||||
$ cd rustc_codegen_cranelift
|
||||
$ ./y.sh prepare
|
||||
$ ./y.sh build
|
||||
```
|
||||
|
||||
To run the test suite replace the last command with:
|
||||
|
||||
```bash
|
||||
$ ./y.sh prepare # only needs to be run the first time
|
||||
$ ./test.sh
|
||||
```
|
||||
|
||||
|
@ -91,6 +91,13 @@ impl GitRepo {
|
||||
|
||||
fn verify_checksum(&self, dirs: &Dirs) {
|
||||
let download_dir = self.download_dir(dirs);
|
||||
if !download_dir.exists() {
|
||||
eprintln!(
|
||||
"Missing directory {download_dir}: Please run ./y.sh prepare to download.",
|
||||
download_dir = download_dir.display(),
|
||||
);
|
||||
std::process::exit(1);
|
||||
}
|
||||
let actual_hash = format!("{:016x}", hash_dir(&download_dir));
|
||||
if actual_hash != self.content_hash {
|
||||
eprintln!(
|
||||
|
@ -1,5 +1,4 @@
|
||||
use std::ffi::OsStr;
|
||||
use std::fs;
|
||||
use std::path::PathBuf;
|
||||
use std::process::Command;
|
||||
|
||||
@ -126,9 +125,9 @@ static PORTABLE_SIMD_SRC: RelPath = RelPath::build("portable-simd");
|
||||
|
||||
static PORTABLE_SIMD: CargoProject = CargoProject::new(&PORTABLE_SIMD_SRC, "portable-simd_target");
|
||||
|
||||
static LIBCORE_TESTS_SRC: RelPath = RelPath::build("coretests");
|
||||
static SYSROOT_TESTS_SRC: RelPath = RelPath::build("sysroot_tests");
|
||||
|
||||
static LIBCORE_TESTS: CargoProject = CargoProject::new(&LIBCORE_TESTS_SRC, "coretests_target");
|
||||
static SYSROOT_TESTS: CargoProject = CargoProject::new(&SYSROOT_TESTS_SRC, "sysroot_tests_target");
|
||||
|
||||
const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[
|
||||
TestCase::custom("test.rust-random/rand", &|runner| {
|
||||
@ -147,28 +146,24 @@ const EXTENDED_SYSROOT_SUITE: &[TestCase] = &[
|
||||
spawn_and_wait(build_cmd);
|
||||
}
|
||||
}),
|
||||
TestCase::custom("test.libcore", &|runner| {
|
||||
TestCase::custom("test.sysroot", &|runner| {
|
||||
apply_patches(
|
||||
&runner.dirs,
|
||||
"coretests",
|
||||
&runner.stdlib_source.join("library/coretests"),
|
||||
&LIBCORE_TESTS_SRC.to_path(&runner.dirs),
|
||||
"sysroot_tests",
|
||||
&runner.stdlib_source.join("library"),
|
||||
&SYSROOT_TESTS_SRC.to_path(&runner.dirs),
|
||||
);
|
||||
|
||||
let source_lockfile = runner.dirs.source_dir.join("patches/coretests-lock.toml");
|
||||
let target_lockfile = LIBCORE_TESTS_SRC.to_path(&runner.dirs).join("Cargo.lock");
|
||||
fs::copy(source_lockfile, target_lockfile).unwrap();
|
||||
|
||||
LIBCORE_TESTS.clean(&runner.dirs);
|
||||
SYSROOT_TESTS.clean(&runner.dirs);
|
||||
|
||||
if runner.is_native {
|
||||
let mut test_cmd = LIBCORE_TESTS.test(&runner.target_compiler, &runner.dirs);
|
||||
test_cmd.arg("--").arg("-q");
|
||||
let mut test_cmd = SYSROOT_TESTS.test(&runner.target_compiler, &runner.dirs);
|
||||
test_cmd.args(["-p", "coretests", "-p", "alloctests", "--", "-q"]);
|
||||
spawn_and_wait(test_cmd);
|
||||
} else {
|
||||
eprintln!("Cross-Compiling: Not running tests");
|
||||
let mut build_cmd = LIBCORE_TESTS.build(&runner.target_compiler, &runner.dirs);
|
||||
build_cmd.arg("--tests");
|
||||
let mut build_cmd = SYSROOT_TESTS.build(&runner.target_compiler, &runner.dirs);
|
||||
build_cmd.args(["-p", "coretests", "-p", "alloctests", "--tests"]);
|
||||
spawn_and_wait(build_cmd);
|
||||
}
|
||||
}),
|
||||
@ -330,10 +325,8 @@ impl<'a> TestRunner<'a> {
|
||||
target_compiler.rustflags.extend(rustflags_from_env("RUSTFLAGS"));
|
||||
target_compiler.rustdocflags.extend(rustflags_from_env("RUSTDOCFLAGS"));
|
||||
|
||||
let jit_supported = use_unstable_features
|
||||
&& is_native
|
||||
&& target_compiler.triple.contains("x86_64")
|
||||
&& !target_compiler.triple.contains("windows");
|
||||
let jit_supported =
|
||||
use_unstable_features && is_native && !target_compiler.triple.contains("windows");
|
||||
|
||||
Self { is_native, jit_supported, skip_tests, dirs, target_compiler, stdlib_source }
|
||||
}
|
||||
@ -374,21 +367,7 @@ impl<'a> TestRunner<'a> {
|
||||
TestCaseCmd::JitBin { source, args } => {
|
||||
let mut jit_cmd = self.rustc_command([
|
||||
"-Zunstable-options",
|
||||
"-Cllvm-args=mode=jit",
|
||||
"-Cprefer-dynamic",
|
||||
source,
|
||||
"--cfg",
|
||||
"jit",
|
||||
]);
|
||||
if !args.is_empty() {
|
||||
jit_cmd.env("CG_CLIF_JIT_ARGS", args);
|
||||
}
|
||||
spawn_and_wait(jit_cmd);
|
||||
|
||||
eprintln!("[JIT-lazy] {testname}");
|
||||
let mut jit_cmd = self.rustc_command([
|
||||
"-Zunstable-options",
|
||||
"-Cllvm-args=mode=jit-lazy",
|
||||
"-Cllvm-args=jit-mode",
|
||||
"-Cprefer-dynamic",
|
||||
source,
|
||||
"--cfg",
|
||||
|
@ -35,6 +35,6 @@ aot.raw-dylib
|
||||
|
||||
testsuite.extended_sysroot
|
||||
test.rust-random/rand
|
||||
test.libcore
|
||||
test.sysroot
|
||||
test.regex
|
||||
test.portable-simd
|
||||
|
@ -38,14 +38,7 @@ $ $cg_clif_dir/dist/cargo-clif jit
|
||||
or
|
||||
|
||||
```bash
|
||||
$ $cg_clif_dir/dist/rustc-clif -Zunstable-features -Cllvm-args=mode=jit -Cprefer-dynamic my_crate.rs
|
||||
```
|
||||
|
||||
There is also an experimental lazy jit mode. In this mode functions are only compiled once they are
|
||||
first called.
|
||||
|
||||
```bash
|
||||
$ $cg_clif_dir/dist/cargo-clif lazy-jit
|
||||
$ $cg_clif_dir/dist/rustc-clif -Cllvm-args=jit-mode -Cprefer-dynamic my_crate.rs
|
||||
```
|
||||
|
||||
## Shell
|
||||
@ -54,7 +47,7 @@ These are a few functions that allow you to easily run rust code from the shell
|
||||
|
||||
```bash
|
||||
function jit_naked() {
|
||||
echo "$@" | $cg_clif_dir/dist/rustc-clif - -Zunstable-options -Cllvm-args=mode=jit-lazy -Cprefer-dynamic
|
||||
echo "$@" | $cg_clif_dir/dist/rustc-clif - -Zunstable-options -Cllvm-args=jit-mode-Cprefer-dynamic
|
||||
}
|
||||
|
||||
function jit() {
|
||||
|
@ -6,16 +6,25 @@
|
||||
#![feature(gen_blocks)]
|
||||
|
||||
fn foo() -> impl Iterator<Item = u32> {
|
||||
gen { yield 42; for x in 3..6 { yield x } }
|
||||
gen {
|
||||
yield 42;
|
||||
for x in 3..6 {
|
||||
yield x
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn moved() -> impl Iterator<Item = u32> {
|
||||
let mut x = "foo".to_string();
|
||||
gen move {
|
||||
yield 42;
|
||||
if x == "foo" { return }
|
||||
if x == "foo" {
|
||||
return;
|
||||
}
|
||||
x.clear();
|
||||
for x in 3..6 { yield x }
|
||||
for x in 3..6 {
|
||||
yield x
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -32,5 +41,4 @@ fn main() {
|
||||
let mut iter = moved();
|
||||
assert_eq!(iter.next(), Some(42));
|
||||
assert_eq!(iter.next(), None);
|
||||
|
||||
}
|
||||
|
@ -10,20 +10,20 @@ Cranelift doesn't support them yet
|
||||
library/core/tests/atomic.rs | 4 ---
|
||||
4 files changed, 4 insertions(+), 50 deletions(-)
|
||||
|
||||
diff --git a/tests/lib.rs b/tests/lib.rs
|
||||
diff --git a/coretests/tests/lib.rs b/coretests/tests/lib.rs
|
||||
index 1e336bf..35e6f54 100644
|
||||
--- a/tests/lib.rs
|
||||
+++ b/tests/lib.rs
|
||||
--- a/coretests/tests/lib.rs
|
||||
+++ b/coretests/tests/lib.rs
|
||||
@@ -2,5 +2,4 @@
|
||||
// tidy-alphabetical-start
|
||||
-#![cfg_attr(target_has_atomic = "128", feature(integer_atomics))]
|
||||
#![cfg_attr(test, feature(cfg_match))]
|
||||
#![feature(alloc_layout_extra)]
|
||||
#![feature(array_chunks)]
|
||||
diff --git a/tests/atomic.rs b/tests/atomic.rs
|
||||
diff --git a/coretests/tests/atomic.rs b/coretests/tests/atomic.rs
|
||||
index b735957..ea728b6 100644
|
||||
--- a/tests/atomic.rs
|
||||
+++ b/tests/atomic.rs
|
||||
--- a/coretests/tests/atomic.rs
|
||||
+++ b/coretests/tests/atomic.rs
|
||||
@@ -185,10 +185,6 @@ fn atomic_alignment() {
|
||||
assert_eq!(align_of::<AtomicU64>(), size_of::<AtomicU64>());
|
||||
#[cfg(target_has_atomic = "64")]
|
@ -1,48 +0,0 @@
|
||||
From eb703e627e7a84f1cd8d0d87f0f69da1f0acf765 Mon Sep 17 00:00:00 2001
|
||||
From: bjorn3 <bjorn3@users.noreply.github.com>
|
||||
Date: Fri, 3 Dec 2021 12:16:30 +0100
|
||||
Subject: [PATCH] Disable long running tests
|
||||
|
||||
---
|
||||
library/core/tests/slice.rs | 2 ++
|
||||
1 file changed, 2 insertions(+)
|
||||
|
||||
diff --git a/tests/slice.rs b/tests/slice.rs
|
||||
index 8402833..84592e0 100644
|
||||
--- a/tests/slice.rs
|
||||
+++ b/tests/slice.rs
|
||||
@@ -1809,6 +1809,7 @@ fn sort_unstable() {
|
||||
}
|
||||
}
|
||||
|
||||
+/*
|
||||
#[test]
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
#[cfg_attr(miri, ignore)] // Miri is too slow
|
||||
@@ -1914,6 +1915,7 @@ fn select_nth_unstable() {
|
||||
v.select_nth_unstable(0);
|
||||
assert!(v == [0xDEADBEEF]);
|
||||
}
|
||||
+*/
|
||||
|
||||
#[test]
|
||||
#[should_panic(expected = "index 0 greater than length of slice")]
|
||||
@@ -2462,6 +2462,7 @@ take_tests! {
|
||||
#[cfg(not(miri))] // unused in Miri
|
||||
const EMPTY_MAX: &'static [()] = &[(); usize::MAX];
|
||||
|
||||
+/*
|
||||
// can't be a constant due to const mutability rules
|
||||
#[cfg(not(miri))] // unused in Miri
|
||||
macro_rules! empty_max_mut {
|
||||
@@ -2485,6 +2486,7 @@ take_tests! {
|
||||
(split_off_mut_oob_max_range_to_inclusive, (..=usize::MAX), None, empty_max_mut!()),
|
||||
(split_off_mut_in_bounds_max_range_from, (usize::MAX..), Some(&mut [] as _), empty_max_mut!()),
|
||||
}
|
||||
+*/
|
||||
|
||||
#[test]
|
||||
fn test_slice_from_ptr_range() {
|
||||
--
|
||||
2.26.2.7.g19db9cfb68
|
||||
|
@ -0,0 +1,105 @@
|
||||
From eb703e627e7a84f1cd8d0d87f0f69da1f0acf765 Mon Sep 17 00:00:00 2001
|
||||
From: bjorn3 <bjorn3@users.noreply.github.com>
|
||||
Date: Fri, 3 Dec 2021 12:16:30 +0100
|
||||
Subject: [PATCH] Disable long running tests
|
||||
|
||||
---
|
||||
library/coretests/tests/slice.rs | 2 ++
|
||||
1 file changed, 2 insertions(+)
|
||||
|
||||
diff --git a/coretests/tests/slice.rs b/coretests/tests/slice.rs
|
||||
index 8402833..84592e0 100644
|
||||
--- a/coretests/tests/slice.rs
|
||||
+++ b/coretests/tests/slice.rs
|
||||
@@ -1809,6 +1809,7 @@ fn sort_unstable() {
|
||||
}
|
||||
}
|
||||
|
||||
+/*
|
||||
#[test]
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
#[cfg_attr(miri, ignore)] // Miri is too slow
|
||||
@@ -1914,6 +1915,7 @@ fn select_nth_unstable() {
|
||||
v.select_nth_unstable(0);
|
||||
assert!(v == [0xDEADBEEF]);
|
||||
}
|
||||
+*/
|
||||
|
||||
#[test]
|
||||
#[should_panic(expected = "index 0 greater than length of slice")]
|
||||
@@ -2462,6 +2462,7 @@ take_tests! {
|
||||
#[cfg(not(miri))] // unused in Miri
|
||||
const EMPTY_MAX: &'static [()] = &[(); usize::MAX];
|
||||
|
||||
+/*
|
||||
// can't be a constant due to const mutability rules
|
||||
#[cfg(not(miri))] // unused in Miri
|
||||
macro_rules! empty_max_mut {
|
||||
@@ -2485,6 +2486,7 @@ take_tests! {
|
||||
(split_off_mut_oob_max_range_to_inclusive, (..=usize::MAX), None, empty_max_mut!()),
|
||||
(split_off_mut_in_bounds_max_range_from, (usize::MAX..), Some(&mut [] as _), empty_max_mut!()),
|
||||
}
|
||||
+*/
|
||||
|
||||
#[test]
|
||||
fn test_slice_from_ptr_range() {
|
||||
diff --git a/alloctests/tests/sort/tests.rs b/alloctests/tests/sort/tests.rs
|
||||
index d321f8d..8b2040a 100644
|
||||
--- a/alloctests/tests/sort/tests.rs
|
||||
+++ b/alloctests/tests/sort/tests.rs
|
||||
@@ -1,3 +1,5 @@
|
||||
+#![cfg(any())]
|
||||
+
|
||||
use std::cell::Cell;
|
||||
use std::cmp::Ordering;
|
||||
use std::fmt::Debug;
|
||||
diff --git a/alloctests/tests/str.rs b/alloctests/tests/str.rs
|
||||
index 906fa2d..b82fa99 100644
|
||||
--- a/alloctests/tests/str.rs
|
||||
+++ b/alloctests/tests/str.rs
|
||||
@@ -2234,7 +2234,7 @@ fn const_str_ptr() {
|
||||
const C: *const u8 = B as *const u8;
|
||||
|
||||
// Miri does not deduplicate consts (https://github.com/rust-lang/miri/issues/131)
|
||||
- #[cfg(not(miri))]
|
||||
+ #[cfg(any())]
|
||||
{
|
||||
let foo = &A as *const u8;
|
||||
assert_eq!(foo, C);
|
||||
diff --git a/alloctests/tests/task.rs b/alloctests/tests/task.rs
|
||||
index 390dec1..87df6e6 100644
|
||||
--- a/alloctests/tests/task.rs
|
||||
+++ b/alloctests/tests/task.rs
|
||||
@@ -4,7 +4,7 @@ use alloc::task::{LocalWake, Wake};
|
||||
use core::task::{LocalWaker, Waker};
|
||||
|
||||
#[test]
|
||||
-#[cfg_attr(miri, ignore)] // `will_wake` doesn't guarantee that this test will work, and indeed on Miri it can fail
|
||||
+#[ignore] // `will_wake` doesn't guarantee that this test will work, and indeed on Miri it can fail
|
||||
fn test_waker_will_wake_clone() {
|
||||
struct NoopWaker;
|
||||
|
||||
@@ -20,7 +20,7 @@ fn test_waker_will_wake_clone() {
|
||||
}
|
||||
|
||||
#[test]
|
||||
-#[cfg_attr(miri, ignore)] // `will_wake` doesn't guarantee that this test will work, and indeed on Miri it can fail
|
||||
+#[ignore] // `will_wake` doesn't guarantee that this test will work, and indeed on Miri it can fail
|
||||
fn test_local_waker_will_wake_clone() {
|
||||
struct NoopWaker;
|
||||
|
||||
diff --git a/alloctests/tests/vec.rs b/alloctests/tests/vec.rs
|
||||
index f430d97..cfbd3cb 100644
|
||||
--- a/alloctests/tests/vec.rs
|
||||
+++ b/alloctests/tests/vec.rs
|
||||
@@ -762,6 +762,7 @@ fn test_drain_inclusive_range() {
|
||||
}
|
||||
|
||||
#[test]
|
||||
+#[ignore]
|
||||
fn test_drain_max_vec_size() {
|
||||
let mut v = Vec::<()>::with_capacity(usize::MAX);
|
||||
unsafe {
|
||||
--
|
||||
2.26.2.7.g19db9cfb68
|
||||
|
@ -1,26 +0,0 @@
|
||||
From 175d52c5e1779764b66777db1e6f172c2dc365ff Mon Sep 17 00:00:00 2001
|
||||
From: bjorn3 <17426603+bjorn3@users.noreply.github.com>
|
||||
Date: Fri, 9 Aug 2024 15:44:51 +0000
|
||||
Subject: [PATCH] Disable f16 and f128 in compiler-builtins
|
||||
|
||||
---
|
||||
library/liballoc/Cargo.toml | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/library/liballoc/Cargo.toml b/library/liballoc/Cargo.toml
|
||||
index 7165c3e48af..968552ad435 100644
|
||||
--- a/library/alloc/Cargo.toml
|
||||
+++ b/library/alloc/Cargo.toml
|
||||
@@ -11,7 +11,7 @@ test = { path = "../test" }
|
||||
bench = false
|
||||
|
||||
[dependencies]
|
||||
core = { path = "../core", public = true }
|
||||
-compiler_builtins = { version = "=0.1.151", features = ['rustc-dep-of-std'] }
|
||||
+compiler_builtins = { version = "=0.1.151", features = ['rustc-dep-of-std', 'no-f16-f128'] }
|
||||
|
||||
[features]
|
||||
compiler-builtins-mem = ['compiler_builtins/mem']
|
||||
--
|
||||
2.34.1
|
||||
|
@ -1,35 +0,0 @@
|
||||
# This file is automatically @generated by Cargo.
|
||||
# It is not intended for manual editing.
|
||||
version = 3
|
||||
|
||||
[[package]]
|
||||
name = "coretests"
|
||||
version = "0.0.0"
|
||||
dependencies = [
|
||||
"rand",
|
||||
"rand_xorshift",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand"
|
||||
version = "0.8.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404"
|
||||
dependencies = [
|
||||
"rand_core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_core"
|
||||
version = "0.6.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c"
|
||||
|
||||
[[package]]
|
||||
name = "rand_xorshift"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f"
|
||||
dependencies = [
|
||||
"rand_core",
|
||||
]
|
@ -1,4 +1,4 @@
|
||||
[toolchain]
|
||||
channel = "nightly-2025-02-15"
|
||||
channel = "nightly-2025-03-30"
|
||||
components = ["rust-src", "rustc-dev", "llvm-tools"]
|
||||
profile = "minimal"
|
||||
|
@ -1,7 +1,3 @@
|
||||
ignore = [
|
||||
"example/gen_block_iterate.rs", # uses edition 2024
|
||||
]
|
||||
|
||||
# Matches rustfmt.toml of rustc
|
||||
style_edition = "2024"
|
||||
use_small_heuristics = "Max"
|
||||
|
@ -50,19 +50,7 @@ fn main() {
|
||||
.chain([
|
||||
"--".to_string(),
|
||||
"-Zunstable-options".to_string(),
|
||||
"-Cllvm-args=mode=jit".to_string(),
|
||||
])
|
||||
.collect()
|
||||
}
|
||||
Some("lazy-jit") => {
|
||||
rustflags.push("-Cprefer-dynamic".to_owned());
|
||||
args.remove(0);
|
||||
IntoIterator::into_iter(["rustc".to_string()])
|
||||
.chain(args)
|
||||
.chain([
|
||||
"--".to_string(),
|
||||
"-Zunstable-options".to_string(),
|
||||
"-Cllvm-args=mode=jit-lazy".to_string(),
|
||||
"-Cllvm-args=jit-mode".to_string(),
|
||||
])
|
||||
.collect()
|
||||
}
|
||||
|
@ -4,7 +4,7 @@
|
||||
pushd $(dirname "$0")/../
|
||||
RUSTC="$(pwd)/dist/rustc-clif"
|
||||
popd
|
||||
PROFILE=$1 OUTPUT=$2 exec $RUSTC -Zunstable-options -Cllvm-args=mode=jit -Cprefer-dynamic $0
|
||||
PROFILE=$1 OUTPUT=$2 exec $RUSTC -Zunstable-options -Cllvm-args=jit-mode -Cprefer-dynamic $0
|
||||
#*/
|
||||
|
||||
//! This program filters away uninteresting samples and trims uninteresting frames for stackcollapse
|
||||
|
@ -64,7 +64,7 @@ case $1 in
|
||||
cg_clif=$(pwd)
|
||||
pushd ../rust
|
||||
git fetch origin master
|
||||
git checkout "$RUST_VERS"
|
||||
git -c advice.detachedHead=false checkout "$RUST_VERS"
|
||||
"$cg_clif/git-fixed-subtree.sh" push --prefix=compiler/rustc_codegen_cranelift/ "$cg_clif" sync_from_rust
|
||||
popd
|
||||
git merge sync_from_rust -m "Sync from rust $RUST_VERS"
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user