From 7381f9d6dc453148107e8d6fde9eb7454a0e47ba Mon Sep 17 00:00:00 2001 From: Trevor Gross Date: Mon, 18 Sep 2023 20:51:58 -0400 Subject: [PATCH 1/8] Stabilize `{IpAddr, Ipv6Addr}::to_canonical` Make `IpAddr::to_canonical` and `IpV6Addr::to_canonical` stable, as well as const stabilize `Ipv6Addr::to_ipv4_mapped`. Newly stable API: impl IpAddr { // Now stable under `ip_to_canonical` const fn to_canonical(&self) -> IpAddr; } impl Ipv6Addr { // Now stable under `ip_to_canonical` const fn to_canonical(&self) -> IpAddr; // Already stable, this makes it const stable under // `const_ipv6_to_ipv4_mapped` const fn to_ipv4_mapped(&self) -> Option } These stabilize a subset of the following tracking issues: - https://github.com/rust-lang/rust/issues/27709 - https://github.com/rust-lang/rust/issues/76205 --- library/core/src/net/ip_addr.rs | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/library/core/src/net/ip_addr.rs b/library/core/src/net/ip_addr.rs index 6a36dfec098c7..43f93667b555d 100644 --- a/library/core/src/net/ip_addr.rs +++ b/library/core/src/net/ip_addr.rs @@ -410,9 +410,12 @@ impl IpAddr { /// # Examples /// /// ``` - /// #![feature(ip)] /// use std::net::{IpAddr, Ipv4Addr, Ipv6Addr}; /// + /// let localhost_v4 = Ipv4Addr::new(127, 0, 0, 1); + /// + /// assert_eq!(IpAddr::V4(localhost_v4).to_canonical(), localhost_v4); + /// assert_eq!(IpAddr::V6(localhost_v4.to_ipv6_mapped()).to_canonical(), localhost_v4); /// assert_eq!(IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)).to_canonical().is_loopback(), true); /// assert_eq!(IpAddr::V6(Ipv6Addr::new(0, 0, 0, 0, 0, 0xffff, 0x7f00, 0x1)).is_loopback(), false); /// assert_eq!(IpAddr::V6(Ipv6Addr::new(0, 0, 0, 0, 0, 0xffff, 0x7f00, 0x1)).to_canonical().is_loopback(), true); @@ -420,11 +423,11 @@ impl IpAddr { #[inline] #[must_use = "this returns the result of the operation, \ without modifying the original"] - #[rustc_const_unstable(feature = "const_ip", issue = "76205")] - #[unstable(feature = "ip", issue = "27709")] + #[stable(feature = "ip_to_canonical", since = "CURRENT_RUSTC_VERSION")] + #[rustc_const_stable(feature = "ip_to_canonical", since = "CURRENT_RUSTC_VERSION")] pub const fn to_canonical(&self) -> IpAddr { match self { - &v4 @ IpAddr::V4(_) => v4, + IpAddr::V4(_) => *self, IpAddr::V6(v6) => v6.to_canonical(), } } @@ -1748,11 +1751,11 @@ impl Ipv6Addr { /// Some(Ipv4Addr::new(192, 10, 2, 255))); /// assert_eq!(Ipv6Addr::new(0, 0, 0, 0, 0, 0, 0, 1).to_ipv4_mapped(), None); /// ``` - #[rustc_const_unstable(feature = "const_ipv6", issue = "76205")] - #[stable(feature = "ipv6_to_ipv4_mapped", since = "1.63.0")] + #[inline] #[must_use = "this returns the result of the operation, \ without modifying the original"] - #[inline] + #[stable(feature = "ipv6_to_ipv4_mapped", since = "1.63.0")] + #[rustc_const_stable(feature = "const_ipv6_to_ipv4_mapped", since = "CURRENT_RUSTC_VERSION")] pub const fn to_ipv4_mapped(&self) -> Option { match self.octets() { [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xff, 0xff, a, b, c, d] => { @@ -1817,11 +1820,11 @@ impl Ipv6Addr { /// assert_eq!(Ipv6Addr::new(0, 0, 0, 0, 0, 0xffff, 0x7f00, 0x1).is_loopback(), false); /// assert_eq!(Ipv6Addr::new(0, 0, 0, 0, 0, 0xffff, 0x7f00, 0x1).to_canonical().is_loopback(), true); /// ``` - #[rustc_const_unstable(feature = "const_ipv6", issue = "76205")] - #[unstable(feature = "ip", issue = "27709")] + #[inline] #[must_use = "this returns the result of the operation, \ without modifying the original"] - #[inline] + #[stable(feature = "ip_to_canonical", since = "CURRENT_RUSTC_VERSION")] + #[rustc_const_stable(feature = "ip_to_canonical", since = "CURRENT_RUSTC_VERSION")] pub const fn to_canonical(&self) -> IpAddr { if let Some(mapped) = self.to_ipv4_mapped() { return IpAddr::V4(mapped); From 559ec69e4106bd257ec4474c93b7d9066467ad38 Mon Sep 17 00:00:00 2001 From: joboet Date: Tue, 26 Sep 2023 12:54:01 +0200 Subject: [PATCH 2/8] std: broaden the allowed behaviour for recursive TLS initialization --- library/std/src/thread/local.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/library/std/src/thread/local.rs b/library/std/src/thread/local.rs index 09994e47f0a69..def94acd45727 100644 --- a/library/std/src/thread/local.rs +++ b/library/std/src/thread/local.rs @@ -29,9 +29,9 @@ use crate::fmt; /// within a thread, and values that implement [`Drop`] get destructed when a /// thread exits. Some caveats apply, which are explained below. /// -/// A `LocalKey`'s initializer cannot recursively depend on itself, and using -/// a `LocalKey` in this way will cause the initializer to infinitely recurse -/// on the first call to `with`. +/// A `LocalKey`'s initializer cannot recursively depend on itself. Using a +/// `LocalKey` in this way may cause panics, aborts or infinite recursion on +/// the first call to `with`. /// /// # Examples /// From e0fe1d6008f0ba8b395636dd1c850fa91cd2f9a2 Mon Sep 17 00:00:00 2001 From: onur-ozkan Date: Sat, 14 Oct 2023 17:53:33 +0300 Subject: [PATCH 3/8] Make x capable of resolving symlinks When bootstrapping from outside of the rust source, instead of calling 'x' from the absolute path (like /home/user/rust/x), we should be able to link 'x' from the rust source to binary paths so it can be used easily. Before this change, 'x' was not capable of finding 'x.py' when called from the linked file. Signed-off-by: onur-ozkan --- x | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/x b/x index ef3eb8b04b4bf..426b58d0d4ec7 100755 --- a/x +++ b/x @@ -11,10 +11,13 @@ set -eu sh -n "$0" realpath() { - if [ -d "$1" ]; then - CDPATH='' command cd "$1" && pwd -P + local path="$1" + if [ -L "$path" ]; then + readlink -f "$path" + elif [ -d "$path" ]; then + (cd -P "$path" && pwd) else - echo "$(realpath "$(dirname "$1")")/$(basename "$1")" + echo "$(realpath "$(dirname "$path")")/$(basename "$path")" fi } From b50aa24a4e041ddbeb23e4ba701ebfef2c75acee Mon Sep 17 00:00:00 2001 From: Scott McMurray Date: Sun, 15 Oct 2023 00:49:44 -0700 Subject: [PATCH 4/8] Remove me from libcore review rotation --- triagebot.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/triagebot.toml b/triagebot.toml index 4b051db0d73f2..63b49585d7951 100644 --- a/triagebot.toml +++ b/triagebot.toml @@ -722,7 +722,7 @@ style-team = [ "/compiler/rustc_traits" = ["compiler", "types"] "/compiler/rustc_type_ir" = ["compiler", "types"] "/library/alloc" = ["libs"] -"/library/core" = ["libs", "@scottmcm"] +"/library/core" = ["libs"] "/library/panic_abort" = ["libs"] "/library/panic_unwind" = ["libs"] "/library/proc_macro" = ["@petrochenkov"] From fe9d422e7b0e279bfb8cc348fdef409a100c8dac Mon Sep 17 00:00:00 2001 From: Nilstrieb <48135649+Nilstrieb@users.noreply.github.com> Date: Sun, 15 Oct 2023 12:33:44 +0200 Subject: [PATCH 5/8] Remove trivial cast in `guaranteed_eq` I found this while accidentally breaking trivial casts in another branch. --- library/core/src/ptr/const_ptr.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/library/core/src/ptr/const_ptr.rs b/library/core/src/ptr/const_ptr.rs index 9af8f1228f0b6..a3e4f0fb90abe 100644 --- a/library/core/src/ptr/const_ptr.rs +++ b/library/core/src/ptr/const_ptr.rs @@ -842,7 +842,7 @@ impl *const T { where T: Sized, { - match intrinsics::ptr_guaranteed_cmp(self as _, other as _) { + match intrinsics::ptr_guaranteed_cmp(self, other) { 2 => None, other => Some(other == 1), } From 223674a824317284b42ba197be43fd68b957ab58 Mon Sep 17 00:00:00 2001 From: bohan Date: Sun, 15 Oct 2023 19:20:06 +0800 Subject: [PATCH 6/8] use `PatKind::error` when an ADT const value has violation --- .../rustc_mir_build/src/thir/pattern/const_to_pat.rs | 8 ++++++++ tests/ui/pattern/issue-115599.rs | 7 +++++++ tests/ui/pattern/issue-115599.stderr | 11 +++++++++++ 3 files changed, 26 insertions(+) create mode 100644 tests/ui/pattern/issue-115599.rs create mode 100644 tests/ui/pattern/issue-115599.stderr diff --git a/compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs b/compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs index 32d389c4354c7..cda10d9d4304a 100644 --- a/compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs +++ b/compiler/rustc_mir_build/src/thir/pattern/const_to_pat.rs @@ -198,6 +198,14 @@ impl<'tcx> ConstToPat<'tcx> { // We errored. Signal that in the pattern, so that follow up errors can be silenced. let kind = PatKind::Error(e); return Box::new(Pat { span: self.span, ty: cv.ty(), kind }); + } else if let ty::Adt(..) = cv.ty().kind() && matches!(cv, mir::Const::Val(..)) { + // This branch is only entered when the current `cv` is `mir::Const::Val`. + // This is because `mir::Const::ty` has already been handled by `Self::recur` + // and the invalid types may be ignored. + let err = TypeNotStructural { span: self.span, non_sm_ty }; + let e = self.tcx().sess.emit_err(err); + let kind = PatKind::Error(e); + return Box::new(Pat { span: self.span, ty: cv.ty(), kind }); } else if !self.saw_const_match_lint.get() { if let Some(mir_structural_match_violation) = mir_structural_match_violation { match non_sm_ty.kind() { diff --git a/tests/ui/pattern/issue-115599.rs b/tests/ui/pattern/issue-115599.rs new file mode 100644 index 0000000000000..7a222b90aec97 --- /dev/null +++ b/tests/ui/pattern/issue-115599.rs @@ -0,0 +1,7 @@ +const CONST_STRING: String = String::new(); + +fn main() { + let empty_str = String::from(""); + if let CONST_STRING = empty_str {} + //~^ ERROR to use a constant of type `Vec` in a pattern, `Vec` must be annotated with `#[derive(PartialEq, Eq)]` +} diff --git a/tests/ui/pattern/issue-115599.stderr b/tests/ui/pattern/issue-115599.stderr new file mode 100644 index 0000000000000..e6cb6c1ddac77 --- /dev/null +++ b/tests/ui/pattern/issue-115599.stderr @@ -0,0 +1,11 @@ +error: to use a constant of type `Vec` in a pattern, `Vec` must be annotated with `#[derive(PartialEq, Eq)]` + --> $DIR/issue-115599.rs:5:12 + | +LL | if let CONST_STRING = empty_str {} + | ^^^^^^^^^^^^ + | + = note: the traits must be derived, manual `impl`s are not sufficient + = note: see https://doc.rust-lang.org/stable/std/marker/trait.StructuralEq.html for details + +error: aborting due to previous error + From 6beb3946dfbd9f1a9cc267f740c357a4d77f1de6 Mon Sep 17 00:00:00 2001 From: bohan Date: Sun, 15 Oct 2023 19:38:22 +0800 Subject: [PATCH 7/8] use visibility to check unused imports and delete some stmts --- compiler/rustc_ast/src/lib.rs | 1 - .../rustc_codegen_llvm/src/debuginfo/mod.rs | 1 - compiler/rustc_codegen_llvm/src/mono_item.rs | 1 - compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs | 2 - compiler/rustc_infer/src/traits/mod.rs | 1 - compiler/rustc_middle/src/mir/terminator.rs | 2 - compiler/rustc_middle/src/ty/assoc.rs | 2 - .../rustc_mir_dataflow/src/framework/mod.rs | 2 +- compiler/rustc_resolve/src/check_unused.rs | 5 +-- .../src/traits/error_reporting/mod.rs | 1 - .../rustc_trait_selection/src/traits/mod.rs | 5 --- .../rustc_trait_selection/src/traits/util.rs | 2 +- library/core/tests/lib.rs | 2 - library/core/tests/num/flt2dec/mod.rs | 2 - .../portable-simd/crates/core_simd/src/mod.rs | 1 - library/std/src/sys/common/mod.rs | 1 + library/std/src/sys/unix/process/mod.rs | 1 - src/tools/clippy/tests/ui/enum_glob_use.fixed | 1 + src/tools/clippy/tests/ui/enum_glob_use.rs | 1 + src/tools/miri/tests/utils/mod.rs | 1 + .../crates/parser/src/syntax_kind.rs | 2 +- .../parser/src/syntax_kind/generated.rs | 1 - .../crates/syntax/src/tests/sourcegen_ast.rs | 1 - src/tools/rustfmt/src/config/options.rs | 2 + tests/ui/imports/pub-reexport-empty.rs | 25 ++++++++++++ tests/ui/imports/pub-reexport-empty.stderr | 20 ++++++++++ tests/ui/imports/reexports.rs | 5 ++- tests/ui/imports/reexports.stderr | 34 +++++++++++------ tests/ui/lint/unused/lint-unused-imports.rs | 2 +- .../recover-missing-semi-before-item.fixed | 2 +- .../recover-missing-semi-before-item.rs | 2 +- ...sue-46209-private-enum-variant-reexport.rs | 4 ++ ...46209-private-enum-variant-reexport.stderr | 38 +++++++++++++++---- tests/ui/privacy/private-variant-reexport.rs | 4 +- .../privacy/private-variant-reexport.stderr | 8 +++- 35 files changed, 130 insertions(+), 55 deletions(-) create mode 100644 tests/ui/imports/pub-reexport-empty.rs create mode 100644 tests/ui/imports/pub-reexport-empty.stderr diff --git a/compiler/rustc_ast/src/lib.rs b/compiler/rustc_ast/src/lib.rs index ddc7c8ee82583..73af6bd1550a0 100644 --- a/compiler/rustc_ast/src/lib.rs +++ b/compiler/rustc_ast/src/lib.rs @@ -53,7 +53,6 @@ pub mod visit; pub use self::ast::*; pub use self::ast_traits::{AstDeref, AstNodeWrapper, HasAttrs, HasNodeId, HasSpan, HasTokens}; -pub use self::format::*; use rustc_data_structures::stable_hasher::{HashStable, StableHasher}; diff --git a/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs b/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs index 30cc9ea9b8258..6d64862625ded 100644 --- a/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs +++ b/compiler/rustc_codegen_llvm/src/debuginfo/mod.rs @@ -50,7 +50,6 @@ mod utils; pub use self::create_scope_map::compute_mir_scopes; pub use self::metadata::build_global_var_di_node; -pub use self::metadata::extend_scope_to_file; #[allow(non_upper_case_globals)] const DW_TAG_auto_variable: c_uint = 0x100; diff --git a/compiler/rustc_codegen_llvm/src/mono_item.rs b/compiler/rustc_codegen_llvm/src/mono_item.rs index 38e8220569a2a..01e823396646c 100644 --- a/compiler/rustc_codegen_llvm/src/mono_item.rs +++ b/compiler/rustc_codegen_llvm/src/mono_item.rs @@ -6,7 +6,6 @@ use crate::llvm; use crate::type_of::LayoutLlvmExt; use rustc_codegen_ssa::traits::*; use rustc_hir::def_id::{DefId, LOCAL_CRATE}; -pub use rustc_middle::mir::mono::MonoItem; use rustc_middle::mir::mono::{Linkage, Visibility}; use rustc_middle::ty::layout::{FnAbiOf, LayoutOf}; use rustc_middle::ty::{self, Instance, TypeVisitableExt}; diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs index 4a245d30c8e39..bca35c7b4c8bf 100644 --- a/compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs +++ b/compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs @@ -4,9 +4,7 @@ mod arg_matrix; mod checks; mod suggestions; -pub use _impl::*; use rustc_errors::ErrorGuaranteed; -pub use suggestions::*; use crate::coercion::DynamicCoerceMany; use crate::{Diverges, EnclosingBreakables, Inherited}; diff --git a/compiler/rustc_infer/src/traits/mod.rs b/compiler/rustc_infer/src/traits/mod.rs index a5b2ccce85e1e..a26e676c52175 100644 --- a/compiler/rustc_infer/src/traits/mod.rs +++ b/compiler/rustc_infer/src/traits/mod.rs @@ -19,7 +19,6 @@ use rustc_span::Span; pub use self::FulfillmentErrorCode::*; pub use self::ImplSource::*; -pub use self::ObligationCauseCode::*; pub use self::SelectionError::*; pub use self::engine::{TraitEngine, TraitEngineExt}; diff --git a/compiler/rustc_middle/src/mir/terminator.rs b/compiler/rustc_middle/src/mir/terminator.rs index 02aab4a892d05..4866ae8e69b83 100644 --- a/compiler/rustc_middle/src/mir/terminator.rs +++ b/compiler/rustc_middle/src/mir/terminator.rs @@ -3,12 +3,10 @@ use rustc_hir::LangItem; use smallvec::SmallVec; use super::{BasicBlock, InlineAsmOperand, Operand, SourceInfo, TerminatorKind, UnwindAction}; -pub use rustc_ast::Mutability; use rustc_macros::HashStable; use std::iter; use std::slice; -pub use super::query::*; use super::*; impl SwitchTargets { diff --git a/compiler/rustc_middle/src/ty/assoc.rs b/compiler/rustc_middle/src/ty/assoc.rs index f77a8c6712efa..94a5ff13158a2 100644 --- a/compiler/rustc_middle/src/ty/assoc.rs +++ b/compiler/rustc_middle/src/ty/assoc.rs @@ -1,5 +1,3 @@ -pub use self::AssocItemContainer::*; - use crate::ty; use rustc_data_structures::sorted_map::SortedIndexMultiMap; use rustc_hir as hir; diff --git a/compiler/rustc_mir_dataflow/src/framework/mod.rs b/compiler/rustc_mir_dataflow/src/framework/mod.rs index ce30c642fcc9f..70821637acf8e 100644 --- a/compiler/rustc_mir_dataflow/src/framework/mod.rs +++ b/compiler/rustc_mir_dataflow/src/framework/mod.rs @@ -48,7 +48,7 @@ mod visitor; pub use self::cursor::{AnalysisResults, ResultsClonedCursor, ResultsCursor, ResultsRefCursor}; pub use self::direction::{Backward, Direction, Forward}; pub use self::engine::{Engine, EntrySets, Results, ResultsCloned}; -pub use self::lattice::{JoinSemiLattice, MaybeReachable, MeetSemiLattice}; +pub use self::lattice::{JoinSemiLattice, MaybeReachable}; pub use self::visitor::{visit_results, ResultsVisitable, ResultsVisitor}; /// Analysis domains are all bitsets of various kinds. This trait holds diff --git a/compiler/rustc_resolve/src/check_unused.rs b/compiler/rustc_resolve/src/check_unused.rs index 7dbbd4c34ea7d..352bf98d01fb2 100644 --- a/compiler/rustc_resolve/src/check_unused.rs +++ b/compiler/rustc_resolve/src/check_unused.rs @@ -59,7 +59,6 @@ struct UnusedImportCheckVisitor<'a, 'b, 'tcx> { base_use_tree: Option<&'a ast::UseTree>, base_id: ast::NodeId, item_span: Span, - base_use_is_pub: bool, } struct ExternCrateToLint { @@ -146,7 +145,6 @@ impl<'a, 'b, 'tcx> Visitor<'a> for UnusedImportCheckVisitor<'a, 'b, 'tcx> { // because this means that they were generated in some fashion by the // compiler and we don't need to consider them. ast::ItemKind::Use(..) if item.span.is_dummy() => return, - ast::ItemKind::Use(..) => self.base_use_is_pub = item.vis.kind.is_pub(), ast::ItemKind::ExternCrate(orig_name) => { self.extern_crate_items.push(ExternCrateToLint { id: item.id, @@ -173,7 +171,7 @@ impl<'a, 'b, 'tcx> Visitor<'a> for UnusedImportCheckVisitor<'a, 'b, 'tcx> { self.base_use_tree = Some(use_tree); } - if self.base_use_is_pub { + if self.r.effective_visibilities.is_exported(self.r.local_def_id(id)) { self.check_import_as_underscore(use_tree, id); return; } @@ -332,7 +330,6 @@ impl Resolver<'_, '_> { base_use_tree: None, base_id: ast::DUMMY_NODE_ID, item_span: DUMMY_SP, - base_use_is_pub: false, }; visit::walk_crate(&mut visitor, krate); diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs index 989c1310b76c8..79b09db2268b6 100644 --- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs @@ -20,7 +20,6 @@ use std::ops::ControlFlow; pub use self::infer_ctxt_ext::*; pub use self::type_err_ctxt_ext::*; -pub use rustc_infer::traits::error_reporting::*; // When outputting impl candidates, prefer showing those that are more similar. // diff --git a/compiler/rustc_trait_selection/src/traits/mod.rs b/compiler/rustc_trait_selection/src/traits/mod.rs index ab81d77a268d8..71007e1f0e0a7 100644 --- a/compiler/rustc_trait_selection/src/traits/mod.rs +++ b/compiler/rustc_trait_selection/src/traits/mod.rs @@ -41,11 +41,6 @@ use std::ops::ControlFlow; pub(crate) use self::project::{needs_normalization, BoundVarReplacer, PlaceholderReplacer}; -pub use self::FulfillmentErrorCode::*; -pub use self::ImplSource::*; -pub use self::ObligationCauseCode::*; -pub use self::SelectionError::*; - pub use self::coherence::{add_placeholder_note, orphan_check, overlapping_impls}; pub use self::coherence::{OrphanCheckErr, OverlapResult}; pub use self::engine::{ObligationCtxt, TraitEngineExt}; diff --git a/compiler/rustc_trait_selection/src/traits/util.rs b/compiler/rustc_trait_selection/src/traits/util.rs index a76272e9d092d..8be2ac5a8364e 100644 --- a/compiler/rustc_trait_selection/src/traits/util.rs +++ b/compiler/rustc_trait_selection/src/traits/util.rs @@ -9,7 +9,7 @@ use rustc_middle::ty::{self, ImplSubject, ToPredicate, Ty, TyCtxt, TypeVisitable use rustc_span::Span; use smallvec::SmallVec; -pub use rustc_infer::traits::{self, util::*}; +pub use rustc_infer::traits::util::*; /////////////////////////////////////////////////////////////////////////// // `TraitAliasExpander` iterator diff --git a/library/core/tests/lib.rs b/library/core/tests/lib.rs index 79601c8c19d37..280d2219b9e98 100644 --- a/library/core/tests/lib.rs +++ b/library/core/tests/lib.rs @@ -120,8 +120,6 @@ #![deny(unsafe_op_in_unsafe_fn)] #![deny(fuzzy_provenance_casts)] -extern crate test; - mod alloc; mod any; mod array; diff --git a/library/core/tests/num/flt2dec/mod.rs b/library/core/tests/num/flt2dec/mod.rs index 30843cc3dd79c..83e2707b57e8b 100644 --- a/library/core/tests/num/flt2dec/mod.rs +++ b/library/core/tests/num/flt2dec/mod.rs @@ -8,8 +8,6 @@ use core::num::flt2dec::{ }; use core::num::fmt::{Formatted, Part}; -pub use test::Bencher; - mod estimator; mod strategy { mod dragon; diff --git a/library/portable-simd/crates/core_simd/src/mod.rs b/library/portable-simd/crates/core_simd/src/mod.rs index f9891a3b7c1d7..19426769858b0 100644 --- a/library/portable-simd/crates/core_simd/src/mod.rs +++ b/library/portable-simd/crates/core_simd/src/mod.rs @@ -35,6 +35,5 @@ pub mod simd { pub use crate::core_simd::masks::*; pub use crate::core_simd::ord::*; pub use crate::core_simd::swizzle::*; - pub use crate::core_simd::swizzle_dyn::*; pub use crate::core_simd::vector::*; } diff --git a/library/std/src/sys/common/mod.rs b/library/std/src/sys/common/mod.rs index 2b8782ddf4482..b35c5d30b4113 100644 --- a/library/std/src/sys/common/mod.rs +++ b/library/std/src/sys/common/mod.rs @@ -12,6 +12,7 @@ pub mod alloc; pub mod small_c_string; +#[allow(unused_imports)] pub mod thread_local; #[cfg(test)] diff --git a/library/std/src/sys/unix/process/mod.rs b/library/std/src/sys/unix/process/mod.rs index 947ef4c8aeff5..074f0a105e329 100644 --- a/library/std/src/sys/unix/process/mod.rs +++ b/library/std/src/sys/unix/process/mod.rs @@ -1,7 +1,6 @@ pub use self::process_common::{Command, CommandArgs, ExitCode, Stdio, StdioPipes}; pub use self::process_inner::{ExitStatus, ExitStatusError, Process}; pub use crate::ffi::OsString as EnvKey; -pub use crate::sys_common::process::CommandEnvs; #[cfg_attr(any(target_os = "espidf", target_os = "horizon"), allow(unused))] mod process_common; diff --git a/src/tools/clippy/tests/ui/enum_glob_use.fixed b/src/tools/clippy/tests/ui/enum_glob_use.fixed index 9044e80268dbf..3c0db9beb1a6e 100644 --- a/src/tools/clippy/tests/ui/enum_glob_use.fixed +++ b/src/tools/clippy/tests/ui/enum_glob_use.fixed @@ -19,6 +19,7 @@ mod in_fn_test { } mod blurg { + #[allow(unused_imports)] pub use std::cmp::Ordering::*; // ok, re-export } diff --git a/src/tools/clippy/tests/ui/enum_glob_use.rs b/src/tools/clippy/tests/ui/enum_glob_use.rs index 4f157a97cbc9b..2538477f79789 100644 --- a/src/tools/clippy/tests/ui/enum_glob_use.rs +++ b/src/tools/clippy/tests/ui/enum_glob_use.rs @@ -19,6 +19,7 @@ mod in_fn_test { } mod blurg { + #[allow(unused_imports)] pub use std::cmp::Ordering::*; // ok, re-export } diff --git a/src/tools/miri/tests/utils/mod.rs b/src/tools/miri/tests/utils/mod.rs index 593f82910c6fe..7b7dc231a5019 100644 --- a/src/tools/miri/tests/utils/mod.rs +++ b/src/tools/miri/tests/utils/mod.rs @@ -1,4 +1,5 @@ #![allow(dead_code)] +#![allow(unused_imports)] #[macro_use] mod macros; diff --git a/src/tools/rust-analyzer/crates/parser/src/syntax_kind.rs b/src/tools/rust-analyzer/crates/parser/src/syntax_kind.rs index 0483adc776fa6..3ca6bd4cb111c 100644 --- a/src/tools/rust-analyzer/crates/parser/src/syntax_kind.rs +++ b/src/tools/rust-analyzer/crates/parser/src/syntax_kind.rs @@ -4,7 +4,7 @@ mod generated; #[allow(unreachable_pub)] -pub use self::generated::{SyntaxKind, T}; +pub use self::generated::SyntaxKind; impl From for SyntaxKind { #[inline] diff --git a/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs b/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs index db5278f89d560..4b589037672f4 100644 --- a/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs +++ b/src/tools/rust-analyzer/crates/parser/src/syntax_kind/generated.rs @@ -497,4 +497,3 @@ impl SyntaxKind { } #[macro_export] macro_rules ! T { [;] => { $ crate :: SyntaxKind :: SEMICOLON } ; [,] => { $ crate :: SyntaxKind :: COMMA } ; ['('] => { $ crate :: SyntaxKind :: L_PAREN } ; [')'] => { $ crate :: SyntaxKind :: R_PAREN } ; ['{'] => { $ crate :: SyntaxKind :: L_CURLY } ; ['}'] => { $ crate :: SyntaxKind :: R_CURLY } ; ['['] => { $ crate :: SyntaxKind :: L_BRACK } ; [']'] => { $ crate :: SyntaxKind :: R_BRACK } ; [<] => { $ crate :: SyntaxKind :: L_ANGLE } ; [>] => { $ crate :: SyntaxKind :: R_ANGLE } ; [@] => { $ crate :: SyntaxKind :: AT } ; [#] => { $ crate :: SyntaxKind :: POUND } ; [~] => { $ crate :: SyntaxKind :: TILDE } ; [?] => { $ crate :: SyntaxKind :: QUESTION } ; [$] => { $ crate :: SyntaxKind :: DOLLAR } ; [&] => { $ crate :: SyntaxKind :: AMP } ; [|] => { $ crate :: SyntaxKind :: PIPE } ; [+] => { $ crate :: SyntaxKind :: PLUS } ; [*] => { $ crate :: SyntaxKind :: STAR } ; [/] => { $ crate :: SyntaxKind :: SLASH } ; [^] => { $ crate :: SyntaxKind :: CARET } ; [%] => { $ crate :: SyntaxKind :: PERCENT } ; [_] => { $ crate :: SyntaxKind :: UNDERSCORE } ; [.] => { $ crate :: SyntaxKind :: DOT } ; [..] => { $ crate :: SyntaxKind :: DOT2 } ; [...] => { $ crate :: SyntaxKind :: DOT3 } ; [..=] => { $ crate :: SyntaxKind :: DOT2EQ } ; [:] => { $ crate :: SyntaxKind :: COLON } ; [::] => { $ crate :: SyntaxKind :: COLON2 } ; [=] => { $ crate :: SyntaxKind :: EQ } ; [==] => { $ crate :: SyntaxKind :: EQ2 } ; [=>] => { $ crate :: SyntaxKind :: FAT_ARROW } ; [!] => { $ crate :: SyntaxKind :: BANG } ; [!=] => { $ crate :: SyntaxKind :: NEQ } ; [-] => { $ crate :: SyntaxKind :: MINUS } ; [->] => { $ crate :: SyntaxKind :: THIN_ARROW } ; [<=] => { $ crate :: SyntaxKind :: LTEQ } ; [>=] => { $ crate :: SyntaxKind :: GTEQ } ; [+=] => { $ crate :: SyntaxKind :: PLUSEQ } ; [-=] => { $ crate :: SyntaxKind :: MINUSEQ } ; [|=] => { $ crate :: SyntaxKind :: PIPEEQ } ; [&=] => { $ crate :: SyntaxKind :: AMPEQ } ; [^=] => { $ crate :: SyntaxKind :: CARETEQ } ; [/=] => { $ crate :: SyntaxKind :: SLASHEQ } ; [*=] => { $ crate :: SyntaxKind :: STAREQ } ; [%=] => { $ crate :: SyntaxKind :: PERCENTEQ } ; [&&] => { $ crate :: SyntaxKind :: AMP2 } ; [||] => { $ crate :: SyntaxKind :: PIPE2 } ; [<<] => { $ crate :: SyntaxKind :: SHL } ; [>>] => { $ crate :: SyntaxKind :: SHR } ; [<<=] => { $ crate :: SyntaxKind :: SHLEQ } ; [>>=] => { $ crate :: SyntaxKind :: SHREQ } ; [as] => { $ crate :: SyntaxKind :: AS_KW } ; [async] => { $ crate :: SyntaxKind :: ASYNC_KW } ; [await] => { $ crate :: SyntaxKind :: AWAIT_KW } ; [box] => { $ crate :: SyntaxKind :: BOX_KW } ; [break] => { $ crate :: SyntaxKind :: BREAK_KW } ; [const] => { $ crate :: SyntaxKind :: CONST_KW } ; [continue] => { $ crate :: SyntaxKind :: CONTINUE_KW } ; [crate] => { $ crate :: SyntaxKind :: CRATE_KW } ; [do] => { $ crate :: SyntaxKind :: DO_KW } ; [dyn] => { $ crate :: SyntaxKind :: DYN_KW } ; [else] => { $ crate :: SyntaxKind :: ELSE_KW } ; [enum] => { $ crate :: SyntaxKind :: ENUM_KW } ; [extern] => { $ crate :: SyntaxKind :: EXTERN_KW } ; [false] => { $ crate :: SyntaxKind :: FALSE_KW } ; [fn] => { $ crate :: SyntaxKind :: FN_KW } ; [for] => { $ crate :: SyntaxKind :: FOR_KW } ; [if] => { $ crate :: SyntaxKind :: IF_KW } ; [impl] => { $ crate :: SyntaxKind :: IMPL_KW } ; [in] => { $ crate :: SyntaxKind :: IN_KW } ; [let] => { $ crate :: SyntaxKind :: LET_KW } ; [loop] => { $ crate :: SyntaxKind :: LOOP_KW } ; [macro] => { $ crate :: SyntaxKind :: MACRO_KW } ; [match] => { $ crate :: SyntaxKind :: MATCH_KW } ; [mod] => { $ crate :: SyntaxKind :: MOD_KW } ; [move] => { $ crate :: SyntaxKind :: MOVE_KW } ; [mut] => { $ crate :: SyntaxKind :: MUT_KW } ; [pub] => { $ crate :: SyntaxKind :: PUB_KW } ; [ref] => { $ crate :: SyntaxKind :: REF_KW } ; [return] => { $ crate :: SyntaxKind :: RETURN_KW } ; [self] => { $ crate :: SyntaxKind :: SELF_KW } ; [Self] => { $ crate :: SyntaxKind :: SELF_TYPE_KW } ; [static] => { $ crate :: SyntaxKind :: STATIC_KW } ; [struct] => { $ crate :: SyntaxKind :: STRUCT_KW } ; [super] => { $ crate :: SyntaxKind :: SUPER_KW } ; [trait] => { $ crate :: SyntaxKind :: TRAIT_KW } ; [true] => { $ crate :: SyntaxKind :: TRUE_KW } ; [try] => { $ crate :: SyntaxKind :: TRY_KW } ; [type] => { $ crate :: SyntaxKind :: TYPE_KW } ; [unsafe] => { $ crate :: SyntaxKind :: UNSAFE_KW } ; [use] => { $ crate :: SyntaxKind :: USE_KW } ; [where] => { $ crate :: SyntaxKind :: WHERE_KW } ; [while] => { $ crate :: SyntaxKind :: WHILE_KW } ; [yield] => { $ crate :: SyntaxKind :: YIELD_KW } ; [auto] => { $ crate :: SyntaxKind :: AUTO_KW } ; [builtin] => { $ crate :: SyntaxKind :: BUILTIN_KW } ; [default] => { $ crate :: SyntaxKind :: DEFAULT_KW } ; [existential] => { $ crate :: SyntaxKind :: EXISTENTIAL_KW } ; [union] => { $ crate :: SyntaxKind :: UNION_KW } ; [raw] => { $ crate :: SyntaxKind :: RAW_KW } ; [macro_rules] => { $ crate :: SyntaxKind :: MACRO_RULES_KW } ; [yeet] => { $ crate :: SyntaxKind :: YEET_KW } ; [offset_of] => { $ crate :: SyntaxKind :: OFFSET_OF_KW } ; [asm] => { $ crate :: SyntaxKind :: ASM_KW } ; [format_args] => { $ crate :: SyntaxKind :: FORMAT_ARGS_KW } ; [lifetime_ident] => { $ crate :: SyntaxKind :: LIFETIME_IDENT } ; [ident] => { $ crate :: SyntaxKind :: IDENT } ; [shebang] => { $ crate :: SyntaxKind :: SHEBANG } ; } -pub use T; diff --git a/src/tools/rust-analyzer/crates/syntax/src/tests/sourcegen_ast.rs b/src/tools/rust-analyzer/crates/syntax/src/tests/sourcegen_ast.rs index 56227fce9b5c5..dc6c96343d61c 100644 --- a/src/tools/rust-analyzer/crates/syntax/src/tests/sourcegen_ast.rs +++ b/src/tools/rust-analyzer/crates/syntax/src/tests/sourcegen_ast.rs @@ -450,7 +450,6 @@ fn generate_syntax_kinds(grammar: KindsSrc<'_>) -> String { [ident] => { $crate::SyntaxKind::IDENT }; [shebang] => { $crate::SyntaxKind::SHEBANG }; } - pub use T; }; sourcegen::add_preamble("sourcegen_ast", sourcegen::reformat(ast.to_string())) diff --git a/src/tools/rustfmt/src/config/options.rs b/src/tools/rustfmt/src/config/options.rs index 3aa1a4de99d66..231a1ceb199c7 100644 --- a/src/tools/rustfmt/src/config/options.rs +++ b/src/tools/rustfmt/src/config/options.rs @@ -1,3 +1,5 @@ +#![allow(unused_imports)] + use std::collections::{hash_set, HashSet}; use std::fmt; use std::path::{Path, PathBuf}; diff --git a/tests/ui/imports/pub-reexport-empty.rs b/tests/ui/imports/pub-reexport-empty.rs new file mode 100644 index 0000000000000..2a46f4c8de86c --- /dev/null +++ b/tests/ui/imports/pub-reexport-empty.rs @@ -0,0 +1,25 @@ +#![deny(unused_imports)] + +mod a {} + +pub use a::*; +//~^ ERROR: unused import: `a::*` + +mod b { + mod c { + #[derive(Clone)] + pub struct D; + } + pub use self::c::*; // don't show unused import lint +} + +pub use b::*; // don't show unused import lint + +mod d { + const D: i32 = 1; +} + +pub use d::*; +//~^ ERROR: unused import: `d::*` + +fn main() {} diff --git a/tests/ui/imports/pub-reexport-empty.stderr b/tests/ui/imports/pub-reexport-empty.stderr new file mode 100644 index 0000000000000..813b2ef71c513 --- /dev/null +++ b/tests/ui/imports/pub-reexport-empty.stderr @@ -0,0 +1,20 @@ +error: unused import: `a::*` + --> $DIR/pub-reexport-empty.rs:5:9 + | +LL | pub use a::*; + | ^^^^ + | +note: the lint level is defined here + --> $DIR/pub-reexport-empty.rs:1:9 + | +LL | #![deny(unused_imports)] + | ^^^^^^^^^^^^^^ + +error: unused import: `d::*` + --> $DIR/pub-reexport-empty.rs:22:9 + | +LL | pub use d::*; + | ^^^^ + +error: aborting due to 2 previous errors + diff --git a/tests/ui/imports/reexports.rs b/tests/ui/imports/reexports.rs index d76cc41be4e55..cb1a3ebe18028 100644 --- a/tests/ui/imports/reexports.rs +++ b/tests/ui/imports/reexports.rs @@ -5,9 +5,12 @@ mod a { mod foo {} mod a { - pub use super::foo; //~ ERROR cannot be re-exported + pub use super::foo; + //~^ ERROR cannot be re-exported + //~| WARNING unused import: `super::foo` pub use super::*; //~^ WARNING glob import doesn't reexport anything because no candidate is public enough + //~| WARNING unused import: `super::*` } } diff --git a/tests/ui/imports/reexports.stderr b/tests/ui/imports/reexports.stderr index 8cbff0ac73dee..401e422af0f8e 100644 --- a/tests/ui/imports/reexports.stderr +++ b/tests/ui/imports/reexports.stderr @@ -11,44 +11,44 @@ LL | pub use super::foo; | ^^^^^^^^^^ error[E0603]: module import `foo` is private - --> $DIR/reexports.rs:33:15 + --> $DIR/reexports.rs:36:15 | LL | use b::a::foo::S; | ^^^ private module import | note: the module import `foo` is defined here... - --> $DIR/reexports.rs:21:17 + --> $DIR/reexports.rs:24:17 | LL | pub use super::foo; // This is OK since the value `foo` is visible enough. | ^^^^^^^^^^ note: ...and refers to the module `foo` which is defined here - --> $DIR/reexports.rs:16:5 + --> $DIR/reexports.rs:19:5 | LL | mod foo { | ^^^^^^^ error[E0603]: module import `foo` is private - --> $DIR/reexports.rs:34:15 + --> $DIR/reexports.rs:37:15 | LL | use b::b::foo::S as T; | ^^^ private module import | note: the module import `foo` is defined here... - --> $DIR/reexports.rs:26:17 + --> $DIR/reexports.rs:29:17 | LL | pub use super::*; // This is also OK since the value `foo` is visible enough. | ^^^^^^^^ note: ...and refers to the module `foo` which is defined here - --> $DIR/reexports.rs:16:5 + --> $DIR/reexports.rs:19:5 | LL | mod foo { | ^^^^^^^ -warning: glob import doesn't reexport anything because no candidate is public enough - --> $DIR/reexports.rs:9:17 +warning: unused import: `super::foo` + --> $DIR/reexports.rs:8:17 | -LL | pub use super::*; - | ^^^^^^^^ +LL | pub use super::foo; + | ^^^^^^^^^^ | note: the lint level is defined here --> $DIR/reexports.rs:1:9 @@ -56,7 +56,19 @@ note: the lint level is defined here LL | #![warn(unused_imports)] | ^^^^^^^^^^^^^^ -error: aborting due to 3 previous errors; 1 warning emitted +warning: glob import doesn't reexport anything because no candidate is public enough + --> $DIR/reexports.rs:11:17 + | +LL | pub use super::*; + | ^^^^^^^^ + +warning: unused import: `super::*` + --> $DIR/reexports.rs:11:17 + | +LL | pub use super::*; + | ^^^^^^^^ + +error: aborting due to 3 previous errors; 3 warnings emitted Some errors have detailed explanations: E0364, E0603. For more information about an error, try `rustc --explain E0364`. diff --git a/tests/ui/lint/unused/lint-unused-imports.rs b/tests/ui/lint/unused/lint-unused-imports.rs index 953992ecf7147..4fa6511c97e1d 100644 --- a/tests/ui/lint/unused/lint-unused-imports.rs +++ b/tests/ui/lint/unused/lint-unused-imports.rs @@ -42,7 +42,7 @@ mod foo { pub struct Square{pub p: Point, pub h: usize, pub w: usize} } -mod bar { +pub mod bar { // Don't ignore on 'pub use' because we're not sure if it's used or not pub use std::cmp::PartialEq; pub struct Square; diff --git a/tests/ui/parser/recover-missing-semi-before-item.fixed b/tests/ui/parser/recover-missing-semi-before-item.fixed index 0be17e69e8ff7..acb846373cbb2 100644 --- a/tests/ui/parser/recover-missing-semi-before-item.fixed +++ b/tests/ui/parser/recover-missing-semi-before-item.fixed @@ -1,6 +1,6 @@ // run-rustfix -#![allow(unused_variables, dead_code)] +#![allow(unused_variables, dead_code, unused_imports)] fn for_struct() { let foo = 3; //~ ERROR expected `;`, found keyword `struct` diff --git a/tests/ui/parser/recover-missing-semi-before-item.rs b/tests/ui/parser/recover-missing-semi-before-item.rs index 867b7b749bb1f..ef6cfe3c4ed7a 100644 --- a/tests/ui/parser/recover-missing-semi-before-item.rs +++ b/tests/ui/parser/recover-missing-semi-before-item.rs @@ -1,6 +1,6 @@ // run-rustfix -#![allow(unused_variables, dead_code)] +#![allow(unused_variables, dead_code, unused_imports)] fn for_struct() { let foo = 3 //~ ERROR expected `;`, found keyword `struct` diff --git a/tests/ui/privacy/issue-46209-private-enum-variant-reexport.rs b/tests/ui/privacy/issue-46209-private-enum-variant-reexport.rs index 6f115e78e147b..653dcab577148 100644 --- a/tests/ui/privacy/issue-46209-private-enum-variant-reexport.rs +++ b/tests/ui/privacy/issue-46209-private-enum-variant-reexport.rs @@ -2,13 +2,17 @@ mod rank { pub use self::Professor::*; //~^ ERROR glob import doesn't reexport anything + //~| ERROR unused import: `self::Professor::*` pub use self::Lieutenant::{JuniorGrade, Full}; //~^ ERROR `JuniorGrade` is private, and cannot be re-exported //~| ERROR `Full` is private, and cannot be re-exported + //~| ERROR unused imports: `Full`, `JuniorGrade` pub use self::PettyOfficer::*; //~^ ERROR glob import doesn't reexport anything + //~| ERROR unused import: `self::PettyOfficer::*` pub use self::Crewman::*; //~^ ERROR glob import doesn't reexport anything + //~| ERROR unused import: `self::Crewman::*` enum Professor { Adjunct, diff --git a/tests/ui/privacy/issue-46209-private-enum-variant-reexport.stderr b/tests/ui/privacy/issue-46209-private-enum-variant-reexport.stderr index 59b181fab4001..df5968ba323b3 100644 --- a/tests/ui/privacy/issue-46209-private-enum-variant-reexport.stderr +++ b/tests/ui/privacy/issue-46209-private-enum-variant-reexport.stderr @@ -1,23 +1,23 @@ error[E0364]: `JuniorGrade` is private, and cannot be re-exported - --> $DIR/issue-46209-private-enum-variant-reexport.rs:5:32 + --> $DIR/issue-46209-private-enum-variant-reexport.rs:6:32 | LL | pub use self::Lieutenant::{JuniorGrade, Full}; | ^^^^^^^^^^^ | note: consider marking `JuniorGrade` as `pub` in the imported module - --> $DIR/issue-46209-private-enum-variant-reexport.rs:5:32 + --> $DIR/issue-46209-private-enum-variant-reexport.rs:6:32 | LL | pub use self::Lieutenant::{JuniorGrade, Full}; | ^^^^^^^^^^^ error[E0364]: `Full` is private, and cannot be re-exported - --> $DIR/issue-46209-private-enum-variant-reexport.rs:5:45 + --> $DIR/issue-46209-private-enum-variant-reexport.rs:6:45 | LL | pub use self::Lieutenant::{JuniorGrade, Full}; | ^^^^ | note: consider marking `Full` as `pub` in the imported module - --> $DIR/issue-46209-private-enum-variant-reexport.rs:5:45 + --> $DIR/issue-46209-private-enum-variant-reexport.rs:6:45 | LL | pub use self::Lieutenant::{JuniorGrade, Full}; | ^^^^ @@ -34,18 +34,42 @@ note: the lint level is defined here LL | #[deny(unused_imports)] | ^^^^^^^^^^^^^^ +error: unused import: `self::Professor::*` + --> $DIR/issue-46209-private-enum-variant-reexport.rs:3:13 + | +LL | pub use self::Professor::*; + | ^^^^^^^^^^^^^^^^^^ + +error: unused imports: `Full`, `JuniorGrade` + --> $DIR/issue-46209-private-enum-variant-reexport.rs:6:32 + | +LL | pub use self::Lieutenant::{JuniorGrade, Full}; + | ^^^^^^^^^^^ ^^^^ + error: glob import doesn't reexport anything because no candidate is public enough - --> $DIR/issue-46209-private-enum-variant-reexport.rs:8:13 + --> $DIR/issue-46209-private-enum-variant-reexport.rs:10:13 | LL | pub use self::PettyOfficer::*; | ^^^^^^^^^^^^^^^^^^^^^ -error: glob import doesn't reexport anything because no candidate is public enough +error: unused import: `self::PettyOfficer::*` --> $DIR/issue-46209-private-enum-variant-reexport.rs:10:13 | +LL | pub use self::PettyOfficer::*; + | ^^^^^^^^^^^^^^^^^^^^^ + +error: glob import doesn't reexport anything because no candidate is public enough + --> $DIR/issue-46209-private-enum-variant-reexport.rs:13:13 + | +LL | pub use self::Crewman::*; + | ^^^^^^^^^^^^^^^^ + +error: unused import: `self::Crewman::*` + --> $DIR/issue-46209-private-enum-variant-reexport.rs:13:13 + | LL | pub use self::Crewman::*; | ^^^^^^^^^^^^^^^^ -error: aborting due to 5 previous errors +error: aborting due to 9 previous errors For more information about this error, try `rustc --explain E0364`. diff --git a/tests/ui/privacy/private-variant-reexport.rs b/tests/ui/privacy/private-variant-reexport.rs index 6882844602286..b59243af62067 100644 --- a/tests/ui/privacy/private-variant-reexport.rs +++ b/tests/ui/privacy/private-variant-reexport.rs @@ -12,7 +12,9 @@ mod m3 { #[deny(unused_imports)] mod m4 { - pub use ::E::*; //~ ERROR glob import doesn't reexport anything + pub use ::E::*; + //~^ ERROR glob import doesn't reexport anything + //~| ERROR unused import: `::E::*` } enum E { V } diff --git a/tests/ui/privacy/private-variant-reexport.stderr b/tests/ui/privacy/private-variant-reexport.stderr index 78771ee30d314..2f041934a8171 100644 --- a/tests/ui/privacy/private-variant-reexport.stderr +++ b/tests/ui/privacy/private-variant-reexport.stderr @@ -42,7 +42,13 @@ note: the lint level is defined here LL | #[deny(unused_imports)] | ^^^^^^^^^^^^^^ -error: aborting due to 4 previous errors +error: unused import: `::E::*` + --> $DIR/private-variant-reexport.rs:15:13 + | +LL | pub use ::E::*; + | ^^^^^^ + +error: aborting due to 5 previous errors Some errors have detailed explanations: E0364, E0365. For more information about an error, try `rustc --explain E0364`. From 6713ae9d4262976aed77083b322b981c12d6a432 Mon Sep 17 00:00:00 2001 From: Ayush Singh Date: Mon, 2 Oct 2023 17:00:09 +0530 Subject: [PATCH 8/8] Implement args for UEFI - Uses `EFI_LOADED_IMAGE_PROTOCOL` - verify that cli args are valid UTF-16 - Update Docs Signed-off-by: Ayush Singh --- library/std/src/sys/uefi/args.rs | 158 ++++++++++++++++++ library/std/src/sys/uefi/helpers.rs | 7 + library/std/src/sys/uefi/mod.rs | 1 - .../src/platform-support/unknown-uefi.md | 2 + 4 files changed, 167 insertions(+), 1 deletion(-) create mode 100644 library/std/src/sys/uefi/args.rs diff --git a/library/std/src/sys/uefi/args.rs b/library/std/src/sys/uefi/args.rs new file mode 100644 index 0000000000000..4ff7be748e90b --- /dev/null +++ b/library/std/src/sys/uefi/args.rs @@ -0,0 +1,158 @@ +use r_efi::protocols::loaded_image; + +use crate::env::current_exe; +use crate::ffi::OsString; +use crate::fmt; +use crate::iter::Iterator; +use crate::mem::size_of; +use crate::sys::uefi::helpers; +use crate::vec; + +pub struct Args { + parsed_args_list: vec::IntoIter, +} + +pub fn args() -> Args { + let lazy_current_exe = || Vec::from([current_exe().map(Into::into).unwrap_or_default()]); + + // Each loaded image has an image handle that supports `EFI_LOADED_IMAGE_PROTOCOL`. Thus, this + // will never fail. + let protocol = + helpers::image_handle_protocol::(loaded_image::PROTOCOL_GUID) + .unwrap(); + + let lp_size = unsafe { (*protocol.as_ptr()).load_options_size } as usize; + // Break if we are sure that it cannot be UTF-16 + if lp_size < size_of::() || lp_size % size_of::() != 0 { + return Args { parsed_args_list: lazy_current_exe().into_iter() }; + } + let lp_size = lp_size / size_of::(); + + let lp_cmd_line = unsafe { (*protocol.as_ptr()).load_options as *const u16 }; + if !lp_cmd_line.is_aligned() { + return Args { parsed_args_list: lazy_current_exe().into_iter() }; + } + let lp_cmd_line = unsafe { crate::slice::from_raw_parts(lp_cmd_line, lp_size) }; + + Args { + parsed_args_list: parse_lp_cmd_line(lp_cmd_line) + .unwrap_or_else(lazy_current_exe) + .into_iter(), + } +} + +impl fmt::Debug for Args { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + self.parsed_args_list.as_slice().fmt(f) + } +} + +impl Iterator for Args { + type Item = OsString; + + fn next(&mut self) -> Option { + self.parsed_args_list.next() + } + + fn size_hint(&self) -> (usize, Option) { + self.parsed_args_list.size_hint() + } +} + +impl ExactSizeIterator for Args { + fn len(&self) -> usize { + self.parsed_args_list.len() + } +} + +impl DoubleEndedIterator for Args { + fn next_back(&mut self) -> Option { + self.parsed_args_list.next_back() + } +} + +/// Implements the UEFI command-line argument parsing algorithm. +/// +/// This implementation is based on what is defined in Section 3.4 of +/// [UEFI Shell Specification](https://uefi.org/sites/default/files/resources/UEFI_Shell_Spec_2_0.pdf) +/// +/// Return None in the following cases: +/// - Invalid UTF-16 (unpaired surrogate) +/// - Empty/improper arguments +fn parse_lp_cmd_line(code_units: &[u16]) -> Option> { + const QUOTE: char = '"'; + const SPACE: char = ' '; + const CARET: char = '^'; + const NULL: char = '\0'; + + let mut ret_val = Vec::new(); + let mut code_units_iter = char::decode_utf16(code_units.iter().cloned()).peekable(); + + // The executable name at the beginning is special. + let mut in_quotes = false; + let mut cur = String::new(); + while let Some(w) = code_units_iter.next() { + let w = w.ok()?; + match w { + // break on NULL + NULL => break, + // A quote mark always toggles `in_quotes` no matter what because + // there are no escape characters when parsing the executable name. + QUOTE => in_quotes = !in_quotes, + // If not `in_quotes` then whitespace ends argv[0]. + SPACE if !in_quotes => break, + // In all other cases the code unit is taken literally. + _ => cur.push(w), + } + } + + // If exe name is missing, the cli args are invalid + if cur.is_empty() { + return None; + } + + ret_val.push(OsString::from(cur)); + // Skip whitespace. + while code_units_iter.next_if_eq(&Ok(SPACE)).is_some() {} + + // Parse the arguments according to these rules: + // * All code units are taken literally except space, quote and caret. + // * When not `in_quotes`, space separate arguments. Consecutive spaces are + // treated as a single separator. + // * A space `in_quotes` is taken literally. + // * A quote toggles `in_quotes` mode unless it's escaped. An escaped quote is taken literally. + // * A quote can be escaped if preceded by caret. + // * A caret can be escaped if preceded by caret. + let mut cur = String::new(); + let mut in_quotes = false; + while let Some(w) = code_units_iter.next() { + let w = w.ok()?; + match w { + // break on NULL + NULL => break, + // If not `in_quotes`, a space or tab ends the argument. + SPACE if !in_quotes => { + ret_val.push(OsString::from(&cur[..])); + cur.truncate(0); + + // Skip whitespace. + while code_units_iter.next_if_eq(&Ok(SPACE)).is_some() {} + } + // Caret can escape quotes or carets + CARET if in_quotes => { + if let Some(x) = code_units_iter.next() { + cur.push(x.ok()?); + } + } + // If quote then flip `in_quotes` + QUOTE => in_quotes = !in_quotes, + // Everything else is always taken literally. + _ => cur.push(w), + } + } + // Push the final argument, if any. + if !cur.is_empty() || in_quotes { + ret_val.push(OsString::from(cur)); + } + Some(ret_val) +} diff --git a/library/std/src/sys/uefi/helpers.rs b/library/std/src/sys/uefi/helpers.rs index 126661bfc961c..9837cc89f2d39 100644 --- a/library/std/src/sys/uefi/helpers.rs +++ b/library/std/src/sys/uefi/helpers.rs @@ -139,3 +139,10 @@ pub(crate) unsafe fn close_event(evt: NonNull) -> io::Result if r.is_error() { Err(crate::io::Error::from_raw_os_error(r.as_usize())) } else { Ok(()) } } + +/// Get the Protocol for current system handle. +/// Note: Some protocols need to be manually freed. It is the callers responsibility to do so. +pub(crate) fn image_handle_protocol(protocol_guid: Guid) -> Option> { + let system_handle = uefi::env::try_image_handle()?; + open_protocol(system_handle, protocol_guid).ok() +} diff --git a/library/std/src/sys/uefi/mod.rs b/library/std/src/sys/uefi/mod.rs index 097396ae99396..4edc00e3ea022 100644 --- a/library/std/src/sys/uefi/mod.rs +++ b/library/std/src/sys/uefi/mod.rs @@ -13,7 +13,6 @@ //! [`OsString`]: crate::ffi::OsString pub mod alloc; -#[path = "../unsupported/args.rs"] pub mod args; #[path = "../unix/cmath.rs"] pub mod cmath; diff --git a/src/doc/rustc/src/platform-support/unknown-uefi.md b/src/doc/rustc/src/platform-support/unknown-uefi.md index 370939520dc0c..1230ea22bd99b 100644 --- a/src/doc/rustc/src/platform-support/unknown-uefi.md +++ b/src/doc/rustc/src/platform-support/unknown-uefi.md @@ -268,6 +268,8 @@ cargo build --target x86_64-unknown-uefi -Zbuild-std=std,panic_abort #### stdio - Uses `Simple Text Input Protocol` and `Simple Text Output Protocol`. - Note: UEFI uses CRLF for new line. This means Enter key is registered as CR instead of LF. +#### args +- Uses `EFI_LOADED_IMAGE_PROTOCOL->LoadOptions` ## Example: Hello World With std The following code features a valid UEFI application, including `stdio` and `alloc` (`OsString` and `Vec`):