diff --git a/src/cargo/core/compiler/build_context/target_info.rs b/src/cargo/core/compiler/build_context/target_info.rs index e8ed0a07381..3c032b6e1a5 100644 --- a/src/cargo/core/compiler/build_context/target_info.rs +++ b/src/cargo/core/compiler/build_context/target_info.rs @@ -47,6 +47,8 @@ pub struct TargetInfo { pub rustdocflags: Vec, /// Whether or not rustc supports the `-Csplit-debuginfo` flag. pub supports_split_debuginfo: bool, + /// Whether or not rustc supports the `--force-warn` flag. Remove after 1.56 is stable. + pub supports_force_warn: bool, } /// Kind of each file generated by a Unit, part of `FileType`. @@ -178,6 +180,12 @@ impl TargetInfo { extra_fingerprint, ) .is_ok(); + let supports_force_warn = rustc + .cached_output( + process.clone().arg("--force-warn=rust-2021-compatibility"), + extra_fingerprint, + ) + .is_ok(); process.arg("--print=sysroot"); process.arg("--print=cfg"); @@ -253,6 +261,7 @@ impl TargetInfo { )?, cfg, supports_split_debuginfo, + supports_force_warn, }) } diff --git a/src/cargo/core/features.rs b/src/cargo/core/features.rs index d2661eaef17..524985dcaa3 100644 --- a/src/cargo/core/features.rs +++ b/src/cargo/core/features.rs @@ -139,6 +139,7 @@ pub enum Edition { // - Set LATEST_STABLE to the new version. // - Update `is_stable` to `true`. // - Set the editionNNNN feature to stable in the features macro below. +// - Update any tests that are affected. // - Update the man page for the --edition flag. // - Update unstable.md to move the edition section to the bottom. // - Update the documentation: @@ -150,9 +151,9 @@ impl Edition { /// The latest edition that is unstable. /// /// This is `None` if there is no next unstable edition. - pub const LATEST_UNSTABLE: Option = Some(Edition::Edition2021); + pub const LATEST_UNSTABLE: Option = None; /// The latest stable edition. - pub const LATEST_STABLE: Edition = Edition::Edition2018; + pub const LATEST_STABLE: Edition = Edition::Edition2021; /// Possible values allowed for the `--edition` CLI flag. /// /// This requires a static value due to the way clap works, otherwise I @@ -176,7 +177,7 @@ impl Edition { match self { Edition2015 => true, Edition2018 => true, - Edition2021 => false, + Edition2021 => true, } } @@ -398,7 +399,7 @@ features! { (stable, rust_version, "1.56", "reference/manifest.html#the-rust-version-field"), // Support for 2021 edition. - (unstable, edition2021, "", "reference/unstable.html#edition-2021"), + (stable, edition2021, "1.56", "reference/manifest.html#the-edition-field"), // Allow to specify per-package targets (compile kinds) (unstable, per_package_target, "", "reference/unstable.html#per-package-target"), diff --git a/src/cargo/ops/fix.rs b/src/cargo/ops/fix.rs index 86f5b2c4390..1d479176c3c 100644 --- a/src/cargo/ops/fix.rs +++ b/src/cargo/ops/fix.rs @@ -51,7 +51,7 @@ use log::{debug, trace, warn}; use rustfix::diagnostics::Diagnostic; use rustfix::{self, CodeFix}; -use crate::core::compiler::RustcTargetData; +use crate::core::compiler::{CompileKind, RustcTargetData, TargetInfo}; use crate::core::resolver::features::{DiffMap, FeatureOpts, FeatureResolver}; use crate::core::resolver::{HasDevUnits, Resolve, ResolveBehavior}; use crate::core::{Edition, MaybePackage, Workspace}; @@ -67,6 +67,7 @@ const FIX_ENV: &str = "__CARGO_FIX_PLZ"; const BROKEN_CODE_ENV: &str = "__CARGO_FIX_BROKEN_CODE"; const EDITION_ENV: &str = "__CARGO_FIX_EDITION"; const IDIOMS_ENV: &str = "__CARGO_FIX_IDIOMS"; +const SUPPORTS_FORCE_WARN: &str = "__CARGO_SUPPORTS_FORCE_WARN"; pub struct FixOptions { pub edition: bool, @@ -122,6 +123,17 @@ pub fn fix(ws: &Workspace<'_>, opts: &mut FixOptions) -> CargoResult<()> { let rustc = ws.config().load_global_rustc(Some(ws))?; wrapper.arg(&rustc.path); + // Remove this once 1.56 is stabilized. + let target_info = TargetInfo::new( + ws.config(), + &opts.compile_opts.build_config.requested_kinds, + &rustc, + CompileKind::Host, + )?; + if target_info.supports_force_warn { + wrapper.env(SUPPORTS_FORCE_WARN, "1"); + } + // primary crates are compiled using a cargo subprocess to do extra work of applying fixes and // repeating build until there are no more changes to be applied opts.compile_opts.build_config.primary_unit_rustc = Some(wrapper); @@ -362,7 +374,7 @@ pub fn fix_maybe_exec_rustc(config: &Config) -> CargoResult { // that we have to back it all out. if !fixes.files.is_empty() { let mut cmd = rustc.build_command(); - args.apply(&mut cmd, config); + args.apply(&mut cmd); cmd.arg("--error-format=json"); debug!("calling rustc for final verification: {:?}", cmd); let output = cmd.output().context("failed to spawn rustc")?; @@ -403,7 +415,7 @@ pub fn fix_maybe_exec_rustc(config: &Config) -> CargoResult { // - If `--broken-code`, show the error messages. // - If the fix succeeded, show any remaining warnings. let mut cmd = rustc.build_command(); - args.apply(&mut cmd, config); + args.apply(&mut cmd); for arg in args.format_args { // Add any json/error format arguments that Cargo wants. This allows // things like colored output to work correctly. @@ -497,7 +509,7 @@ fn rustfix_crate( // We'll generate new errors below. file.errors_applying_fixes.clear(); } - rustfix_and_fix(&mut fixes, rustc, filename, args, config)?; + rustfix_and_fix(&mut fixes, rustc, filename, args)?; let mut progress_yet_to_be_made = false; for (path, file) in fixes.files.iter_mut() { if file.errors_applying_fixes.is_empty() { @@ -539,7 +551,6 @@ fn rustfix_and_fix( rustc: &ProcessBuilder, filename: &Path, args: &FixArgs, - config: &Config, ) -> Result<(), Error> { // If not empty, filter by these lints. // TODO: implement a way to specify this. @@ -547,7 +558,7 @@ fn rustfix_and_fix( let mut cmd = rustc.build_command(); cmd.arg("--error-format=json"); - args.apply(&mut cmd, config); + args.apply(&mut cmd); debug!( "calling rustc to collect suggestions and validate previous fixes: {:?}", cmd @@ -822,10 +833,10 @@ impl FixArgs { }) } - fn apply(&self, cmd: &mut Command, config: &Config) { + fn apply(&self, cmd: &mut Command) { cmd.arg(&self.file); cmd.args(&self.other); - if self.prepare_for_edition.is_some() && config.nightly_features_allowed { + if self.prepare_for_edition.is_some() && env::var_os(SUPPORTS_FORCE_WARN).is_some() { // When migrating an edition, we don't want to fix other lints as // they can sometimes add suggestions that fail to apply, causing // the entire migration to fail. But those lints aren't needed to @@ -844,7 +855,7 @@ impl FixArgs { if let Some(edition) = self.prepare_for_edition { if edition.supports_compat_lint() { - if config.nightly_features_allowed { + if env::var_os(SUPPORTS_FORCE_WARN).is_some() { cmd.arg("--force-warn") .arg(format!("rust-{}-compatibility", edition)) .arg("-Zunstable-options"); diff --git a/src/doc/man/generated_txt/cargo-init.txt b/src/doc/man/generated_txt/cargo-init.txt index e96abbb28de..443f8fa0b9e 100644 --- a/src/doc/man/generated_txt/cargo-init.txt +++ b/src/doc/man/generated_txt/cargo-init.txt @@ -30,7 +30,7 @@ OPTIONS Create a package with a library target (src/lib.rs). --edition edition - Specify the Rust edition to use. Default is 2018. Possible values: + Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021 --name name diff --git a/src/doc/man/generated_txt/cargo-new.txt b/src/doc/man/generated_txt/cargo-new.txt index 69ccfe37521..4ea0ccba83d 100644 --- a/src/doc/man/generated_txt/cargo-new.txt +++ b/src/doc/man/generated_txt/cargo-new.txt @@ -25,7 +25,7 @@ OPTIONS Create a package with a library target (src/lib.rs). --edition edition - Specify the Rust edition to use. Default is 2018. Possible values: + Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021 --name name diff --git a/src/doc/man/includes/options-new.md b/src/doc/man/includes/options-new.md index 30e2b34269d..e9792f05e6a 100644 --- a/src/doc/man/includes/options-new.md +++ b/src/doc/man/includes/options-new.md @@ -10,7 +10,7 @@ Create a package with a library target (`src/lib.rs`). {{/option}} {{#option "`--edition` _edition_" }} -Specify the Rust edition to use. Default is 2018. +Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021 {{/option}} diff --git a/src/doc/src/commands/cargo-init.md b/src/doc/src/commands/cargo-init.md index 4e5dc50456e..b6790596a6c 100644 --- a/src/doc/src/commands/cargo-init.md +++ b/src/doc/src/commands/cargo-init.md @@ -39,7 +39,7 @@ This is the default behavior.
--edition edition
-
Specify the Rust edition to use. Default is 2018. +
Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021
diff --git a/src/doc/src/commands/cargo-new.md b/src/doc/src/commands/cargo-new.md index 8236a08fbbd..c9257d91293 100644 --- a/src/doc/src/commands/cargo-new.md +++ b/src/doc/src/commands/cargo-new.md @@ -34,7 +34,7 @@ This is the default behavior.
--edition edition
-
Specify the Rust edition to use. Default is 2018. +
Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021
diff --git a/src/doc/src/reference/manifest.md b/src/doc/src/reference/manifest.md index 0a3566b5062..81ea65ce79a 100644 --- a/src/doc/src/reference/manifest.md +++ b/src/doc/src/reference/manifest.md @@ -133,12 +133,12 @@ examples, etc. ```toml [package] # ... -edition = '2018' +edition = '2021' ``` Most manifests have the `edition` field filled in automatically by [`cargo new`] with the latest stable edition. By default `cargo new` creates a manifest with -the 2018 edition currently. +the 2021 edition currently. If the `edition` field is not present in `Cargo.toml`, then the 2015 edition is assumed for backwards compatibility. Note that all manifests diff --git a/src/doc/src/reference/resolver.md b/src/doc/src/reference/resolver.md index d6a97f1621b..d3476d08366 100644 --- a/src/doc/src/reference/resolver.md +++ b/src/doc/src/reference/resolver.md @@ -408,8 +408,9 @@ version = "1.0.0" resolver = "2" ``` -The version `"1"` resolver is the original resolver that shipped with Cargo up -to version 1.50, and is the default if the `resolver` is not specified. +The version `"1"` resolver is the original resolver that shipped with Cargo up to version 1.50. +The default is `"2"` if the root package specifies [`edition = "2021"`](manifest.md#the-edition-field) or a newer edition. +Otherwise the default is `"1"`. The version `"2"` resolver introduces changes in [feature unification](#features). See the [features chapter][features-2] for more diff --git a/src/doc/src/reference/unstable.md b/src/doc/src/reference/unstable.md index b64b841de82..c27b0085582 100644 --- a/src/doc/src/reference/unstable.md +++ b/src/doc/src/reference/unstable.md @@ -90,7 +90,6 @@ Each new feature described below should explain how to use it. * [Custom named profiles](#custom-named-profiles) — Adds custom named profiles in addition to the standard names. * [Profile `strip` option](#profile-strip-option) — Forces the removal of debug information and symbols from executables. * [per-package-target](#per-package-target) — Sets the `--target` to use for each individual package. - * [Edition 2021](#edition-2021) — Adds support for the 2021 Edition. * Information and metadata * [Build-plan](#build-plan) — Emits JSON information on which commands will be run. * [timings](#timings) — Generates a report on how long individual dependencies took to run. @@ -1169,34 +1168,6 @@ cargo logout -Z credential-process [crates.io]: https://crates.io/ [config file]: config.md -### edition 2021 -* Tracking Issue: [rust-lang/rust#85811](https://github.com/rust-lang/rust/issues/85811) - -Support for the 2021 [edition] can be enabled by adding the `edition2021` -unstable feature to the top of `Cargo.toml`: - -```toml -cargo-features = ["edition2021"] - -[package] -name = "my-package" -version = "0.1.0" -edition = "2021" -``` - -If you want to transition an existing project from a previous edition, then -`cargo fix --edition` can be used on the nightly channel. After running `cargo -fix`, you can switch the edition to 2021 as illustrated above. - -This feature is very unstable, and is only intended for early testing and -experimentation. Future nightly releases may introduce changes for the 2021 -edition that may break your build. - -The 2021 edition will set the default [resolver version] to "2". - -[edition]: ../../edition-guide/index.html -[resolver version]: resolver.md#resolver-versions - ### future incompat report * RFC: [#2834](https://github.com/rust-lang/rfcs/blob/master/text/2834-cargo-report-future-incompat.md) * rustc Tracking Issue: [#71249](https://github.com/rust-lang/rust/issues/71249) @@ -1444,3 +1415,9 @@ The `-Z patch-in-config` flag, and the corresponding support for `[patch]` section in Cargo configuration files has been stabilized in the 1.56 release. See the [patch field](config.html#patch) for more information. + +### edition 2021 + +The 2021 edition has been stabilized in the 1.56 release. +See the [`edition` field](manifest.md#the-edition-field) for more information on setting the edition. +See [`cargo fix --edition`](../commands/cargo-fix.md) and [The Edition Guide](../../edition-guide/index.html) for more information on migrating existing projects. diff --git a/src/etc/man/cargo-init.1 b/src/etc/man/cargo-init.1 index 4cba15fb424..16fc80f780e 100644 --- a/src/etc/man/cargo-init.1 +++ b/src/etc/man/cargo-init.1 @@ -36,7 +36,7 @@ Create a package with a library target (\fBsrc/lib.rs\fR). .sp \fB\-\-edition\fR \fIedition\fR .RS 4 -Specify the Rust edition to use. Default is 2018. +Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021 .RE .sp diff --git a/src/etc/man/cargo-new.1 b/src/etc/man/cargo-new.1 index 6d507b704f5..53b23224d0d 100644 --- a/src/etc/man/cargo-new.1 +++ b/src/etc/man/cargo-new.1 @@ -31,7 +31,7 @@ Create a package with a library target (\fBsrc/lib.rs\fR). .sp \fB\-\-edition\fR \fIedition\fR .RS 4 -Specify the Rust edition to use. Default is 2018. +Specify the Rust edition to use. Default is 2021. Possible values: 2015, 2018, 2021 .RE .sp diff --git a/tests/testsuite/fix.rs b/tests/testsuite/fix.rs index c761b3720e2..6ec21d18bd5 100644 --- a/tests/testsuite/fix.rs +++ b/tests/testsuite/fix.rs @@ -950,6 +950,10 @@ fn prepare_for_already_on_latest_unstable() { #[cargo_test] fn prepare_for_already_on_latest_stable() { // Stable counterpart of prepare_for_already_on_latest_unstable. + if !is_nightly() { + // Remove once 1.56 is stabilized. + return; + } if Edition::LATEST_UNSTABLE.is_some() { eprintln!("This test cannot run while the latest edition is unstable, skipping."); return; @@ -1434,10 +1438,6 @@ fn fix_color_message() { #[cargo_test] fn edition_v2_resolver_report() { // Show a report if the V2 resolver shows differences. - if !is_nightly() { - // 2021 is unstable - return; - } Package::new("common", "1.0.0") .feature("f1", &[]) .feature("dev-feat", &[]) @@ -1477,7 +1477,6 @@ fn edition_v2_resolver_report() { .build(); p.cargo("fix --edition --allow-no-vcs") - .masquerade_as_nightly_cargo() .with_stderr_unordered("\ [UPDATING] [..] [DOWNLOADING] crates ... @@ -1530,7 +1529,7 @@ fn rustfix_handles_multi_spans() { fn fix_edition_2021() { // Can migrate 2021, even when lints are allowed. if !is_nightly() { - // 2021 is unstable + // Remove once 1.56 is stabilized. return; } let p = project() diff --git a/tests/testsuite/new.rs b/tests/testsuite/new.rs index 71fe63be6a2..a85189ce5ff 100644 --- a/tests/testsuite/new.rs +++ b/tests/testsuite/new.rs @@ -356,7 +356,7 @@ fn new_with_edition_2018() { fn new_default_edition() { cargo_process("new foo").run(); let manifest = fs::read_to_string(paths::root().join("foo/Cargo.toml")).unwrap(); - assert!(manifest.contains("edition = \"2018\"")); + assert!(manifest.contains("edition = \"2021\"")); } #[cargo_test] @@ -377,6 +377,10 @@ fn new_with_reference_link() { #[cargo_test] fn lockfile_constant_during_new() { + if !cargo_test_support::is_nightly() { + // Remove when 1.56 is stable (cargo new defaults to 2021). + return; + } cargo_process("new foo").run(); cargo_process("build").cwd(&paths::root().join("foo")).run();