# Stabilization report
## Summary
This stabilizes using macro expansion in key-value attributes, like so:
```rust
#[doc = include_str!("my_doc.md")]
struct S;
#[path = concat!(env!("OUT_DIR"), "/generated.rs")]
mod m;
```
See the changes to the reference for details on what macros are allowed;
see Petrochenkov's excellent blog post [on internals](https://internals.rust-lang.org/t/macro-expansion-points-in-attributes/11455)
for alternatives that were considered and rejected ("why accept no more
and no less?")
This has been available on nightly since 1.50 with no major issues.
## Notes
### Accepted syntax
The parser accepts arbitrary Rust expressions in this position, but any expression other than a macro invocation will ultimately lead to an error because it is not expected by the built-in expression forms (e.g., `#[doc]`). Note that decorators and the like may be able to observe other expression forms.
### Expansion ordering
Expansion of macro expressions in "inert" attributes occurs after decorators have executed, analogously to macro expressions appearing in the function body or other parts of decorator input.
There is currently no way for decorators to accept macros in key-value position if macro expansion must be performed before the decorator executes (if the macro can simply be copied into the output for later expansion, that can work).
## Test cases
- https://github.com/rust-lang/rust/blob/master/src/test/ui/attributes/key-value-expansion-on-mac.rs
- https://github.com/rust-lang/rust/blob/master/src/test/rustdoc/external-doc.rs
The feature has also been dogfooded extensively in the compiler and
standard library:
- https://github.com/rust-lang/rust/pull/83329
- https://github.com/rust-lang/rust/pull/83230
- https://github.com/rust-lang/rust/pull/82641
- https://github.com/rust-lang/rust/pull/80534
## Implementation history
- Initial proposal: https://github.com/rust-lang/rust/issues/55414#issuecomment-554005412
- Experiment to see how much code it would break: https://github.com/rust-lang/rust/pull/67121
- Preliminary work to restrict expansion that would conflict with this
feature: https://github.com/rust-lang/rust/pull/77271
- Initial implementation: https://github.com/rust-lang/rust/pull/78837
- Fix for an ICE: https://github.com/rust-lang/rust/pull/80563
## Unresolved Questions
~~https://github.com/rust-lang/rust/pull/83366#issuecomment-805180738 listed some concerns, but they have been resolved as of this final report.~~
## Additional Information
There are two workarounds that have a similar effect for `#[doc]`
attributes on nightly. One is to emulate this behavior by using a limited version of this feature that was stabilized for historical reasons:
```rust
macro_rules! forward_inner_docs {
($e:expr => $i:item) => {
#[doc = $e]
$i
};
}
forward_inner_docs!(include_str!("lib.rs") => struct S {});
```
This also works for other attributes (like `#[path = concat!(...)]`).
The other is to use `doc(include)`:
```rust
#![feature(external_doc)]
#[doc(include = "lib.rs")]
struct S {}
```
The first works, but is non-trivial for people to discover, and
difficult to read and maintain. The second is a strange special-case for
a particular use of the macro. This generalizes it to work for any use
case, not just including files.
I plan to remove `doc(include)` when this is stabilized. The
`forward_inner_docs` workaround will still compile without warnings, but
I expect it to be used less once it's no longer necessary.
Parse unnamed fields of struct and union type
Added the `unnamed_fields` feature gate.
This is a prototype of [RFC 2102](https://github.com/rust-lang/rust/issues/49804), so any suggestions are greatly appreciated.
r? `@petrochenkov`
have on_completion record subcycles
have on_completion record subcycles
Rework `on_completion` method so that it removes all
provisional cache entries that are "below" a completed
node (while leaving those entries that are not below
the node).
This corrects an imprecise result that could in turn lead
to an incremental compilation failure. Under the old
scheme, if you had:
* A depends on...
* B depends on A
* C depends on...
* D depends on C
* T: 'static
then the provisional results for A, B, C, and D would all
be entangled. Thus, if A was `EvaluatedToOkModuloRegions`
(because of that final condition), then the result for C and
D would also be demoted to "ok modulo regions".
In reality, though, the result for C depends only on C and itself,
and is not dependent on regions. If we happen to evaluate the
cycle starting from C, we would never reach A, and hence the
result would be "ok".
Under the new scheme, the provisional results for C and D
are moved to the permanent cache immediately and are not affected
by the result of A.
Fixes#83538
r? `@Aaron1011`
This attribute will cause us to invoke evaluate on every where clause of an
invoked function and to generate an error with the result.
Without this, it is very difficult to observe the effects of invoking the trait
evaluator.
Disallows `#![feature(no_coverage)]` on stable and beta (using standard crate-level gating)
Fixes: #84836
Removes the function-level feature gating solution originally implemented, and solves the same problem using `allow_internal_unstable`, so normal crate-level feature gating mechanism can still be used (which disallows the feature on stable and beta).
I tested this, building the compiler with and without `CFG_DISABLE_UNSTABLE_FEATURES=1`
With unstable features disabled, I get the expected result as shown here:
```shell
$ ./build/x86_64-unknown-linux-gnu/stage1/bin/rustc src/test/run-make-fulldeps/coverage/no_cov_crate.rs
error[E0554]: `#![feature]` may not be used on the dev release channel
--> src/test/run-make-fulldeps/coverage/no_cov_crate.rs:2:1
|
2 | #![feature(no_coverage)]
| ^^^^^^^^^^^^^^^^^^^^^^^^
error: aborting due to previous error
For more information about this error, try `rustc --explain E0554`.
```
r? ````@Mark-Simulacrum````
cc: ````@tmandry```` ````@wesleywiser````
This commit implements both the native linking modifiers infrastructure
as well as an initial attempt at the individual modifiers from the RFC.
It also introduces a feature flag for the general syntax along with
individual feature flags for each modifier.
using allow_internal_unstable (as recommended)
Fixes: #84836
```shell
$ ./build/x86_64-unknown-linux-gnu/stage1/bin/rustc src/test/run-make-fulldeps/coverage/no_cov_crate.rs
error[E0554]: `#![feature]` may not be used on the dev release channel
--> src/test/run-make-fulldeps/coverage/no_cov_crate.rs:2:1
|
2 | #![feature(no_coverage)]
| ^^^^^^^^^^^^^^^^^^^^^^^^
error: aborting due to previous error
For more information about this error, try `rustc --explain E0554`.
```
Implement RFC 1260 with feature_name `imported_main`.
This is the second extraction part of #84062 plus additional adjustments.
This (mostly) implements RFC 1260.
However there's still one test case failure in the extern crate case. Maybe `LocalDefId` doesn't work here? I'm not sure.
cc https://github.com/rust-lang/rust/issues/28937
r? `@petrochenkov`
Adds feature-gated `#[no_coverage]` function attribute, to fix derived Eq `0` coverage issue #83601
Derived Eq no longer shows uncovered
The Eq trait has a special hidden function. MIR `InstrumentCoverage`
would add this function to the coverage map, but it is never called, so
the `Eq` trait would always appear uncovered.
Fixes: #83601
The fix required creating a new function attribute `no_coverage` to mark
functions that should be ignored by `InstrumentCoverage` and the
coverage `mapgen` (during codegen).
Adding a `no_coverage` feature gate with tracking issue #84605.
r? `@tmandry`
cc: `@wesleywiser`
Revert "Rollup merge of #82296 - spastorino:pubrules, r=nikomatsakis"
This reverts commit e2561c58a4, reversing
changes made to 2982ba50fc.
As discussed in #83641 this feature is not complete and in particular doesn't work cross macros and given that this is not going to be included in edition 2021 nobody seems to be trying to fix the underlying problem. When can add this again I guess, whenever somebody has the time to make it work cross crates.
r? `@nikomatsakis`
The Eq trait has a special hidden function. MIR `InstrumentCoverage`
would add this function to the coverage map, but it is never called, so
the `Eq` trait would always appear uncovered.
Fixes: #83601
The fix required creating a new function attribute `no_coverage` to mark
functions that should be ignored by `InstrumentCoverage` and the
coverage `mapgen` (during codegen).
While testing, I also noticed two other issues:
* spanview debug file output ICEd on a function with no body. The
workaround for this is included in this PR.
* `assert_*!()` macro coverage can appear covered if followed by another
`assert_*!()` macro. Normally they appear uncovered. I submitted a new
Issue #84561, and added a coverage test to demonstrate this issue.
various const parameter defaults improvements
Actually resolve names in const parameter defaults, fixing `struct Foo<const N: usize = { usize::MAX }>`.
---
Split generic parameter ban rib for types and consts, allowing
```rust
#![feature(const_generics_defaults)]
struct Q;
struct Foo<T = Q, const Q: usize = 3>(T);
```
---
Remove the type/const ordering restriction if `const_generics_defaults` is active, even if `const_generics` is not. allowing us to stabilize and test const param defaults separately.
---
Check well formedness of const parameter defaults, eagerly emitting an error for `struct Foo<const N: usize = { 0 - 1 }>`
---
Do not forbid const parameters in param defaults, allowing `struct Foo<const N: usize, T = [u8; N]>(T)` and `struct Foo<const N: usize, const M: usize = N>`. Note that this should not change anything which is stabilized, as on stable, type parameters must be in front of const parameters, which means that type parameter defaults are only allowed if no const parameters exist.
We still forbid generic parameters inside of const param types.
r? `@varkor` `@petrochenkov`
Cautiously add IntoIterator for arrays by value
Add the attribute described in #84133, `#[rustc_skip_array_during_method_dispatch]`, which effectively hides a trait from method dispatch when the receiver type is an array.
Then cherry-pick `IntoIterator for [T; N]` from #65819 and gate it with that attribute. Arrays can now be used as `IntoIterator` normally, but `array.into_iter()` has edition-dependent behavior, returning `slice::Iter` for 2015 and 2018 editions, or `array::IntoIter` for 2021 and later.
r? `@nikomatsakis`
cc `@LukasKalbertodt` `@rust-lang/libs`
further split up const_fn feature flag
This continues the work on splitting up `const_fn` into separate feature flags:
* `const_fn_trait_bound` for `const fn` with trait bounds
* `const_fn_unsize` for unsizing coercions in `const fn` (looks like only `dyn` unsizing is still guarded here)
I don't know if there are even any things left that `const_fn` guards... at least libcore and liballoc do not need it any more.
`@oli-obk` are you currently able to do reviews?
Match against attribute name when validating attributes
Extract attribute name once and match it against symbols that are being
validated, instead of using `Session::check_name` for each symbol
individually.
Assume that all validated attributes are used, instead of marking them
as such, since the attribute check should be exhaustive.
Stablize `non-ascii-idents`
This is the stablization PR for RFC 2457. Currently this is waiting on fcp in [tracking issue](https://github.com/rust-lang/rust/issues/55467).
r? `@Manishearth`
Extract attribute name once and match it against symbols that are being
validated, instead of using `Session::check_name` for each symbol
individually.
Assume that all validated attributes are used, instead of marking them
as such, since the attribute check should be exhaustive.
This commit implements the idea of a new ABI for the WebAssembly target,
one called `"wasm"`. This ABI is entirely of my own invention
and has no current precedent, but I think that the addition of this ABI
might help solve a number of issues with the WebAssembly targets.
When `wasm32-unknown-unknown` was first added to Rust I naively
"implemented an abi" for the target. I then went to write `wasm-bindgen`
which accidentally relied on details of this ABI. Turns out the ABI
definition didn't match C, which is causing issues for C/Rust interop.
Currently the compiler has a "wasm32 bindgen compat" ABI which is the
original implementation I added, and it's purely there for, well,
`wasm-bindgen`.
Another issue with the WebAssembly target is that it's not clear to me
when and if the default C ABI will change to account for WebAssembly's
multi-value feature (a feature that allows functions to return multiple
values). Even if this does happen, though, it seems like the C ABI will
be guided based on the performance of WebAssembly code and will likely
not match even what the current wasm-bindgen-compat ABI is today. This
leaves a hole in Rust's expressivity in binding WebAssembly where given
a particular import type, Rust may not be able to import that signature
with an updated C ABI for multi-value.
To fix these issues I had the idea of a new ABI for WebAssembly, one
called `wasm`. The definition of this ABI is "what you write
maps straight to wasm". The goal here is that whatever you write down in
the parameter list or in the return values goes straight into the
function's signature in the WebAssembly file. This special ABI is for
intentionally matching the ABI of an imported function from the
environment or exporting a function with the right signature.
With the addition of a new ABI, this enables rustc to:
* Eventually remove the "wasm-bindgen compat hack". Once this
ABI is stable wasm-bindgen can switch to using it everywhere.
Afterwards the wasm32-unknown-unknown target can have its default ABI
updated to match C.
* Expose the ability to precisely match an ABI signature for a
WebAssembly function, regardless of what the C ABI that clang chooses
turns out to be.
* Continue to evolve the definition of the default C ABI to match what
clang does on all targets, since the purpose of that ABI will be
explicitly matching C rather than generating particular function
imports/exports.
Naturally this is implemented as an unstable feature initially, but it
would be nice for this to get stabilized (if it works) in the near-ish
future to remove the wasm32-unknown-unknown incompatibility with the C
ABI. Doing this, however, requires the feature to be on stable because
wasm-bindgen works with stable Rust.
Allow specifying alignment for functions
Fixes#75072
This allows the user to specify alignment for functions, which can be useful for low level work where functions need to necessarily be aligned to a specific value.
I believe the error cases not covered in the match are caught earlier based on my testing so I had them just return `None`.
Rename `#[doc(spotlight)]` to `#[doc(notable_trait)]`
Fixes#80936.
"spotlight" is not a very specific or self-explaining name.
Additionally, the dialog that it triggers is called "Notable traits".
So, "notable trait" is a better name.
* Rename `#[doc(spotlight)]` to `#[doc(notable_trait)]`
* Rename `#![feature(doc_spotlight)]` to `#![feature(doc_notable_trait)]`
* Update documentation
* Improve documentation
r? `@Manishearth`
"spotlight" is not a very specific or self-explaining name.
Additionally, the dialog that it triggers is called "Notable traits".
So, "notable trait" is a better name.
* Rename `#[doc(spotlight)]` to `#[doc(notable_trait)]`
* Rename `#![feature(doc_spotlight)]` to `#![feature(doc_notable_trait)]`
* Update documentation
* Improve documentation
Implement RFC 2945: "C-unwind" ABI
## Implement RFC 2945: "C-unwind" ABI
This branch implements [RFC 2945]. The tracking issue for this RFC is #74990.
The feature gate for the issue is `#![feature(c_unwind)]`.
This RFC was created as part of the ffi-unwind project group tracked at rust-lang/lang-team#19.
### Changes
Further details will be provided in commit messages, but a high-level overview
of the changes follows:
* A boolean `unwind` payload is added to the `C`, `System`, `Stdcall`,
and `Thiscall` variants, marking whether unwinding across FFI boundaries is
acceptable. The cases where each of these variants' `unwind` member is true
correspond with the `C-unwind`, `system-unwind`, `stdcall-unwind`, and
`thiscall-unwind` ABI strings introduced in RFC 2945 [3].
* This commit adds a `c_unwind` feature gate for the new ABI strings.
Tests for this feature gate are included in `src/test/ui/c-unwind/`, which
ensure that this feature gate works correctly for each of the new ABIs.
A new language features entry in the unstable book is added as well.
* We adjust the `rustc_middle::ty::layout::fn_can_unwind` function,
used to compute whether or not a `FnAbi` object represents a function that
should be able to unwind when `panic=unwind` is in use.
* Changes are also made to
`rustc_mir_build::build::should_abort_on_panic` so that the function ABI is
used to determind whether it should abort, assuming that the `panic=unwind`
strategy is being used, and no explicit unwind attribute was provided.
[RFC 2945]: https://github.com/rust-lang/rfcs/blob/master/text/2945-c-unwind-abi.md
Stabilize `unsafe_op_in_unsafe_fn` lint
This makes it possible to override the level of the `unsafe_op_in_unsafe_fn`, as proposed in https://github.com/rust-lang/rust/issues/71668#issuecomment-729770896.
Tracking issue: #71668
r? ```@nikomatsakis``` cc ```@SimonSapin``` ```@RalfJung```
# Stabilization report
This is a stabilization report for `#![feature(unsafe_block_in_unsafe_fn)]`.
## Summary
Currently, the body of unsafe functions is an unsafe block, i.e. you can perform unsafe operations inside.
The `unsafe_op_in_unsafe_fn` lint, stabilized here, can be used to change this behavior, so performing unsafe operations in unsafe functions requires an unsafe block.
For now, the lint is allow-by-default, which means that this PR does not change anything without overriding the lint level.
For more information, see [RFC 2585](https://github.com/rust-lang/rfcs/blob/master/text/2585-unsafe-block-in-unsafe-fn.md)
### Example
```rust
// An `unsafe fn` for demonstration purposes.
// Calling this is an unsafe operation.
unsafe fn unsf() {}
// #[allow(unsafe_op_in_unsafe_fn)] by default,
// the behavior of `unsafe fn` is unchanged
unsafe fn allowed() {
// Here, no `unsafe` block is needed to
// perform unsafe operations...
unsf();
// ...and any `unsafe` block is considered
// unused and is warned on by the compiler.
unsafe {
unsf();
}
}
#[warn(unsafe_op_in_unsafe_fn)]
unsafe fn warned() {
// Removing this `unsafe` block will
// cause the compiler to emit a warning.
// (Also, no "unused unsafe" warning will be emitted here.)
unsafe {
unsf();
}
}
#[deny(unsafe_op_in_unsafe_fn)]
unsafe fn denied() {
// Removing this `unsafe` block will
// cause a compilation error.
// (Also, no "unused unsafe" warning will be emitted here.)
unsafe {
unsf();
}
}
```
### Overview
This commit begins the implementation work for RFC 2945. For more
information, see the rendered RFC [1] and tracking issue [2].
A boolean `unwind` payload is added to the `C`, `System`, `Stdcall`,
and `Thiscall` variants, marking whether unwinding across FFI
boundaries is acceptable. The cases where each of these variants'
`unwind` member is true correspond with the `C-unwind`,
`system-unwind`, `stdcall-unwind`, and `thiscall-unwind` ABI strings
introduced in RFC 2945 [3].
### Feature Gate and Unstable Book
This commit adds a `c_unwind` feature gate for the new ABI strings.
Tests for this feature gate are included in `src/test/ui/c-unwind/`,
which ensure that this feature gate works correctly for each of the
new ABIs.
A new language features entry in the unstable book is added as well.
### Further Work To Be Done
This commit does not proceed to implement the new unwinding ABIs,
and is intentionally scoped specifically to *defining* the ABIs and
their feature flag.
### One Note on Test Churn
This will lead to some test churn, in re-blessing hash tests, as the
deleted comment in `src/librustc_target/spec/abi.rs` mentioned,
because we can no longer guarantee the ordering of the `Abi`
variants.
While this is a downside, this decision was made bearing in mind
that RFC 2945 states the following, in the "Other `unwind` Strings"
section [3]:
> More unwind variants of existing ABI strings may be introduced,
> with the same semantics, without an additional RFC.
Adding a new variant for each of these cases, rather than specifying
a payload for a given ABI, would quickly become untenable, and make
working with the `Abi` enum prone to mistakes.
This approach encodes the unwinding information *into* a given ABI,
to account for the future possibility of other `-unwind` ABI
strings.
### Ignore Directives
`ignore-*` directives are used in two of our `*-unwind` ABI test
cases.
Specifically, the `stdcall-unwind` and `thiscall-unwind` test cases
ignore architectures that do not support `stdcall` and
`thiscall`, respectively.
These directives are cribbed from
`src/test/ui/c-variadic/variadic-ffi-1.rs` for `stdcall`, and
`src/test/ui/extern/extern-thiscall.rs` for `thiscall`.
This would otherwise fail on some targets, see:
fcf697f902
### Footnotes
[1]: https://github.com/rust-lang/rfcs/blob/master/text/2945-c-unwind-abi.md
[2]: https://github.com/rust-lang/rust/issues/74990
[3]: https://github.com/rust-lang/rfcs/blob/master/text/2945-c-unwind-abi.md#other-unwind-abi-strings
Add incomplete feature gate for inherent associate types.
Mentored by ``````@oli-obk``````
So far the only change is that instead of giving an automatic error, the following code compiles:
```rust
struct Foo;
impl Foo {
type Bar = isize;
}
```
The backend work to make it actually usable isn't there yet. In particular, this:
```rust
let x : Foo::Bar;
```
will give you:
```sh
error[E0223]: ambiguous associated type
--> /$RUSTC_DIR/src/test/ui/assoc-inherent.rs:15:13
|
LL | let x : Foo::Bar;
| ^^^^^^^^ help: use fully-qualified syntax: `<Foo as Trait>::Bar`
```
Add #[rustc_legacy_const_generics]
This is the first step towards removing `#[rustc_args_required_const]`: a new attribute is added which rewrites function calls of the form `func(a, b, c)` to `func::<{b}>(a, c)`. This allows previously stabilized functions in `stdarch` which use `rustc_args_required_const` to use const generics instead.
This new attribute is not intended to ever be stabilized, it is only intended for use in `stdarch` as a replacement for `#[rustc_args_required_const]`.
```rust
#[rustc_legacy_const_generics(1)]
pub fn foo<const Y: usize>(x: usize, z: usize) -> [usize; 3] {
[x, Y, z]
}
fn main() {
assert_eq!(foo(0 + 0, 1 + 1, 2 + 2), [0, 2, 4]);
assert_eq!(foo::<{1 + 1}>(0 + 0, 2 + 2), [0, 2, 4]);
}
```
r? `@oli-obk`
This commit adds a new ABI to be selected via `extern
"C-cmse-nonsecure-call"` on function pointers in order for the compiler to
apply the corresponding cmse_nonsecure_call callsite attribute.
For Armv8-M targets supporting TrustZone-M, this will perform a
non-secure function call by saving, clearing and calling a non-secure
function pointer using the BLXNS instruction.
See the page on the unstable book for details.
Signed-off-by: Hugues de Valon <hugues.devalon@arm.com>
Enforce that query results implement Debug
Currently, we require that query keys implement `Debug`, but we do not do the same for query values. This can make incremental compilation bugs difficult to debug - there isn't a good place to print out the result loaded from disk.
This PR adds `Debug` bounds to several query-related functions, allowing us to debug-print the query value when an 'unstable fingerprint' error occurs. This required adding `#[derive(Debug)]` to a fairly large number of types - hopefully, this doesn't have much of an impact on compiler bootstrapping times.
This makes it possible to have both std::panic and core::panic as a
builtin macro, by using different builtin macro names for each.
Also removes SyntaxExtension::is_derive_copy, as the macro name (e.g.
sym::Copy) is now tracked and provides that information directly.
- Adds optional default values to const generic parameters in the AST
and HIR
- Parses these optional default values
- Adds a `const_generics_defaults` feature gate
They were originally called "opt-in, built-in traits" (OIBITs), but
people realized that the name was too confusing and a mouthful, and so
they were renamed to just "auto traits". The feature flag's name wasn't
updated, though, so that's what this PR does.
There are some other spots in the compiler that still refer to OIBITs,
but I don't think changing those now is worth it since they are internal
and not particularly relevant to this PR.
Also see <https://rust-lang.zulipchat.com/#narrow/stream/131828-t-compiler/topic/opt-in.2C.20built-in.20traits.20(auto.20traits).20feature.20name>.
RFC-2229: Implement Precise Capture Analysis
### This PR introduces
- Feature gate for RFC-2229 (incomplete) `capture_disjoint_field`
- Rustc Attribute to print out the capture analysis `rustc_capture_analysis`
- Precise capture analysis
### Description of the analysis
1. If the feature gate is not set then all variables that are not local to the closure will be added to the list of captures. (This is for backcompat)
2. The rest of the analysis is based entirely on how the captured `Place`s are used within the closure. Precise information (i.e. projections) about the `Place` is maintained throughout.
3. To reduce the amount of information we need to keep track of, we do a minimization step. In this step, we determine a list such that no Place within this list represents an ancestor path to another entry in the list. Check rust-lang/project-rfc-2229#9 for more detailed examples.
4. To keep the compiler functional as before we implement a Bridge between the results of this new analysis to existing data structures used for closure captures. Note the new capture analysis results are only part of MaybeTypeckTables that is the information is only available during typeck-ing.
### Known issues
- Statements like `let _ = x` will make the compiler ICE when used within a closure with the feature enabled. More generally speaking the issue is caused by `let` statements that create no bindings and are init'ed using a Place expression.
### Testing
We removed the code that would handle the case where the feature gate is not set, to enable the feature as default and did a bors try and perf run. More information here: #78762
### Thanks
This has been slowly in the works for a while now.
I want to call out `@Azhng` `@ChrisPardy` `@null-sleep` `@jenniferwills` `@logmosier` `@roxelo` for working on this and the previous PRs that led up to this, `@nikomatsakis` for guiding us.
Closesrust-lang/project-rfc-2229#7Closesrust-lang/project-rfc-2229#9Closesrust-lang/project-rfc-2229#6Closesrust-lang/project-rfc-2229#19
r? `@nikomatsakis`
Allow making `RUSTC_BOOTSTRAP` conditional on the crate name
Motivation: This came up in the [Zulip stream](https://rust-lang.zulipchat.com/#narrow/stream/233931-t-compiler.2Fmajor-changes/topic/Require.20users.20to.20confirm.20they.20know.20RUSTC_.E2.80.A6.20compiler-team.23350/near/208403962) for https://github.com/rust-lang/compiler-team/issues/350.
See also https://github.com/rust-lang/cargo/pull/6608#issuecomment-458546258; this implements https://github.com/rust-lang/cargo/issues/6627.
The goal is for this to eventually allow prohibiting setting `RUSTC_BOOTSTRAP` in build.rs (https://github.com/rust-lang/cargo/issues/7088).
## User-facing changes
- `RUSTC_BOOTSTRAP=1` still works; there is no current plan to remove this.
- Things like `RUSTC_BOOTSTRAP=0` no longer activate nightly features. In practice this shouldn't be a big deal, since `RUSTC_BOOTSTRAP` is the opposite of stable and everyone uses `RUSTC_BOOTSTRAP=1` anyway.
- `RUSTC_BOOTSTRAP=x` will enable nightly features only for crate `x`.
- `RUSTC_BOOTSTRAP=x,y` will enable nightly features only for crates `x` and `y`.
## Implementation changes
The main change is that `UnstableOptions::from_environment` now requires
an (optional) crate name. If the crate name is unknown (`None`), then the new feature is not available and you still have to use `RUSTC_BOOTSTRAP=1`. In practice this means the feature is only available for `--crate-name`, not for `#![crate_name]`; I'm interested in supporting the second but I'm not sure how.
Other major changes:
- Added `Session::is_nightly_build()`, which uses the `crate_name` of
the session
- Added `nightly_options::match_is_nightly_build`, a convenience method
for looking up `--crate-name` from CLI arguments.
`Session::is_nightly_build()`should be preferred where possible, since
it will take into account `#![crate_name]` (I think).
- Added `unstable_features` to `rustdoc::RenderOptions`
I'm not sure whether this counts as T-compiler or T-lang; _technically_ RUSTC_BOOTSTRAP is an implementation detail, but it's been used so much it seems like this counts as a language change too.
r? `@joshtriplett`
cc `@Mark-Simulacrum` `@hsivonen`
The main change is that `UnstableOptions::from_environment` now requires
an (optional) crate name. If the crate name is unknown (`None`), then the new feature is not available and you still have to use `RUSTC_BOOTSTRAP=1`. In practice this means the feature is only available for `--crate-name`, not for `#![crate_name]`; I'm interested in supporting the second but I'm not sure how.
Other major changes:
- Added `Session::is_nightly_build()`, which uses the `crate_name` of
the session
- Added `nightly_options::match_is_nightly_build`, a convenience method
for looking up `--crate-name` from CLI arguments.
`Session::is_nightly_build()`should be preferred where possible, since
it will take into account `#![crate_name]` (I think).
- Added `unstable_features` to `rustdoc::RenderOptions`
There is a user-facing change here: things like `RUSTC_BOOTSTRAP=0` no
longer active nightly features. In practice this shouldn't be a big
deal, since `RUSTC_BOOTSTRAP` is the opposite of stable and everyone
uses `RUSTC_BOOTSTRAP=1` anyway.
- Add tests
Check against `Cheat`, not whether nightly features are allowed.
Nightly features are always allowed on the nightly channel.
- Only call `is_nightly_build()` once within a function
- Use booleans consistently for rustc_incremental
Sessions can't be passed through threads, so `read_file` couldn't take a
session. To be consistent, also take a boolean in `write_file_header`.
Add compiler support for LLVM's x86_64 ERMSB feature
This change is needed for compiler-builtins to check for this feature
when implementing memcpy/memset. See:
https://github.com/rust-lang/compiler-builtins/pull/365
Without this change, the following code compiles, but does nothing:
```rust
#[cfg(target_feature = "ermsb")]
pub unsafe fn ermsb_memcpy() { ... }
```
The change just does compile-time detection. I think that runtime
detection will have to come in a follow-up CL to std-detect.
Like all the CPU feature flags, this just references #44839
Signed-off-by: Joe Richey <joerichey@google.com>
This change is needed for compiler-builtins to check for this feature
when implementing memcpy/memset. See:
https://github.com/rust-lang/compiler-builtins/pull/365
The change just does compile-time detection. I think that runtime
detection will have to come in a follow-up CL to std-detect.
Like all the CPU feature flags, this just references #44839
Signed-off-by: Joe Richey <joerichey@google.com>
replace `#[allow_internal_unstable]` with `#[rustc_allow_const_fn_unstable]` for `const fn`s
`#[allow_internal_unstable]` is currently used to side-step feature gate and stability checks.
While it was originally only meant to be used only on macros, its use was expanded to `const fn`s.
This pr adds stricter checks for the usage of `#[allow_internal_unstable]` (only on macros) and introduces the `#[rustc_allow_const_fn_unstable]` attribute for usage on `const fn`s.
This pr does not change any of the functionality associated with the use of `#[allow_internal_unstable]` on macros or the usage of `#[rustc_allow_const_fn_unstable]` (instead of `#[allow_internal_unstable]`) on `const fn`s (see https://github.com/rust-lang/rust/issues/69399#issuecomment-712911540).
Note: The check for `#[rustc_allow_const_fn_unstable]` currently only validates that the attribute is used on a function, because I don't know how I would check if the function is a `const fn` at the place of the check. I therefore openend this as a 'draft pull request'.
Closesrust-lang/rust#69399
r? @oli-obk
allow_internal_unstable is currently used
to side-step feature gate and stability checks.
While it was originally only meant to be used
only on macros, its use was expanded to
const functions.
This commit prepares stricter checks for the usage of allow_internal_unstable (only on macros)
and introduces the rustc_allow_const_fn_unstable attribute for usage on functions.
See rust-lang/rust#69399
Stabilize move_ref_pattern
# Implementation
- Initially the rule was added in the run-up to 1.0. The AST-based borrow checker was having difficulty correctly enforcing match expressions that combined ref and move bindings, and so it was decided to simplify forbid the combination out right.
- The move to MIR-based borrow checking made it possible to enforce the rules in a finer-grained level, but we kept the rule in place in an effort to be conservative in our changes.
- In #68376, @Centril lifted the restriction but required a feature-gate.
- This PR removes the feature-gate.
Tracking issue: #68354.
# Description
This PR is to stabilize the feature `move_ref_pattern`, which allows patterns
containing both `by-ref` and `by-move` bindings at the same time.
For example: `Foo(ref x, y)`, where `x` is `by-ref`,
and `y` is `by-move`.
The rules of moving a variable also apply here when moving *part* of a variable,
such as it can't be referenced or moved before.
If this pattern is used, it would result in *partial move*, which means that
part of the variable is moved. The variable that was partially moved from
cannot be used as a whole in this case, only the parts that are still
not moved can be used.
## Documentation
- The reference (rust-lang/reference#881)
- Rust by example (rust-lang/rust-by-example#1377)
## Tests
There are many tests, but I think one of the comperhensive ones:
- [borrowck-move-ref-pattern-pass.rs](85fbf49ce0/src/test/ui/pattern/move-ref-patterns/borrowck-move-ref-pattern-pass.rs)
- [borrowck-move-ref-pattern.rs](85fbf49ce0/src/test/ui/pattern/move-ref-patterns/borrowck-move-ref-pattern.rs)
# Examples
```rust
#[derive(PartialEq, Eq)]
struct Finished {}
#[derive(PartialEq, Eq)]
struct Processing {
status: ProcessStatus,
}
#[derive(PartialEq, Eq)]
enum ProcessStatus {
One,
Two,
Three,
}
#[derive(PartialEq, Eq)]
enum Status {
Finished(Finished),
Processing(Processing),
}
fn check_result(_url: &str) -> Status {
// fetch status from some server
Status::Processing(Processing {
status: ProcessStatus::One,
})
}
fn wait_for_result(url: &str) -> Finished {
let mut previous_status = None;
loop {
match check_result(url) {
Status::Finished(f) => return f,
Status::Processing(p) => {
match (&mut previous_status, p.status) {
(None, status) => previous_status = Some(status), // first status
(Some(previous), status) if *previous == status => {} // no change, ignore
(Some(previous), status) => { // Now it can be used
// new status
*previous = status;
}
}
}
}
}
}
```
Before, we would have used:
```rust
match (&previous_status, p.status) {
(Some(previous), status) if *previous == status => {} // no change, ignore
(_, status) => {
// new status
previous_status = Some(status);
}
}
```
Demonstrating *partial move*
```rust
fn main() {
#[derive(Debug)]
struct Person {
name: String,
age: u8,
}
let person = Person {
name: String::from("Alice"),
age: 20,
};
// `name` is moved out of person, but `age` is referenced
let Person { name, ref age } = person;
println!("The person's age is {}", age);
println!("The person's name is {}", name);
// Error! borrow of partially moved value: `person` partial move occurs
//println!("The person struct is {:?}", person);
// `person` cannot be used but `person.age` can be used as it is not moved
println!("The person's age from person struct is {}", person.age);
}
```
Related: https://github.com/rust-lang/rust/issues/66741
Guarded with `#![feature(default_alloc_error_handler)]` a default
`alloc_error_handler` is called, if a custom allocator is used and no
other custom `#[alloc_error_handler]` is defined.
The panic message does not contain the size anymore, because it would
pull in the fmt machinery, which would blow up the code size
significantly.
This patch adds support for the LLVM cmse_nonsecure_entry attribute.
This is a target-dependent attribute that only has sense for the
thumbv8m Rust targets.
You can find more information about this attribute here:
https://developer.arm.com/documentation/ecm0359818/latest/
Signed-off-by: Hugues de Valon <hugues.devalon@arm.com>
This was a hack to work around the lack of an escape hatch for the "min
`const fn`" checks in const-stable functions. Now that we have co-opted
`allow_internal_unstable` for this purpose, we no longer need the
bespoke attribute.