mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-22 23:04:33 +00:00
Auto merge of #124910 - matthiaskrgr:rollup-lo1uvdn, r=matthiaskrgr
Rollup of 8 pull requests Successful merges: - #123344 (Remove braces when fixing a nested use tree into a single item) - #124587 (Generic `NonZero` post-stabilization changes.) - #124775 (crashes: add lastest batch of crash tests) - #124869 (Make sure we don't deny macro vars w keyword names) - #124876 (Simplify `use crate::rustc_foo::bar` occurrences.) - #124892 (Update cc crate to v1.0.97) - #124903 (Ignore empty RUSTC_WRAPPER in bootstrap) - #124909 (Reapply the part of #124548 that bors forgot) r? `@ghost` `@rustbot` modify labels: rollup
This commit is contained in:
commit
87293c9585
@ -479,9 +479,9 @@ version = "0.1.0"
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "cc"
|
name = "cc"
|
||||||
version = "1.0.92"
|
version = "1.0.97"
|
||||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||||
checksum = "2678b2e3449475e95b0aa6f9b506a28e61b3dc8996592b983695e8ebb58a8b41"
|
checksum = "099a5357d84c4c61eb35fc8eafa9a79a902c2f76911e5747ced4e032edd8d9b4"
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "cfg-if"
|
name = "cfg-if"
|
||||||
@ -2219,7 +2219,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||||||
checksum = "0c2a198fb6b0eada2a8df47933734e6d35d350665a33a3593d7164fa52c75c19"
|
checksum = "0c2a198fb6b0eada2a8df47933734e6d35d350665a33a3593d7164fa52c75c19"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"cfg-if",
|
"cfg-if",
|
||||||
"windows-targets 0.48.5",
|
"windows-targets 0.52.4",
|
||||||
]
|
]
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
|
@ -2,6 +2,7 @@ use std::borrow::{Borrow, Cow};
|
|||||||
use std::cmp;
|
use std::cmp;
|
||||||
use std::fmt::{self, Write};
|
use std::fmt::{self, Write};
|
||||||
use std::iter;
|
use std::iter;
|
||||||
|
use std::num::NonZero;
|
||||||
use std::ops::Bound;
|
use std::ops::Bound;
|
||||||
use std::ops::Deref;
|
use std::ops::Deref;
|
||||||
|
|
||||||
@ -10,8 +11,8 @@ use tracing::debug;
|
|||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
Abi, AbiAndPrefAlign, Align, FieldsShape, IndexSlice, IndexVec, Integer, LayoutS, Niche,
|
Abi, AbiAndPrefAlign, Align, FieldsShape, IndexSlice, IndexVec, Integer, LayoutS, Niche,
|
||||||
NonZeroUsize, Primitive, ReprOptions, Scalar, Size, StructKind, TagEncoding, TargetDataLayout,
|
Primitive, ReprOptions, Scalar, Size, StructKind, TagEncoding, TargetDataLayout, Variants,
|
||||||
Variants, WrappingRange,
|
WrappingRange,
|
||||||
};
|
};
|
||||||
|
|
||||||
// A variant is absent if it's uninhabited and only has ZST fields.
|
// A variant is absent if it's uninhabited and only has ZST fields.
|
||||||
@ -327,7 +328,7 @@ pub trait LayoutCalculator {
|
|||||||
|
|
||||||
Some(LayoutS {
|
Some(LayoutS {
|
||||||
variants: Variants::Single { index: VariantIdx::new(0) },
|
variants: Variants::Single { index: VariantIdx::new(0) },
|
||||||
fields: FieldsShape::Union(NonZeroUsize::new(only_variant.len())?),
|
fields: FieldsShape::Union(NonZero::new(only_variant.len())?),
|
||||||
abi,
|
abi,
|
||||||
largest_niche: None,
|
largest_niche: None,
|
||||||
align,
|
align,
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
#![cfg_attr(feature = "nightly", feature(rustdoc_internals))]
|
#![cfg_attr(feature = "nightly", feature(rustdoc_internals))]
|
||||||
|
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
use std::num::{NonZeroUsize, ParseIntError};
|
use std::num::{NonZero, ParseIntError};
|
||||||
use std::ops::{Add, AddAssign, Mul, RangeInclusive, Sub};
|
use std::ops::{Add, AddAssign, Mul, RangeInclusive, Sub};
|
||||||
use std::str::FromStr;
|
use std::str::FromStr;
|
||||||
|
|
||||||
@ -1149,7 +1149,7 @@ pub enum FieldsShape<FieldIdx: Idx> {
|
|||||||
Primitive,
|
Primitive,
|
||||||
|
|
||||||
/// All fields start at no offset. The `usize` is the field count.
|
/// All fields start at no offset. The `usize` is the field count.
|
||||||
Union(NonZeroUsize),
|
Union(NonZero<usize>),
|
||||||
|
|
||||||
/// Array/vector-like placement, with all fields of identical types.
|
/// Array/vector-like placement, with all fields of identical types.
|
||||||
Array { stride: Size, count: u64 },
|
Array { stride: Size, count: u64 },
|
||||||
|
@ -2164,7 +2164,7 @@ pub enum TyKind {
|
|||||||
MacCall(P<MacCall>),
|
MacCall(P<MacCall>),
|
||||||
/// Placeholder for a `va_list`.
|
/// Placeholder for a `va_list`.
|
||||||
CVarArgs,
|
CVarArgs,
|
||||||
/// Pattern types like `pattern_type!(u32 is 1..=)`, which is the same as `NonZeroU32`,
|
/// Pattern types like `pattern_type!(u32 is 1..=)`, which is the same as `NonZero<u32>`,
|
||||||
/// just as part of the type system.
|
/// just as part of the type system.
|
||||||
Pat(P<Ty>, P<Pat>),
|
Pat(P<Ty>, P<Pat>),
|
||||||
/// Sometimes we need a dummy value when no error has occurred.
|
/// Sometimes we need a dummy value when no error has occurred.
|
||||||
@ -2729,7 +2729,7 @@ pub enum UseTreeKind {
|
|||||||
/// `use prefix` or `use prefix as rename`
|
/// `use prefix` or `use prefix as rename`
|
||||||
Simple(Option<Ident>),
|
Simple(Option<Ident>),
|
||||||
/// `use prefix::{...}`
|
/// `use prefix::{...}`
|
||||||
Nested(ThinVec<(UseTree, NodeId)>),
|
Nested { items: ThinVec<(UseTree, NodeId)>, span: Span },
|
||||||
/// `use prefix::*`
|
/// `use prefix::*`
|
||||||
Glob,
|
Glob,
|
||||||
}
|
}
|
||||||
|
@ -441,7 +441,7 @@ fn noop_visit_use_tree<T: MutVisitor>(use_tree: &mut UseTree, vis: &mut T) {
|
|||||||
vis.visit_path(prefix);
|
vis.visit_path(prefix);
|
||||||
match kind {
|
match kind {
|
||||||
UseTreeKind::Simple(rename) => visit_opt(rename, |rename| vis.visit_ident(rename)),
|
UseTreeKind::Simple(rename) => visit_opt(rename, |rename| vis.visit_ident(rename)),
|
||||||
UseTreeKind::Nested(items) => {
|
UseTreeKind::Nested { items, .. } => {
|
||||||
for (tree, id) in items {
|
for (tree, id) in items {
|
||||||
vis.visit_use_tree(tree);
|
vis.visit_use_tree(tree);
|
||||||
vis.visit_id(id);
|
vis.visit_id(id);
|
||||||
|
@ -517,8 +517,8 @@ pub fn walk_use_tree<'a, V: Visitor<'a>>(
|
|||||||
visit_opt!(visitor, visit_ident, rename);
|
visit_opt!(visitor, visit_ident, rename);
|
||||||
}
|
}
|
||||||
UseTreeKind::Glob => {}
|
UseTreeKind::Glob => {}
|
||||||
UseTreeKind::Nested(ref use_trees) => {
|
UseTreeKind::Nested { ref items, .. } => {
|
||||||
for &(ref nested_tree, nested_id) in use_trees {
|
for &(ref nested_tree, nested_id) in items {
|
||||||
try_visit!(visitor.visit_use_tree(nested_tree, nested_id, true));
|
try_visit!(visitor.visit_use_tree(nested_tree, nested_id, true));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -135,8 +135,8 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
|
|
||||||
fn lower_item_id_use_tree(&mut self, tree: &UseTree, vec: &mut SmallVec<[hir::ItemId; 1]>) {
|
fn lower_item_id_use_tree(&mut self, tree: &UseTree, vec: &mut SmallVec<[hir::ItemId; 1]>) {
|
||||||
match &tree.kind {
|
match &tree.kind {
|
||||||
UseTreeKind::Nested(nested_vec) => {
|
UseTreeKind::Nested { items, .. } => {
|
||||||
for &(ref nested, id) in nested_vec {
|
for &(ref nested, id) in items {
|
||||||
vec.push(hir::ItemId {
|
vec.push(hir::ItemId {
|
||||||
owner_id: hir::OwnerId { def_id: self.local_def_id(id) },
|
owner_id: hir::OwnerId { def_id: self.local_def_id(id) },
|
||||||
});
|
});
|
||||||
@ -518,7 +518,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
|
|||||||
let path = self.lower_use_path(res, &path, ParamMode::Explicit);
|
let path = self.lower_use_path(res, &path, ParamMode::Explicit);
|
||||||
hir::ItemKind::Use(path, hir::UseKind::Glob)
|
hir::ItemKind::Use(path, hir::UseKind::Glob)
|
||||||
}
|
}
|
||||||
UseTreeKind::Nested(ref trees) => {
|
UseTreeKind::Nested { items: ref trees, .. } => {
|
||||||
// Nested imports are desugared into simple imports.
|
// Nested imports are desugared into simple imports.
|
||||||
// So, if we start with
|
// So, if we start with
|
||||||
//
|
//
|
||||||
|
@ -715,7 +715,7 @@ impl<'a> State<'a> {
|
|||||||
}
|
}
|
||||||
self.word("*");
|
self.word("*");
|
||||||
}
|
}
|
||||||
ast::UseTreeKind::Nested(items) => {
|
ast::UseTreeKind::Nested { items, .. } => {
|
||||||
if !tree.prefix.segments.is_empty() {
|
if !tree.prefix.segments.is_empty() {
|
||||||
self.print_path(&tree.prefix, false, 0);
|
self.print_path(&tree.prefix, false, 0);
|
||||||
self.word("::");
|
self.word("::");
|
||||||
@ -734,7 +734,7 @@ impl<'a> State<'a> {
|
|||||||
self.print_use_tree(&use_tree.0);
|
self.print_use_tree(&use_tree.0);
|
||||||
if !is_last {
|
if !is_last {
|
||||||
self.word(",");
|
self.word(",");
|
||||||
if let ast::UseTreeKind::Nested(_) = use_tree.0.kind {
|
if let ast::UseTreeKind::Nested { .. } = use_tree.0.kind {
|
||||||
self.hardbreak();
|
self.hardbreak();
|
||||||
} else {
|
} else {
|
||||||
self.space();
|
self.space();
|
||||||
|
@ -120,10 +120,13 @@ impl<'cx, 'a> Context<'cx, 'a> {
|
|||||||
thin_vec![self.cx.attr_nested_word(sym::allow, sym::unused_imports, self.span)],
|
thin_vec![self.cx.attr_nested_word(sym::allow, sym::unused_imports, self.span)],
|
||||||
ItemKind::Use(UseTree {
|
ItemKind::Use(UseTree {
|
||||||
prefix: self.cx.path(self.span, self.cx.std_path(&[sym::asserting])),
|
prefix: self.cx.path(self.span, self.cx.std_path(&[sym::asserting])),
|
||||||
kind: UseTreeKind::Nested(thin_vec![
|
kind: UseTreeKind::Nested {
|
||||||
nested_tree(self, sym::TryCaptureGeneric),
|
items: thin_vec![
|
||||||
nested_tree(self, sym::TryCapturePrintable),
|
nested_tree(self, sym::TryCaptureGeneric),
|
||||||
]),
|
nested_tree(self, sym::TryCapturePrintable),
|
||||||
|
],
|
||||||
|
span: self.span,
|
||||||
|
},
|
||||||
span: self.span,
|
span: self.span,
|
||||||
}),
|
}),
|
||||||
),
|
),
|
||||||
|
@ -1,10 +1,9 @@
|
|||||||
use crate::rustc_index::Idx;
|
|
||||||
use gccjit::{Location, RValue};
|
use gccjit::{Location, RValue};
|
||||||
use rustc_codegen_ssa::mir::debuginfo::{DebugScope, FunctionDebugContext, VariableKind};
|
use rustc_codegen_ssa::mir::debuginfo::{DebugScope, FunctionDebugContext, VariableKind};
|
||||||
use rustc_codegen_ssa::traits::{DebugInfoBuilderMethods, DebugInfoMethods};
|
use rustc_codegen_ssa::traits::{DebugInfoBuilderMethods, DebugInfoMethods};
|
||||||
use rustc_data_structures::sync::Lrc;
|
use rustc_data_structures::sync::Lrc;
|
||||||
use rustc_index::bit_set::BitSet;
|
use rustc_index::bit_set::BitSet;
|
||||||
use rustc_index::IndexVec;
|
use rustc_index::{Idx, IndexVec};
|
||||||
use rustc_middle::mir::{self, Body, SourceScope};
|
use rustc_middle::mir::{self, Body, SourceScope};
|
||||||
use rustc_middle::ty::{Instance, PolyExistentialTraitRef, Ty};
|
use rustc_middle::ty::{Instance, PolyExistentialTraitRef, Ty};
|
||||||
use rustc_session::config::DebugInfo;
|
use rustc_session::config::DebugInfo;
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use std::fmt::Write;
|
use std::fmt::Write;
|
||||||
|
|
||||||
use crate::rustc_codegen_ssa::traits::{BaseTypeMethods, DerivedTypeMethods, LayoutTypeMethods};
|
|
||||||
use gccjit::{Struct, Type};
|
use gccjit::{Struct, Type};
|
||||||
|
use rustc_codegen_ssa::traits::{BaseTypeMethods, DerivedTypeMethods, LayoutTypeMethods};
|
||||||
use rustc_middle::bug;
|
use rustc_middle::bug;
|
||||||
use rustc_middle::ty::layout::{LayoutOf, TyAndLayout};
|
use rustc_middle::ty::layout::{LayoutOf, TyAndLayout};
|
||||||
use rustc_middle::ty::print::with_no_trimmed_paths;
|
use rustc_middle::ty::print::with_no_trimmed_paths;
|
||||||
@ -205,7 +205,7 @@ impl<'tcx> LayoutGccExt<'tcx> for TyAndLayout<'tcx> {
|
|||||||
/// of that field's type - this is useful for taking the address of
|
/// of that field's type - this is useful for taking the address of
|
||||||
/// that field and ensuring the struct has the right alignment.
|
/// that field and ensuring the struct has the right alignment.
|
||||||
fn gcc_type<'gcc>(&self, cx: &CodegenCx<'gcc, 'tcx>) -> Type<'gcc> {
|
fn gcc_type<'gcc>(&self, cx: &CodegenCx<'gcc, 'tcx>) -> Type<'gcc> {
|
||||||
use crate::rustc_middle::ty::layout::FnAbiOf;
|
use rustc_middle::ty::layout::FnAbiOf;
|
||||||
// This must produce the same result for `repr(transparent)` wrappers as for the inner type!
|
// This must produce the same result for `repr(transparent)` wrappers as for the inner type!
|
||||||
// In other words, this should generally not look at the type at all, but only at the
|
// In other words, this should generally not look at the type at all, but only at the
|
||||||
// layout.
|
// layout.
|
||||||
|
@ -7,7 +7,7 @@ edition = "2021"
|
|||||||
# tidy-alphabetical-start
|
# tidy-alphabetical-start
|
||||||
ar_archive_writer = "0.2.0"
|
ar_archive_writer = "0.2.0"
|
||||||
bitflags = "2.4.1"
|
bitflags = "2.4.1"
|
||||||
cc = "1.0.90"
|
cc = "1.0.97"
|
||||||
itertools = "0.12"
|
itertools = "0.12"
|
||||||
jobserver = "0.1.28"
|
jobserver = "0.1.28"
|
||||||
pathdiff = "0.2.0"
|
pathdiff = "0.2.0"
|
||||||
|
@ -1194,8 +1194,8 @@ impl InvocationCollectorNode for P<ast::Item> {
|
|||||||
match &ut.kind {
|
match &ut.kind {
|
||||||
ast::UseTreeKind::Glob => {}
|
ast::UseTreeKind::Glob => {}
|
||||||
ast::UseTreeKind::Simple(_) => idents.push(ut.ident()),
|
ast::UseTreeKind::Simple(_) => idents.push(ut.ident()),
|
||||||
ast::UseTreeKind::Nested(nested) => {
|
ast::UseTreeKind::Nested { items, .. } => {
|
||||||
for (ut, _) in nested {
|
for (ut, _) in items {
|
||||||
collect_use_tree_leaves(ut, idents);
|
collect_use_tree_leaves(ut, idents);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,9 +1,8 @@
|
|||||||
//! A utility module to inspect currently ambiguous obligations in the current context.
|
//! A utility module to inspect currently ambiguous obligations in the current context.
|
||||||
use crate::rustc_middle::ty::TypeVisitableExt;
|
|
||||||
use crate::FnCtxt;
|
use crate::FnCtxt;
|
||||||
use rustc_infer::traits::solve::Goal;
|
use rustc_infer::traits::solve::Goal;
|
||||||
use rustc_infer::traits::{self, ObligationCause};
|
use rustc_infer::traits::{self, ObligationCause};
|
||||||
use rustc_middle::ty::{self, Ty};
|
use rustc_middle::ty::{self, Ty, TypeVisitableExt};
|
||||||
use rustc_span::Span;
|
use rustc_span::Span;
|
||||||
use rustc_trait_selection::solve::inspect::ProofTreeInferCtxtExt;
|
use rustc_trait_selection::solve::inspect::ProofTreeInferCtxtExt;
|
||||||
use rustc_trait_selection::solve::inspect::{InspectConfig, InspectGoal, ProofTreeVisitor};
|
use rustc_trait_selection::solve::inspect::{InspectConfig, InspectGoal, ProofTreeVisitor};
|
||||||
|
@ -6,7 +6,6 @@ use crate::fn_ctxt::rustc_span::BytePos;
|
|||||||
use crate::hir::is_range_literal;
|
use crate::hir::is_range_literal;
|
||||||
use crate::method::probe;
|
use crate::method::probe;
|
||||||
use crate::method::probe::{IsSuggestion, Mode, ProbeScope};
|
use crate::method::probe::{IsSuggestion, Mode, ProbeScope};
|
||||||
use crate::rustc_middle::ty::Article;
|
|
||||||
use core::cmp::min;
|
use core::cmp::min;
|
||||||
use core::iter;
|
use core::iter;
|
||||||
use hir::def_id::LocalDefId;
|
use hir::def_id::LocalDefId;
|
||||||
@ -28,7 +27,7 @@ use rustc_middle::lint::in_external_macro;
|
|||||||
use rustc_middle::middle::stability::EvalResult;
|
use rustc_middle::middle::stability::EvalResult;
|
||||||
use rustc_middle::ty::print::with_no_trimmed_paths;
|
use rustc_middle::ty::print::with_no_trimmed_paths;
|
||||||
use rustc_middle::ty::{
|
use rustc_middle::ty::{
|
||||||
self, suggest_constraining_type_params, Binder, IsSuggestable, ToPredicate, Ty,
|
self, suggest_constraining_type_params, Article, Binder, IsSuggestable, ToPredicate, Ty,
|
||||||
TypeVisitableExt,
|
TypeVisitableExt,
|
||||||
};
|
};
|
||||||
use rustc_session::errors::ExprParenthesesNeeded;
|
use rustc_session::errors::ExprParenthesesNeeded;
|
||||||
@ -2227,7 +2226,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
) -> bool {
|
) -> bool {
|
||||||
let tcx = self.tcx;
|
let tcx = self.tcx;
|
||||||
let (adt, args, unwrap) = match expected.kind() {
|
let (adt, args, unwrap) = match expected.kind() {
|
||||||
// In case Option<NonZero*> is wanted, but * is provided, suggest calling new
|
// In case `Option<NonZero<T>>` is wanted, but `T` is provided, suggest calling `new`.
|
||||||
ty::Adt(adt, args) if tcx.is_diagnostic_item(sym::Option, adt.did()) => {
|
ty::Adt(adt, args) if tcx.is_diagnostic_item(sym::Option, adt.did()) => {
|
||||||
let nonzero_type = args.type_at(0); // Unwrap option type.
|
let nonzero_type = args.type_at(0); // Unwrap option type.
|
||||||
let ty::Adt(adt, args) = nonzero_type.kind() else {
|
let ty::Adt(adt, args) = nonzero_type.kind() else {
|
||||||
@ -2235,7 +2234,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
};
|
};
|
||||||
(adt, args, "")
|
(adt, args, "")
|
||||||
}
|
}
|
||||||
// In case `NonZero<*>` is wanted but `*` is provided, also add `.unwrap()` to satisfy types.
|
// In case `NonZero<T>` is wanted but `T` is provided, also add `.unwrap()` to satisfy types.
|
||||||
ty::Adt(adt, args) => (adt, args, ".unwrap()"),
|
ty::Adt(adt, args) => (adt, args, ".unwrap()"),
|
||||||
_ => return false,
|
_ => return false,
|
||||||
};
|
};
|
||||||
@ -2244,32 +2243,15 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// FIXME: This can be simplified once `NonZero<T>` is stable.
|
|
||||||
let coercable_types = [
|
|
||||||
("NonZeroU8", tcx.types.u8),
|
|
||||||
("NonZeroU16", tcx.types.u16),
|
|
||||||
("NonZeroU32", tcx.types.u32),
|
|
||||||
("NonZeroU64", tcx.types.u64),
|
|
||||||
("NonZeroU128", tcx.types.u128),
|
|
||||||
("NonZeroI8", tcx.types.i8),
|
|
||||||
("NonZeroI16", tcx.types.i16),
|
|
||||||
("NonZeroI32", tcx.types.i32),
|
|
||||||
("NonZeroI64", tcx.types.i64),
|
|
||||||
("NonZeroI128", tcx.types.i128),
|
|
||||||
];
|
|
||||||
|
|
||||||
let int_type = args.type_at(0);
|
let int_type = args.type_at(0);
|
||||||
|
if !self.can_coerce(expr_ty, int_type) {
|
||||||
let Some(nonzero_alias) = coercable_types.iter().find_map(|(nonzero_alias, t)| {
|
|
||||||
if *t == int_type && self.can_coerce(expr_ty, *t) { Some(nonzero_alias) } else { None }
|
|
||||||
}) else {
|
|
||||||
return false;
|
return false;
|
||||||
};
|
}
|
||||||
|
|
||||||
err.multipart_suggestion(
|
err.multipart_suggestion(
|
||||||
format!("consider calling `{nonzero_alias}::new`"),
|
format!("consider calling `{}::new`", sym::NonZero),
|
||||||
vec![
|
vec![
|
||||||
(expr.span.shrink_to_lo(), format!("{nonzero_alias}::new(")),
|
(expr.span.shrink_to_lo(), format!("{}::new(", sym::NonZero)),
|
||||||
(expr.span.shrink_to_hi(), format!("){unwrap}")),
|
(expr.span.shrink_to_hi(), format!("){unwrap}")),
|
||||||
],
|
],
|
||||||
Applicability::MaybeIncorrect,
|
Applicability::MaybeIncorrect,
|
||||||
|
@ -40,6 +40,7 @@ use crate::{
|
|||||||
},
|
},
|
||||||
EarlyContext, EarlyLintPass, LateContext, LateLintPass, Level, LintContext,
|
EarlyContext, EarlyLintPass, LateContext, LateLintPass, Level, LintContext,
|
||||||
};
|
};
|
||||||
|
use ast::token::TokenKind;
|
||||||
use rustc_ast::tokenstream::{TokenStream, TokenTree};
|
use rustc_ast::tokenstream::{TokenStream, TokenTree};
|
||||||
use rustc_ast::visit::{FnCtxt, FnKind};
|
use rustc_ast::visit::{FnCtxt, FnKind};
|
||||||
use rustc_ast::{self as ast, *};
|
use rustc_ast::{self as ast, *};
|
||||||
@ -1869,16 +1870,24 @@ struct UnderMacro(bool);
|
|||||||
|
|
||||||
impl KeywordIdents {
|
impl KeywordIdents {
|
||||||
fn check_tokens(&mut self, cx: &EarlyContext<'_>, tokens: &TokenStream) {
|
fn check_tokens(&mut self, cx: &EarlyContext<'_>, tokens: &TokenStream) {
|
||||||
|
// Check if the preceding token is `$`, because we want to allow `$async`, etc.
|
||||||
|
let mut prev_dollar = false;
|
||||||
for tt in tokens.trees() {
|
for tt in tokens.trees() {
|
||||||
match tt {
|
match tt {
|
||||||
// Only report non-raw idents.
|
// Only report non-raw idents.
|
||||||
TokenTree::Token(token, _) => {
|
TokenTree::Token(token, _) => {
|
||||||
if let Some((ident, token::IdentIsRaw::No)) = token.ident() {
|
if let Some((ident, token::IdentIsRaw::No)) = token.ident() {
|
||||||
self.check_ident_token(cx, UnderMacro(true), ident);
|
if !prev_dollar {
|
||||||
|
self.check_ident_token(cx, UnderMacro(true), ident);
|
||||||
|
}
|
||||||
|
} else if token.kind == TokenKind::Dollar {
|
||||||
|
prev_dollar = true;
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TokenTree::Delimited(.., tts) => self.check_tokens(cx, tts),
|
TokenTree::Delimited(.., tts) => self.check_tokens(cx, tts),
|
||||||
}
|
}
|
||||||
|
prev_dollar = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1501,7 +1501,7 @@ declare_lint_pass!(UnusedImportBraces => [UNUSED_IMPORT_BRACES]);
|
|||||||
|
|
||||||
impl UnusedImportBraces {
|
impl UnusedImportBraces {
|
||||||
fn check_use_tree(&self, cx: &EarlyContext<'_>, use_tree: &ast::UseTree, item: &ast::Item) {
|
fn check_use_tree(&self, cx: &EarlyContext<'_>, use_tree: &ast::UseTree, item: &ast::Item) {
|
||||||
if let ast::UseTreeKind::Nested(ref items) = use_tree.kind {
|
if let ast::UseTreeKind::Nested { ref items, .. } = use_tree.kind {
|
||||||
// Recursively check nested UseTrees
|
// Recursively check nested UseTrees
|
||||||
for (tree, _) in items {
|
for (tree, _) in items {
|
||||||
self.check_use_tree(cx, tree, item);
|
self.check_use_tree(cx, tree, item);
|
||||||
@ -1522,7 +1522,7 @@ impl UnusedImportBraces {
|
|||||||
rename.unwrap_or(orig_ident).name
|
rename.unwrap_or(orig_ident).name
|
||||||
}
|
}
|
||||||
ast::UseTreeKind::Glob => Symbol::intern("*"),
|
ast::UseTreeKind::Glob => Symbol::intern("*"),
|
||||||
ast::UseTreeKind::Nested(_) => return,
|
ast::UseTreeKind::Nested { .. } => return,
|
||||||
};
|
};
|
||||||
|
|
||||||
cx.emit_span_lint(
|
cx.emit_span_lint(
|
||||||
|
@ -10,5 +10,5 @@ libc = "0.2.73"
|
|||||||
|
|
||||||
[build-dependencies]
|
[build-dependencies]
|
||||||
# tidy-alphabetical-start
|
# tidy-alphabetical-start
|
||||||
cc = "1.0.90"
|
cc = "1.0.97"
|
||||||
# tidy-alphabetical-end
|
# tidy-alphabetical-end
|
||||||
|
@ -338,13 +338,14 @@ impl<'tcx> SizeSkeleton<'tcx> {
|
|||||||
pointee,
|
pointee,
|
||||||
|ty| match tcx.try_normalize_erasing_regions(param_env, ty) {
|
|ty| match tcx.try_normalize_erasing_regions(param_env, ty) {
|
||||||
Ok(ty) => ty,
|
Ok(ty) => ty,
|
||||||
Err(_e) => {
|
Err(e) => Ty::new_error_with_message(
|
||||||
if let Some(guar) = tcx.dcx().has_errors() {
|
tcx,
|
||||||
Ty::new_error(tcx, guar)
|
DUMMY_SP,
|
||||||
} else {
|
format!(
|
||||||
bug!("normalization failed, but no errors reported");
|
"normalization failed for {} but no errors reported",
|
||||||
}
|
e.get_type_for_failure()
|
||||||
}
|
),
|
||||||
|
),
|
||||||
},
|
},
|
||||||
|| {},
|
|| {},
|
||||||
);
|
);
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use crate::rustc_middle::ty::util::IntTypeExt;
|
|
||||||
use rustc_data_structures::fx::FxHashMap;
|
use rustc_data_structures::fx::FxHashMap;
|
||||||
use rustc_middle::mir::interpret::AllocId;
|
use rustc_middle::mir::interpret::AllocId;
|
||||||
use rustc_middle::mir::*;
|
use rustc_middle::mir::*;
|
||||||
|
use rustc_middle::ty::util::IntTypeExt;
|
||||||
use rustc_middle::ty::{self, AdtDef, ParamEnv, Ty, TyCtxt};
|
use rustc_middle::ty::{self, AdtDef, ParamEnv, Ty, TyCtxt};
|
||||||
use rustc_session::Session;
|
use rustc_session::Session;
|
||||||
use rustc_target::abi::{HasDataLayout, Size, TagEncoding, Variants};
|
use rustc_target::abi::{HasDataLayout, Size, TagEncoding, Variants};
|
||||||
|
@ -336,7 +336,7 @@ impl<'a> Parser<'a> {
|
|||||||
UseTreeKind::Glob => {
|
UseTreeKind::Glob => {
|
||||||
e.note("the wildcard token must be last on the path");
|
e.note("the wildcard token must be last on the path");
|
||||||
}
|
}
|
||||||
UseTreeKind::Nested(..) => {
|
UseTreeKind::Nested { .. } => {
|
||||||
e.note("glob-like brace syntax must be last on the path");
|
e.note("glob-like brace syntax must be last on the path");
|
||||||
}
|
}
|
||||||
_ => (),
|
_ => (),
|
||||||
@ -1056,7 +1056,11 @@ impl<'a> Parser<'a> {
|
|||||||
Ok(if self.eat(&token::BinOp(token::Star)) {
|
Ok(if self.eat(&token::BinOp(token::Star)) {
|
||||||
UseTreeKind::Glob
|
UseTreeKind::Glob
|
||||||
} else {
|
} else {
|
||||||
UseTreeKind::Nested(self.parse_use_tree_list()?)
|
let lo = self.token.span;
|
||||||
|
UseTreeKind::Nested {
|
||||||
|
items: self.parse_use_tree_list()?,
|
||||||
|
span: lo.to(self.prev_token.span),
|
||||||
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,8 +2,6 @@
|
|||||||
//! generate the actual methods on tcx which find and execute the provider,
|
//! generate the actual methods on tcx which find and execute the provider,
|
||||||
//! manage the caches, and so forth.
|
//! manage the caches, and so forth.
|
||||||
|
|
||||||
use crate::rustc_middle::dep_graph::DepContext;
|
|
||||||
use crate::rustc_middle::ty::TyEncoder;
|
|
||||||
use crate::QueryConfigRestored;
|
use crate::QueryConfigRestored;
|
||||||
use rustc_data_structures::stable_hasher::{Hash64, HashStable, StableHasher};
|
use rustc_data_structures::stable_hasher::{Hash64, HashStable, StableHasher};
|
||||||
use rustc_data_structures::sync::Lock;
|
use rustc_data_structures::sync::Lock;
|
||||||
@ -13,14 +11,14 @@ use rustc_errors::DiagInner;
|
|||||||
use rustc_index::Idx;
|
use rustc_index::Idx;
|
||||||
use rustc_middle::dep_graph::dep_kinds;
|
use rustc_middle::dep_graph::dep_kinds;
|
||||||
use rustc_middle::dep_graph::{
|
use rustc_middle::dep_graph::{
|
||||||
self, DepKind, DepKindStruct, DepNode, DepNodeIndex, SerializedDepNodeIndex,
|
self, DepContext, DepKind, DepKindStruct, DepNode, DepNodeIndex, SerializedDepNodeIndex,
|
||||||
};
|
};
|
||||||
use rustc_middle::query::on_disk_cache::AbsoluteBytePos;
|
use rustc_middle::query::on_disk_cache::AbsoluteBytePos;
|
||||||
use rustc_middle::query::on_disk_cache::{CacheDecoder, CacheEncoder, EncodedDepNodeIndex};
|
use rustc_middle::query::on_disk_cache::{CacheDecoder, CacheEncoder, EncodedDepNodeIndex};
|
||||||
use rustc_middle::query::Key;
|
use rustc_middle::query::Key;
|
||||||
use rustc_middle::ty::print::with_reduced_queries;
|
use rustc_middle::ty::print::with_reduced_queries;
|
||||||
use rustc_middle::ty::tls::{self, ImplicitCtxt};
|
use rustc_middle::ty::tls::{self, ImplicitCtxt};
|
||||||
use rustc_middle::ty::{self, TyCtxt};
|
use rustc_middle::ty::{self, TyCtxt, TyEncoder};
|
||||||
use rustc_query_system::dep_graph::{DepNodeParams, HasDepContext};
|
use rustc_query_system::dep_graph::{DepNodeParams, HasDepContext};
|
||||||
use rustc_query_system::ich::StableHashingContext;
|
use rustc_query_system::ich::StableHashingContext;
|
||||||
use rustc_query_system::query::{
|
use rustc_query_system::query::{
|
||||||
|
@ -560,7 +560,7 @@ impl<'a, 'b, 'tcx> BuildReducedGraphVisitor<'a, 'b, 'tcx> {
|
|||||||
|
|
||||||
self.add_import(prefix, kind, use_tree.span, item, root_span, item.id, vis);
|
self.add_import(prefix, kind, use_tree.span, item, root_span, item.id, vis);
|
||||||
}
|
}
|
||||||
ast::UseTreeKind::Nested(ref items) => {
|
ast::UseTreeKind::Nested { ref items, .. } => {
|
||||||
// Ensure there is at most one `self` in the list
|
// Ensure there is at most one `self` in the list
|
||||||
let self_spans = items
|
let self_spans = items
|
||||||
.iter()
|
.iter()
|
||||||
|
@ -128,7 +128,7 @@ impl<'a, 'b, 'tcx> UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
|||||||
self.unused_import(self.base_id).add(id);
|
self.unused_import(self.base_id).add(id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ast::UseTreeKind::Nested(ref items) => self.check_imports_as_underscore(items),
|
ast::UseTreeKind::Nested { ref items, .. } => self.check_imports_as_underscore(items),
|
||||||
_ => {}
|
_ => {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -254,7 +254,7 @@ impl<'a, 'b, 'tcx> Visitor<'a> for UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if let ast::UseTreeKind::Nested(ref items) = use_tree.kind {
|
if let ast::UseTreeKind::Nested { ref items, .. } = use_tree.kind {
|
||||||
if items.is_empty() {
|
if items.is_empty() {
|
||||||
self.unused_import(self.base_id).add(id);
|
self.unused_import(self.base_id).add(id);
|
||||||
}
|
}
|
||||||
@ -268,9 +268,8 @@ impl<'a, 'b, 'tcx> Visitor<'a> for UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
|||||||
|
|
||||||
enum UnusedSpanResult {
|
enum UnusedSpanResult {
|
||||||
Used,
|
Used,
|
||||||
FlatUnused(Span, Span),
|
Unused { spans: Vec<Span>, remove: Span },
|
||||||
NestedFullUnused(Vec<Span>, Span),
|
PartialUnused { spans: Vec<Span>, remove: Vec<Span> },
|
||||||
NestedPartialUnused(Vec<Span>, Vec<Span>),
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn calc_unused_spans(
|
fn calc_unused_spans(
|
||||||
@ -288,36 +287,33 @@ fn calc_unused_spans(
|
|||||||
match use_tree.kind {
|
match use_tree.kind {
|
||||||
ast::UseTreeKind::Simple(..) | ast::UseTreeKind::Glob => {
|
ast::UseTreeKind::Simple(..) | ast::UseTreeKind::Glob => {
|
||||||
if unused_import.unused.contains(&use_tree_id) {
|
if unused_import.unused.contains(&use_tree_id) {
|
||||||
UnusedSpanResult::FlatUnused(use_tree.span, full_span)
|
UnusedSpanResult::Unused { spans: vec![use_tree.span], remove: full_span }
|
||||||
} else {
|
} else {
|
||||||
UnusedSpanResult::Used
|
UnusedSpanResult::Used
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ast::UseTreeKind::Nested(ref nested) => {
|
ast::UseTreeKind::Nested { items: ref nested, span: tree_span } => {
|
||||||
if nested.is_empty() {
|
if nested.is_empty() {
|
||||||
return UnusedSpanResult::FlatUnused(use_tree.span, full_span);
|
return UnusedSpanResult::Unused { spans: vec![use_tree.span], remove: full_span };
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut unused_spans = Vec::new();
|
let mut unused_spans = Vec::new();
|
||||||
let mut to_remove = Vec::new();
|
let mut to_remove = Vec::new();
|
||||||
let mut all_nested_unused = true;
|
let mut used_childs = 0;
|
||||||
|
let mut contains_self = false;
|
||||||
let mut previous_unused = false;
|
let mut previous_unused = false;
|
||||||
for (pos, (use_tree, use_tree_id)) in nested.iter().enumerate() {
|
for (pos, (use_tree, use_tree_id)) in nested.iter().enumerate() {
|
||||||
let remove = match calc_unused_spans(unused_import, use_tree, *use_tree_id) {
|
let remove = match calc_unused_spans(unused_import, use_tree, *use_tree_id) {
|
||||||
UnusedSpanResult::Used => {
|
UnusedSpanResult::Used => {
|
||||||
all_nested_unused = false;
|
used_childs += 1;
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
UnusedSpanResult::FlatUnused(span, remove) => {
|
UnusedSpanResult::Unused { mut spans, remove } => {
|
||||||
unused_spans.push(span);
|
|
||||||
Some(remove)
|
|
||||||
}
|
|
||||||
UnusedSpanResult::NestedFullUnused(mut spans, remove) => {
|
|
||||||
unused_spans.append(&mut spans);
|
unused_spans.append(&mut spans);
|
||||||
Some(remove)
|
Some(remove)
|
||||||
}
|
}
|
||||||
UnusedSpanResult::NestedPartialUnused(mut spans, mut to_remove_extra) => {
|
UnusedSpanResult::PartialUnused { mut spans, remove: mut to_remove_extra } => {
|
||||||
all_nested_unused = false;
|
used_childs += 1;
|
||||||
unused_spans.append(&mut spans);
|
unused_spans.append(&mut spans);
|
||||||
to_remove.append(&mut to_remove_extra);
|
to_remove.append(&mut to_remove_extra);
|
||||||
None
|
None
|
||||||
@ -326,7 +322,7 @@ fn calc_unused_spans(
|
|||||||
if let Some(remove) = remove {
|
if let Some(remove) = remove {
|
||||||
let remove_span = if nested.len() == 1 {
|
let remove_span = if nested.len() == 1 {
|
||||||
remove
|
remove
|
||||||
} else if pos == nested.len() - 1 || !all_nested_unused {
|
} else if pos == nested.len() - 1 || used_childs > 0 {
|
||||||
// Delete everything from the end of the last import, to delete the
|
// Delete everything from the end of the last import, to delete the
|
||||||
// previous comma
|
// previous comma
|
||||||
nested[pos - 1].0.span.shrink_to_hi().to(use_tree.span)
|
nested[pos - 1].0.span.shrink_to_hi().to(use_tree.span)
|
||||||
@ -344,14 +340,38 @@ fn calc_unused_spans(
|
|||||||
to_remove.push(remove_span);
|
to_remove.push(remove_span);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
contains_self |= use_tree.prefix == kw::SelfLower
|
||||||
|
&& matches!(use_tree.kind, ast::UseTreeKind::Simple(None));
|
||||||
previous_unused = remove.is_some();
|
previous_unused = remove.is_some();
|
||||||
}
|
}
|
||||||
if unused_spans.is_empty() {
|
if unused_spans.is_empty() {
|
||||||
UnusedSpanResult::Used
|
UnusedSpanResult::Used
|
||||||
} else if all_nested_unused {
|
} else if used_childs == 0 {
|
||||||
UnusedSpanResult::NestedFullUnused(unused_spans, full_span)
|
UnusedSpanResult::Unused { spans: unused_spans, remove: full_span }
|
||||||
} else {
|
} else {
|
||||||
UnusedSpanResult::NestedPartialUnused(unused_spans, to_remove)
|
// If there is only one remaining child that is used, the braces around the use
|
||||||
|
// tree are not needed anymore. In that case, we determine the span of the left
|
||||||
|
// brace and the right brace, and tell rustfix to remove them as well.
|
||||||
|
//
|
||||||
|
// This means that `use a::{B, C};` will be turned into `use a::B;` rather than
|
||||||
|
// `use a::{B};`, removing a rustfmt roundtrip.
|
||||||
|
//
|
||||||
|
// Note that we cannot remove the braces if the only item inside the use tree is
|
||||||
|
// `self`: `use foo::{self};` is valid Rust syntax, while `use foo::self;` errors
|
||||||
|
// out. We also cannot turn `use foo::{self}` into `use foo`, as the former doesn't
|
||||||
|
// import types with the same name as the module.
|
||||||
|
if used_childs == 1 && !contains_self {
|
||||||
|
// Left brace, from the start of the nested group to the first item.
|
||||||
|
to_remove.push(
|
||||||
|
tree_span.shrink_to_lo().to(nested.first().unwrap().0.span.shrink_to_lo()),
|
||||||
|
);
|
||||||
|
// Right brace, from the end of the last item to the end of the nested group.
|
||||||
|
to_remove.push(
|
||||||
|
nested.last().unwrap().0.span.shrink_to_hi().to(tree_span.shrink_to_hi()),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
UnusedSpanResult::PartialUnused { spans: unused_spans, remove: to_remove }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -417,15 +437,11 @@ impl Resolver<'_, '_> {
|
|||||||
let mut fixes = Vec::new();
|
let mut fixes = Vec::new();
|
||||||
let spans = match calc_unused_spans(unused, &unused.use_tree, unused.use_tree_id) {
|
let spans = match calc_unused_spans(unused, &unused.use_tree, unused.use_tree_id) {
|
||||||
UnusedSpanResult::Used => continue,
|
UnusedSpanResult::Used => continue,
|
||||||
UnusedSpanResult::FlatUnused(span, remove) => {
|
UnusedSpanResult::Unused { spans, remove } => {
|
||||||
fixes.push((remove, String::new()));
|
|
||||||
vec![span]
|
|
||||||
}
|
|
||||||
UnusedSpanResult::NestedFullUnused(spans, remove) => {
|
|
||||||
fixes.push((remove, String::new()));
|
fixes.push((remove, String::new()));
|
||||||
spans
|
spans
|
||||||
}
|
}
|
||||||
UnusedSpanResult::NestedPartialUnused(spans, remove) => {
|
UnusedSpanResult::PartialUnused { spans, remove } => {
|
||||||
for fix in &remove {
|
for fix in &remove {
|
||||||
fixes.push((*fix, String::new()));
|
fixes.push((*fix, String::new()));
|
||||||
}
|
}
|
||||||
|
@ -2347,8 +2347,8 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
|
|||||||
None => {}
|
None => {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if let UseTreeKind::Nested(use_trees) = &use_tree.kind {
|
} else if let UseTreeKind::Nested { items, .. } = &use_tree.kind {
|
||||||
for (use_tree, _) in use_trees {
|
for (use_tree, _) in items {
|
||||||
self.future_proof_import(use_tree);
|
self.future_proof_import(use_tree);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2525,7 +2525,7 @@ impl<'a: 'ast, 'b, 'ast, 'tcx> LateResolutionVisitor<'a, 'b, 'ast, 'tcx> {
|
|||||||
ItemKind::Use(ref use_tree) => {
|
ItemKind::Use(ref use_tree) => {
|
||||||
let maybe_exported = match use_tree.kind {
|
let maybe_exported = match use_tree.kind {
|
||||||
UseTreeKind::Simple(_) | UseTreeKind::Glob => MaybeExported::Ok(item.id),
|
UseTreeKind::Simple(_) | UseTreeKind::Glob => MaybeExported::Ok(item.id),
|
||||||
UseTreeKind::Nested(_) => MaybeExported::NestedUse(&item.vis),
|
UseTreeKind::Nested { .. } => MaybeExported::NestedUse(&item.vis),
|
||||||
};
|
};
|
||||||
self.resolve_doc_links(&item.attrs, maybe_exported);
|
self.resolve_doc_links(&item.attrs, maybe_exported);
|
||||||
|
|
||||||
|
@ -6,7 +6,7 @@ use crate::ty::{Align, IndexedVal, Ty, VariantIdx};
|
|||||||
use crate::Error;
|
use crate::Error;
|
||||||
use crate::Opaque;
|
use crate::Opaque;
|
||||||
use std::fmt::{self, Debug};
|
use std::fmt::{self, Debug};
|
||||||
use std::num::NonZeroUsize;
|
use std::num::NonZero;
|
||||||
use std::ops::RangeInclusive;
|
use std::ops::RangeInclusive;
|
||||||
|
|
||||||
/// A function ABI definition.
|
/// A function ABI definition.
|
||||||
@ -133,7 +133,7 @@ pub enum FieldsShape {
|
|||||||
Primitive,
|
Primitive,
|
||||||
|
|
||||||
/// All fields start at no offset. The `usize` is the field count.
|
/// All fields start at no offset. The `usize` is the field count.
|
||||||
Union(NonZeroUsize),
|
Union(NonZero<usize>),
|
||||||
|
|
||||||
/// Array/vector-like placement, with all fields of identical types.
|
/// Array/vector-like placement, with all fields of identical types.
|
||||||
Array { stride: Size, count: u64 },
|
Array { stride: Size, count: u64 },
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
intrinsics,
|
intrinsics,
|
||||||
iter::{from_fn, TrustedLen, TrustedRandomAccess},
|
iter::{from_fn, TrustedLen, TrustedRandomAccess},
|
||||||
num::NonZeroUsize,
|
num::NonZero,
|
||||||
ops::{Range, Try},
|
ops::{Range, Try},
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -42,10 +42,10 @@ impl<I> StepBy<I> {
|
|||||||
/// The `step` that was originally passed to `Iterator::step_by(step)`,
|
/// The `step` that was originally passed to `Iterator::step_by(step)`,
|
||||||
/// aka `self.step_minus_one + 1`.
|
/// aka `self.step_minus_one + 1`.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn original_step(&self) -> NonZeroUsize {
|
fn original_step(&self) -> NonZero<usize> {
|
||||||
// SAFETY: By type invariant, `step_minus_one` cannot be `MAX`, which
|
// SAFETY: By type invariant, `step_minus_one` cannot be `MAX`, which
|
||||||
// means the addition cannot overflow and the result cannot be zero.
|
// means the addition cannot overflow and the result cannot be zero.
|
||||||
unsafe { NonZeroUsize::new_unchecked(intrinsics::unchecked_add(self.step_minus_one, 1)) }
|
unsafe { NonZero::new_unchecked(intrinsics::unchecked_add(self.step_minus_one, 1)) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -231,12 +231,12 @@ unsafe impl<I: Iterator> StepByImpl<I> for StepBy<I> {
|
|||||||
#[inline]
|
#[inline]
|
||||||
default fn spec_size_hint(&self) -> (usize, Option<usize>) {
|
default fn spec_size_hint(&self) -> (usize, Option<usize>) {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn first_size(step: NonZeroUsize) -> impl Fn(usize) -> usize {
|
fn first_size(step: NonZero<usize>) -> impl Fn(usize) -> usize {
|
||||||
move |n| if n == 0 { 0 } else { 1 + (n - 1) / step }
|
move |n| if n == 0 { 0 } else { 1 + (n - 1) / step }
|
||||||
}
|
}
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
fn other_size(step: NonZeroUsize) -> impl Fn(usize) -> usize {
|
fn other_size(step: NonZero<usize>) -> impl Fn(usize) -> usize {
|
||||||
move |n| n / step
|
move |n| n / step
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -453,8 +453,7 @@ macro_rules! nonzero_integer {
|
|||||||
#[$stability:meta]
|
#[$stability:meta]
|
||||||
Self = $Ty:ident,
|
Self = $Ty:ident,
|
||||||
Primitive = $signedness:ident $Int:ident,
|
Primitive = $signedness:ident $Int:ident,
|
||||||
$(UnsignedNonZero = $UnsignedNonZero:ident,)?
|
UnsignedPrimitive = $Uint:ty,
|
||||||
UnsignedPrimitive = $UnsignedPrimitive:ty,
|
|
||||||
|
|
||||||
// Used in doc comments.
|
// Used in doc comments.
|
||||||
leading_zeros_test = $leading_zeros_test:expr,
|
leading_zeros_test = $leading_zeros_test:expr,
|
||||||
@ -492,7 +491,7 @@ macro_rules! nonzero_integer {
|
|||||||
#[$stability]
|
#[$stability]
|
||||||
pub type $Ty = NonZero<$Int>;
|
pub type $Ty = NonZero<$Int>;
|
||||||
|
|
||||||
impl $Ty {
|
impl NonZero<$Int> {
|
||||||
/// The size of this non-zero integer type in bits.
|
/// The size of this non-zero integer type in bits.
|
||||||
///
|
///
|
||||||
#[doc = concat!("This value is equal to [`", stringify!($Int), "::BITS`].")]
|
#[doc = concat!("This value is equal to [`", stringify!($Int), "::BITS`].")]
|
||||||
@ -500,9 +499,9 @@ macro_rules! nonzero_integer {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
///
|
/// #
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::BITS, ", stringify!($Int), "::BITS);")]
|
#[doc = concat!("assert_eq!(NonZero::<", stringify!($Int), ">::BITS, ", stringify!($Int), "::BITS);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "nonzero_bits", since = "1.67.0")]
|
#[stable(feature = "nonzero_bits", since = "1.67.0")]
|
||||||
pub const BITS: u32 = <$Int>::BITS;
|
pub const BITS: u32 = <$Int>::BITS;
|
||||||
@ -516,7 +515,9 @@ macro_rules! nonzero_integer {
|
|||||||
/// Basic usage:
|
/// Basic usage:
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("let n = std::num::", stringify!($Ty), "::new(", $leading_zeros_test, ").unwrap();")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
|
#[doc = concat!("let n = NonZero::<", stringify!($Int), ">::new(", $leading_zeros_test, ").unwrap();")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(n.leading_zeros(), 0);
|
/// assert_eq!(n.leading_zeros(), 0);
|
||||||
/// ```
|
/// ```
|
||||||
@ -528,7 +529,7 @@ macro_rules! nonzero_integer {
|
|||||||
pub const fn leading_zeros(self) -> u32 {
|
pub const fn leading_zeros(self) -> u32 {
|
||||||
// SAFETY: since `self` cannot be zero, it is safe to call `ctlz_nonzero`.
|
// SAFETY: since `self` cannot be zero, it is safe to call `ctlz_nonzero`.
|
||||||
unsafe {
|
unsafe {
|
||||||
intrinsics::ctlz_nonzero(self.get() as $UnsignedPrimitive)
|
intrinsics::ctlz_nonzero(self.get() as $Uint)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -542,7 +543,9 @@ macro_rules! nonzero_integer {
|
|||||||
/// Basic usage:
|
/// Basic usage:
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("let n = std::num::", stringify!($Ty), "::new(0b0101000).unwrap();")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
|
#[doc = concat!("let n = NonZero::<", stringify!($Int), ">::new(0b0101000).unwrap();")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(n.trailing_zeros(), 3);
|
/// assert_eq!(n.trailing_zeros(), 3);
|
||||||
/// ```
|
/// ```
|
||||||
@ -554,7 +557,7 @@ macro_rules! nonzero_integer {
|
|||||||
pub const fn trailing_zeros(self) -> u32 {
|
pub const fn trailing_zeros(self) -> u32 {
|
||||||
// SAFETY: since `self` cannot be zero, it is safe to call `cttz_nonzero`.
|
// SAFETY: since `self` cannot be zero, it is safe to call `cttz_nonzero`.
|
||||||
unsafe {
|
unsafe {
|
||||||
intrinsics::cttz_nonzero(self.get() as $UnsignedPrimitive)
|
intrinsics::cttz_nonzero(self.get() as $Uint)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -567,10 +570,10 @@ macro_rules! nonzero_integer {
|
|||||||
/// ```
|
/// ```
|
||||||
/// #![feature(non_zero_count_ones)]
|
/// #![feature(non_zero_count_ones)]
|
||||||
///
|
///
|
||||||
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
/// # use std::num::*;
|
|
||||||
/// #
|
|
||||||
#[doc = concat!("let a = NonZero::<", stringify!($Int), ">::new(0b100_0000)?;")]
|
#[doc = concat!("let a = NonZero::<", stringify!($Int), ">::new(0b100_0000)?;")]
|
||||||
#[doc = concat!("let b = NonZero::<", stringify!($Int), ">::new(0b100_0011)?;")]
|
#[doc = concat!("let b = NonZero::<", stringify!($Int), ">::new(0b100_0011)?;")]
|
||||||
///
|
///
|
||||||
@ -597,8 +600,7 @@ macro_rules! nonzero_integer {
|
|||||||
nonzero_integer_signedness_dependent_methods! {
|
nonzero_integer_signedness_dependent_methods! {
|
||||||
Self = $Ty,
|
Self = $Ty,
|
||||||
Primitive = $signedness $Int,
|
Primitive = $signedness $Int,
|
||||||
$(UnsignedNonZero = $UnsignedNonZero,)?
|
UnsignedPrimitive = $Uint,
|
||||||
UnsignedPrimitive = $UnsignedPrimitive,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Multiplies two non-zero integers together.
|
/// Multiplies two non-zero integers together.
|
||||||
@ -608,13 +610,13 @@ macro_rules! nonzero_integer {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
|
#[doc = concat!("let four = NonZero::new(4", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(Some(four), two.checked_mul(two));
|
/// assert_eq!(Some(four), two.checked_mul(two));
|
||||||
/// assert_eq!(None, max.checked_mul(two));
|
/// assert_eq!(None, max.checked_mul(two));
|
||||||
@ -642,18 +644,18 @@ macro_rules! nonzero_integer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Multiplies two non-zero integers together.
|
/// Multiplies two non-zero integers together.
|
||||||
#[doc = concat!("Return [`", stringify!($Ty), "::MAX`] on overflow.")]
|
#[doc = concat!("Return [`NonZero::<", stringify!($Int), ">::MAX`] on overflow.")]
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
|
#[doc = concat!("let four = NonZero::new(4", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(four, two.saturating_mul(two));
|
/// assert_eq!(four, two.saturating_mul(two));
|
||||||
/// assert_eq!(max, four.saturating_mul(max));
|
/// assert_eq!(max, four.saturating_mul(max));
|
||||||
@ -698,11 +700,12 @@ macro_rules! nonzero_integer {
|
|||||||
/// ```
|
/// ```
|
||||||
/// #![feature(nonzero_ops)]
|
/// #![feature(nonzero_ops)]
|
||||||
///
|
///
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
|
#[doc = concat!("let four = NonZero::new(4", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(four, unsafe { two.unchecked_mul(two) });
|
/// assert_eq!(four, unsafe { two.unchecked_mul(two) });
|
||||||
/// # Some(())
|
/// # Some(())
|
||||||
@ -724,13 +727,13 @@ macro_rules! nonzero_integer {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
|
#[doc = concat!("let three = NonZero::new(3", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let twenty_seven = ", stringify!($Ty), "::new(27)?;")]
|
#[doc = concat!("let twenty_seven = NonZero::new(27", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let half_max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let half_max = NonZero::new(", stringify!($Int), "::MAX / 2)?;")]
|
||||||
stringify!($Int), "::MAX / 2)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(Some(twenty_seven), three.checked_pow(3));
|
/// assert_eq!(Some(twenty_seven), three.checked_pow(3));
|
||||||
/// assert_eq!(None, half_max.checked_pow(3));
|
/// assert_eq!(None, half_max.checked_pow(3));
|
||||||
@ -761,24 +764,24 @@ macro_rules! nonzero_integer {
|
|||||||
#[doc = sign_dependent_expr!{
|
#[doc = sign_dependent_expr!{
|
||||||
$signedness ?
|
$signedness ?
|
||||||
if signed {
|
if signed {
|
||||||
concat!("Return [`", stringify!($Ty), "::MIN`] ",
|
concat!("Return [`NonZero::<", stringify!($Int), ">::MIN`] ",
|
||||||
"or [`", stringify!($Ty), "::MAX`] on overflow.")
|
"or [`NonZero::<", stringify!($Int), ">::MAX`] on overflow.")
|
||||||
}
|
}
|
||||||
if unsigned {
|
if unsigned {
|
||||||
concat!("Return [`", stringify!($Ty), "::MAX`] on overflow.")
|
concat!("Return [`NonZero::<", stringify!($Int), ">::MAX`] on overflow.")
|
||||||
}
|
}
|
||||||
}]
|
}]
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
|
#[doc = concat!("let three = NonZero::new(3", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let twenty_seven = ", stringify!($Ty), "::new(27)?;")]
|
#[doc = concat!("let twenty_seven = NonZero::new(27", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(twenty_seven, three.saturating_pow(3));
|
/// assert_eq!(twenty_seven, three.saturating_pow(3));
|
||||||
/// assert_eq!(max, max.saturating_pow(3));
|
/// assert_eq!(max, max.saturating_pow(3));
|
||||||
@ -804,7 +807,7 @@ macro_rules! nonzero_integer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[stable(feature = "nonzero_parse", since = "1.35.0")]
|
#[stable(feature = "nonzero_parse", since = "1.35.0")]
|
||||||
impl FromStr for $Ty {
|
impl FromStr for NonZero<$Int> {
|
||||||
type Err = ParseIntError;
|
type Err = ParseIntError;
|
||||||
fn from_str(src: &str) -> Result<Self, Self::Err> {
|
fn from_str(src: &str) -> Result<Self, Self::Err> {
|
||||||
Self::new(<$Int>::from_str_radix(src, 10)?)
|
Self::new(<$Int>::from_str_radix(src, 10)?)
|
||||||
@ -842,56 +845,55 @@ macro_rules! nonzero_integer_signedness_dependent_impls {
|
|||||||
// Impls for unsigned nonzero types only.
|
// Impls for unsigned nonzero types only.
|
||||||
($Ty:ident unsigned $Int:ty) => {
|
($Ty:ident unsigned $Int:ty) => {
|
||||||
#[stable(feature = "nonzero_div", since = "1.51.0")]
|
#[stable(feature = "nonzero_div", since = "1.51.0")]
|
||||||
impl Div<$Ty> for $Int {
|
impl Div<NonZero<$Int>> for $Int {
|
||||||
type Output = $Int;
|
type Output = $Int;
|
||||||
|
|
||||||
/// This operation rounds towards zero,
|
/// This operation rounds towards zero, truncating any fractional
|
||||||
/// truncating any fractional part of the exact result, and cannot panic.
|
/// part of the exact result, and cannot panic.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn div(self, other: $Ty) -> $Int {
|
fn div(self, other: NonZero<$Int>) -> $Int {
|
||||||
// SAFETY: div by zero is checked because `other` is a nonzero,
|
// SAFETY: Division by zero is checked because `other` is non-zero,
|
||||||
// and MIN/-1 is checked because `self` is an unsigned int.
|
// and MIN/-1 is checked because `self` is an unsigned int.
|
||||||
unsafe { intrinsics::unchecked_div(self, other.get()) }
|
unsafe { intrinsics::unchecked_div(self, other.get()) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[stable(feature = "nonzero_div_assign", since = "1.79.0")]
|
#[stable(feature = "nonzero_div_assign", since = "1.79.0")]
|
||||||
impl DivAssign<$Ty> for $Int {
|
impl DivAssign<NonZero<$Int>> for $Int {
|
||||||
/// This operation rounds towards zero,
|
/// This operation rounds towards zero, truncating any fractional
|
||||||
/// truncating any fractional part of the exact result, and cannot panic.
|
/// part of the exact result, and cannot panic.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn div_assign(&mut self, other: $Ty) {
|
fn div_assign(&mut self, other: NonZero<$Int>) {
|
||||||
*self = *self / other;
|
*self = *self / other;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[stable(feature = "nonzero_div", since = "1.51.0")]
|
#[stable(feature = "nonzero_div", since = "1.51.0")]
|
||||||
impl Rem<$Ty> for $Int {
|
impl Rem<NonZero<$Int>> for $Int {
|
||||||
type Output = $Int;
|
type Output = $Int;
|
||||||
|
|
||||||
/// This operation satisfies `n % d == n - (n / d) * d`, and cannot panic.
|
/// This operation satisfies `n % d == n - (n / d) * d`, and cannot panic.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn rem(self, other: $Ty) -> $Int {
|
fn rem(self, other: NonZero<$Int>) -> $Int {
|
||||||
// SAFETY: rem by zero is checked because `other` is a nonzero,
|
// SAFETY: Remainder by zero is checked because `other` is non-zero,
|
||||||
// and MIN/-1 is checked because `self` is an unsigned int.
|
// and MIN/-1 is checked because `self` is an unsigned int.
|
||||||
unsafe { intrinsics::unchecked_rem(self, other.get()) }
|
unsafe { intrinsics::unchecked_rem(self, other.get()) }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[stable(feature = "nonzero_div_assign", since = "1.79.0")]
|
#[stable(feature = "nonzero_div_assign", since = "1.79.0")]
|
||||||
impl RemAssign<$Ty> for $Int {
|
impl RemAssign<NonZero<$Int>> for $Int {
|
||||||
/// This operation satisfies `n % d == n - (n / d) * d`, and cannot panic.
|
/// This operation satisfies `n % d == n - (n / d) * d`, and cannot panic.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn rem_assign(&mut self, other: $Ty) {
|
fn rem_assign(&mut self, other: NonZero<$Int>) {
|
||||||
*self = *self % other;
|
*self = *self % other;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Impls for signed nonzero types only.
|
// Impls for signed nonzero types only.
|
||||||
($Ty:ident signed $Int:ty) => {
|
($Ty:ident signed $Int:ty) => {
|
||||||
#[stable(feature = "signed_nonzero_neg", since = "1.71.0")]
|
#[stable(feature = "signed_nonzero_neg", since = "1.71.0")]
|
||||||
impl Neg for $Ty {
|
impl Neg for NonZero<$Int> {
|
||||||
type Output = Self;
|
type Output = Self;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
@ -901,7 +903,7 @@ macro_rules! nonzero_integer_signedness_dependent_impls {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
forward_ref_unop! { impl Neg, neg for $Ty,
|
forward_ref_unop! { impl Neg, neg for NonZero<$Int>,
|
||||||
#[stable(feature = "signed_nonzero_neg", since = "1.71.0")] }
|
#[stable(feature = "signed_nonzero_neg", since = "1.71.0")] }
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@ -920,8 +922,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::MIN.get(), 1", stringify!($Int), ");")]
|
/// #
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::<", stringify!($Int), ">::MIN.get(), 1", stringify!($Int), ");")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
||||||
pub const MIN: Self = Self::new(1).unwrap();
|
pub const MIN: Self = Self::new(1).unwrap();
|
||||||
@ -933,8 +936,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::MAX.get(), ", stringify!($Int), "::MAX);")]
|
/// #
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::<", stringify!($Int), ">::MAX.get(), ", stringify!($Int), "::MAX);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
||||||
pub const MAX: Self = Self::new(<$Int>::MAX).unwrap();
|
pub const MAX: Self = Self::new(<$Int>::MAX).unwrap();
|
||||||
@ -947,13 +951,13 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let one = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(Some(two), one.checked_add(1));
|
/// assert_eq!(Some(two), one.checked_add(1));
|
||||||
/// assert_eq!(None, max.checked_add(1));
|
/// assert_eq!(None, max.checked_add(1));
|
||||||
@ -981,18 +985,18 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Adds an unsigned integer to a non-zero value.
|
/// Adds an unsigned integer to a non-zero value.
|
||||||
#[doc = concat!("Return [`", stringify!($Ty), "::MAX`] on overflow.")]
|
#[doc = concat!("Return [`NonZero::<", stringify!($Int), ">::MAX`] on overflow.")]
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let one = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(two, one.saturating_add(1));
|
/// assert_eq!(two, one.saturating_add(1));
|
||||||
/// assert_eq!(max, max.saturating_add(1));
|
/// assert_eq!(max, max.saturating_add(1));
|
||||||
@ -1027,11 +1031,12 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// ```
|
/// ```
|
||||||
/// #![feature(nonzero_ops)]
|
/// #![feature(nonzero_ops)]
|
||||||
///
|
///
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let one = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(two, unsafe { one.unchecked_add(1) });
|
/// assert_eq!(two, unsafe { one.unchecked_add(1) });
|
||||||
/// # Some(())
|
/// # Some(())
|
||||||
@ -1054,14 +1059,14 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
|
#[doc = concat!("let three = NonZero::new(3", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
|
#[doc = concat!("let four = NonZero::new(4", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(Some(two), two.checked_next_power_of_two() );
|
/// assert_eq!(Some(two), two.checked_next_power_of_two() );
|
||||||
/// assert_eq!(Some(four), three.checked_next_power_of_two() );
|
/// assert_eq!(Some(four), three.checked_next_power_of_two() );
|
||||||
@ -1094,10 +1099,11 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(7).unwrap().ilog2(), 2);")]
|
/// #
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(8).unwrap().ilog2(), 3);")]
|
#[doc = concat!("assert_eq!(NonZero::new(7", stringify!($Int), ").unwrap().ilog2(), 2);")]
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(9).unwrap().ilog2(), 3);")]
|
#[doc = concat!("assert_eq!(NonZero::new(8", stringify!($Int), ").unwrap().ilog2(), 3);")]
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::new(9", stringify!($Int), ").unwrap().ilog2(), 3);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "int_log", since = "1.67.0")]
|
#[stable(feature = "int_log", since = "1.67.0")]
|
||||||
#[rustc_const_stable(feature = "int_log", since = "1.67.0")]
|
#[rustc_const_stable(feature = "int_log", since = "1.67.0")]
|
||||||
@ -1118,10 +1124,11 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(99).unwrap().ilog10(), 1);")]
|
/// #
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(100).unwrap().ilog10(), 2);")]
|
#[doc = concat!("assert_eq!(NonZero::new(99", stringify!($Int), ").unwrap().ilog10(), 1);")]
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::new(101).unwrap().ilog10(), 2);")]
|
#[doc = concat!("assert_eq!(NonZero::new(100", stringify!($Int), ").unwrap().ilog10(), 2);")]
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::new(101", stringify!($Int), ").unwrap().ilog10(), 2);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "int_log", since = "1.67.0")]
|
#[stable(feature = "int_log", since = "1.67.0")]
|
||||||
#[rustc_const_stable(feature = "int_log", since = "1.67.0")]
|
#[rustc_const_stable(feature = "int_log", since = "1.67.0")]
|
||||||
@ -1142,13 +1149,14 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
/// #![feature(num_midpoint)]
|
/// #![feature(num_midpoint)]
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
|
||||||
///
|
///
|
||||||
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let one = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
|
#[doc = concat!("let two = NonZero::new(2", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
|
#[doc = concat!("let four = NonZero::new(4", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(one.midpoint(four), two);
|
/// assert_eq!(one.midpoint(four), two);
|
||||||
/// assert_eq!(four.midpoint(one), two);
|
/// assert_eq!(four.midpoint(one), two);
|
||||||
@ -1179,9 +1187,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// Basic usage:
|
/// Basic usage:
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("let eight = std::num::", stringify!($Ty), "::new(8).unwrap();")]
|
#[doc = concat!("let eight = std::num::NonZero::new(8", stringify!($Int), ").unwrap();")]
|
||||||
/// assert!(eight.is_power_of_two());
|
/// assert!(eight.is_power_of_two());
|
||||||
#[doc = concat!("let ten = std::num::", stringify!($Ty), "::new(10).unwrap();")]
|
#[doc = concat!("let ten = std::num::NonZero::new(10", stringify!($Int), ").unwrap();")]
|
||||||
/// assert!(!ten.is_power_of_two());
|
/// assert!(!ten.is_power_of_two());
|
||||||
/// ```
|
/// ```
|
||||||
#[must_use]
|
#[must_use]
|
||||||
@ -1202,7 +1210,6 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
(
|
(
|
||||||
Self = $Ty:ident,
|
Self = $Ty:ident,
|
||||||
Primitive = signed $Int:ident,
|
Primitive = signed $Int:ident,
|
||||||
UnsignedNonZero = $Uty:ident,
|
|
||||||
UnsignedPrimitive = $Uint:ty,
|
UnsignedPrimitive = $Uint:ty,
|
||||||
) => {
|
) => {
|
||||||
/// The smallest value that can be represented by this non-zero
|
/// The smallest value that can be represented by this non-zero
|
||||||
@ -1216,8 +1223,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::MIN.get(), ", stringify!($Int), "::MIN);")]
|
/// #
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::<", stringify!($Int), ">::MIN.get(), ", stringify!($Int), "::MIN);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
||||||
pub const MIN: Self = Self::new(<$Int>::MIN).unwrap();
|
pub const MIN: Self = Self::new(<$Int>::MIN).unwrap();
|
||||||
@ -1233,8 +1241,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("assert_eq!(", stringify!($Ty), "::MAX.get(), ", stringify!($Int), "::MAX);")]
|
/// #
|
||||||
|
#[doc = concat!("assert_eq!(NonZero::<", stringify!($Int), ">::MAX.get(), ", stringify!($Int), "::MAX);")]
|
||||||
/// ```
|
/// ```
|
||||||
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
#[stable(feature = "nonzero_min_max", since = "1.70.0")]
|
||||||
pub const MAX: Self = Self::new(<$Int>::MAX).unwrap();
|
pub const MAX: Self = Self::new(<$Int>::MAX).unwrap();
|
||||||
@ -1246,11 +1255,12 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos, pos.abs());
|
/// assert_eq!(pos, pos.abs());
|
||||||
/// assert_eq!(pos, neg.abs());
|
/// assert_eq!(pos, neg.abs());
|
||||||
@ -1269,19 +1279,19 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
|
|
||||||
/// Checked absolute value.
|
/// Checked absolute value.
|
||||||
/// Checks for overflow and returns [`None`] if
|
/// Checks for overflow and returns [`None`] if
|
||||||
#[doc = concat!("`self == ", stringify!($Ty), "::MIN`.")]
|
#[doc = concat!("`self == NonZero::<", stringify!($Int), ">::MIN`.")]
|
||||||
/// The result cannot be zero.
|
/// The result cannot be zero.
|
||||||
///
|
///
|
||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(Some(pos), neg.checked_abs());
|
/// assert_eq!(Some(pos), neg.checked_abs());
|
||||||
/// assert_eq!(None, min.checked_abs());
|
/// assert_eq!(None, min.checked_abs());
|
||||||
@ -1309,13 +1319,13 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!((pos, false), pos.overflowing_abs());
|
/// assert_eq!((pos, false), pos.overflowing_abs());
|
||||||
/// assert_eq!((pos, false), neg.overflowing_abs());
|
/// assert_eq!((pos, false), neg.overflowing_abs());
|
||||||
@ -1343,17 +1353,15 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
#[doc = concat!("let min_plus = NonZero::new(", stringify!($Int), "::MIN + 1)?;")]
|
||||||
#[doc = concat!("let min_plus = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MIN + 1)?;")]
|
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos, pos.saturating_abs());
|
/// assert_eq!(pos, pos.saturating_abs());
|
||||||
/// assert_eq!(pos, neg.saturating_abs());
|
/// assert_eq!(pos, neg.saturating_abs());
|
||||||
@ -1378,15 +1386,14 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
#[doc = concat!("# let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
#[doc = concat!("# let max = ", stringify!($Ty), "::new(",
|
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos, pos.wrapping_abs());
|
/// assert_eq!(pos, pos.wrapping_abs());
|
||||||
/// assert_eq!(pos, neg.wrapping_abs());
|
/// assert_eq!(pos, neg.wrapping_abs());
|
||||||
@ -1411,18 +1418,15 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
#[doc = concat!("# use std::num::", stringify!($Uty), ";")]
|
/// #
|
||||||
///
|
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let u_pos = ", stringify!($Uty), "::new(1)?;")]
|
#[doc = concat!("let u_pos = NonZero::new(1", stringify!($Uint), ")?;")]
|
||||||
#[doc = concat!("let i_pos = ", stringify!($Ty), "::new(1)?;")]
|
#[doc = concat!("let i_pos = NonZero::new(1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let i_neg = ", stringify!($Ty), "::new(-1)?;")]
|
#[doc = concat!("let i_neg = NonZero::new(-1", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let i_min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let i_min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
#[doc = concat!("let u_max = NonZero::new(", stringify!($Uint), "::MAX / 2 + 1)?;")]
|
||||||
#[doc = concat!("let u_max = ", stringify!($Uty), "::new(",
|
|
||||||
stringify!($Uint), "::MAX / 2 + 1)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(u_pos, i_pos.unsigned_abs());
|
/// assert_eq!(u_pos, i_pos.unsigned_abs());
|
||||||
/// assert_eq!(u_pos, i_neg.unsigned_abs());
|
/// assert_eq!(u_pos, i_neg.unsigned_abs());
|
||||||
@ -1435,9 +1439,9 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
#[must_use = "this returns the result of the operation, \
|
#[must_use = "this returns the result of the operation, \
|
||||||
without modifying the original"]
|
without modifying the original"]
|
||||||
#[inline]
|
#[inline]
|
||||||
pub const fn unsigned_abs(self) -> $Uty {
|
pub const fn unsigned_abs(self) -> NonZero<$Uint> {
|
||||||
// SAFETY: absolute value of nonzero cannot yield zero values.
|
// SAFETY: absolute value of nonzero cannot yield zero values.
|
||||||
unsafe { $Uty::new_unchecked(self.get().unsigned_abs()) }
|
unsafe { NonZero::new_unchecked(self.get().unsigned_abs()) }
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns `true` if `self` is positive and `false` if the
|
/// Returns `true` if `self` is positive and `false` if the
|
||||||
@ -1446,11 +1450,12 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert!(pos_five.is_positive());
|
/// assert!(pos_five.is_positive());
|
||||||
/// assert!(!neg_five.is_positive());
|
/// assert!(!neg_five.is_positive());
|
||||||
@ -1471,11 +1476,12 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
///
|
///
|
||||||
/// assert!(neg_five.is_negative());
|
/// assert!(neg_five.is_negative());
|
||||||
/// assert!(!pos_five.is_negative());
|
/// assert!(!pos_five.is_negative());
|
||||||
@ -1491,18 +1497,18 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Checked negation. Computes `-self`,
|
/// Checked negation. Computes `-self`,
|
||||||
#[doc = concat!("returning `None` if `self == ", stringify!($Ty), "::MIN`.")]
|
#[doc = concat!("returning `None` if `self == NonZero::<", stringify!($Int), ">::MIN`.")]
|
||||||
///
|
///
|
||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos_five.checked_neg(), Some(neg_five));
|
/// assert_eq!(pos_five.checked_neg(), Some(neg_five));
|
||||||
/// assert_eq!(min.checked_neg(), None);
|
/// assert_eq!(min.checked_neg(), None);
|
||||||
@ -1528,13 +1534,13 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos_five.overflowing_neg(), (neg_five, false));
|
/// assert_eq!(pos_five.overflowing_neg(), (neg_five, false));
|
||||||
/// assert_eq!(min.overflowing_neg(), (min, true));
|
/// assert_eq!(min.overflowing_neg(), (min, true));
|
||||||
@ -1551,24 +1557,22 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Saturating negation. Computes `-self`,
|
/// Saturating negation. Computes `-self`,
|
||||||
#[doc = concat!("returning [`", stringify!($Ty), "::MAX`]")]
|
#[doc = concat!("returning [`NonZero::<", stringify!($Int), ">::MAX`]")]
|
||||||
#[doc = concat!("if `self == ", stringify!($Ty), "::MIN`")]
|
#[doc = concat!("if `self == NonZero::<", stringify!($Int), ">::MIN`")]
|
||||||
/// instead of overflowing.
|
/// instead of overflowing.
|
||||||
///
|
///
|
||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
#[doc = concat!("let min_plus_one = NonZero::new(", stringify!($Int), "::MIN + 1)?;")]
|
||||||
#[doc = concat!("let min_plus_one = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let max = NonZero::new(", stringify!($Int), "::MAX)?;")]
|
||||||
stringify!($Int), "::MIN + 1)?;")]
|
|
||||||
#[doc = concat!("let max = ", stringify!($Ty), "::new(",
|
|
||||||
stringify!($Int), "::MAX)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos_five.saturating_neg(), neg_five);
|
/// assert_eq!(pos_five.saturating_neg(), neg_five);
|
||||||
/// assert_eq!(min.saturating_neg(), max);
|
/// assert_eq!(min.saturating_neg(), max);
|
||||||
@ -1595,13 +1599,13 @@ macro_rules! nonzero_integer_signedness_dependent_methods {
|
|||||||
/// # Example
|
/// # Example
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
#[doc = concat!("# use std::num::", stringify!($Ty), ";")]
|
/// # use std::num::NonZero;
|
||||||
|
/// #
|
||||||
/// # fn main() { test().unwrap(); }
|
/// # fn main() { test().unwrap(); }
|
||||||
/// # fn test() -> Option<()> {
|
/// # fn test() -> Option<()> {
|
||||||
#[doc = concat!("let pos_five = ", stringify!($Ty), "::new(5)?;")]
|
#[doc = concat!("let pos_five = NonZero::new(5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let neg_five = ", stringify!($Ty), "::new(-5)?;")]
|
#[doc = concat!("let neg_five = NonZero::new(-5", stringify!($Int), ")?;")]
|
||||||
#[doc = concat!("let min = ", stringify!($Ty), "::new(",
|
#[doc = concat!("let min = NonZero::new(", stringify!($Int), "::MIN)?;")]
|
||||||
stringify!($Int), "::MIN)?;")]
|
|
||||||
///
|
///
|
||||||
/// assert_eq!(pos_five.wrapping_neg(), neg_five);
|
/// assert_eq!(pos_five.wrapping_neg(), neg_five);
|
||||||
/// assert_eq!(min.wrapping_neg(), min);
|
/// assert_eq!(min.wrapping_neg(), min);
|
||||||
@ -1662,41 +1666,35 @@ nonzero_integer! {
|
|||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroI8,
|
Self = NonZeroI8,
|
||||||
Primitive = signed i8,
|
Primitive = signed i8,
|
||||||
UnsignedNonZero = NonZeroU8,
|
|
||||||
UnsignedPrimitive = u8,
|
UnsignedPrimitive = u8,
|
||||||
}
|
}
|
||||||
|
|
||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroI16,
|
Self = NonZeroI16,
|
||||||
Primitive = signed i16,
|
Primitive = signed i16,
|
||||||
UnsignedNonZero = NonZeroU16,
|
|
||||||
UnsignedPrimitive = u16,
|
UnsignedPrimitive = u16,
|
||||||
}
|
}
|
||||||
|
|
||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroI32,
|
Self = NonZeroI32,
|
||||||
Primitive = signed i32,
|
Primitive = signed i32,
|
||||||
UnsignedNonZero = NonZeroU32,
|
|
||||||
UnsignedPrimitive = u32,
|
UnsignedPrimitive = u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroI64,
|
Self = NonZeroI64,
|
||||||
Primitive = signed i64,
|
Primitive = signed i64,
|
||||||
UnsignedNonZero = NonZeroU64,
|
|
||||||
UnsignedPrimitive = u64,
|
UnsignedPrimitive = u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroI128,
|
Self = NonZeroI128,
|
||||||
Primitive = signed i128,
|
Primitive = signed i128,
|
||||||
UnsignedNonZero = NonZeroU128,
|
|
||||||
UnsignedPrimitive = u128,
|
UnsignedPrimitive = u128,
|
||||||
}
|
}
|
||||||
|
|
||||||
nonzero_integer! {
|
nonzero_integer! {
|
||||||
Self = NonZeroIsize,
|
Self = NonZeroIsize,
|
||||||
Primitive = signed isize,
|
Primitive = signed isize,
|
||||||
UnsignedNonZero = NonZeroUsize,
|
|
||||||
UnsignedPrimitive = usize,
|
UnsignedPrimitive = usize,
|
||||||
}
|
}
|
||||||
|
@ -13,4 +13,4 @@ core = { path = "../core" }
|
|||||||
compiler_builtins = { version = "0.1.0", features = ['rustc-dep-of-std'] }
|
compiler_builtins = { version = "0.1.0", features = ['rustc-dep-of-std'] }
|
||||||
|
|
||||||
[build-dependencies]
|
[build-dependencies]
|
||||||
cc = "1.0.90"
|
cc = "1.0.97"
|
||||||
|
@ -91,12 +91,13 @@ fn main() {
|
|||||||
rustc_real
|
rustc_real
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut cmd = if let Some(wrapper) = env::var_os("RUSTC_WRAPPER_REAL") {
|
let mut cmd = match env::var_os("RUSTC_WRAPPER_REAL") {
|
||||||
let mut cmd = Command::new(wrapper);
|
Some(wrapper) if !wrapper.is_empty() => {
|
||||||
cmd.arg(rustc_driver);
|
let mut cmd = Command::new(wrapper);
|
||||||
cmd
|
cmd.arg(rustc_driver);
|
||||||
} else {
|
cmd
|
||||||
Command::new(rustc_driver)
|
}
|
||||||
|
_ => Command::new(rustc_driver),
|
||||||
};
|
};
|
||||||
cmd.args(&args).env(dylib_path_var(), env::join_paths(&dylib_path).unwrap());
|
cmd.args(&args).env(dylib_path_var(), env::join_paths(&dylib_path).unwrap());
|
||||||
|
|
||||||
|
@ -1860,9 +1860,9 @@ fn normalize<'tcx>(
|
|||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
|
|
||||||
use crate::rustc_trait_selection::infer::TyCtxtInferExt;
|
|
||||||
use crate::rustc_trait_selection::traits::query::normalize::QueryNormalizeExt;
|
|
||||||
use rustc_middle::traits::ObligationCause;
|
use rustc_middle::traits::ObligationCause;
|
||||||
|
use rustc_trait_selection::infer::TyCtxtInferExt;
|
||||||
|
use rustc_trait_selection::traits::query::normalize::QueryNormalizeExt;
|
||||||
|
|
||||||
// Try to normalize `<X as Y>::T` to a type
|
// Try to normalize `<X as Y>::T` to a type
|
||||||
let infcx = cx.tcx.infer_ctxt().build();
|
let infcx = cx.tcx.infer_ctxt().build();
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use crate::html::markdown::{ErrorCodes, HeadingOffset, IdMap, Markdown, Playground};
|
use crate::html::markdown::{ErrorCodes, HeadingOffset, IdMap, Markdown, Playground};
|
||||||
use crate::rustc_span::edition::Edition;
|
use rustc_span::edition::Edition;
|
||||||
use std::fs;
|
use std::fs;
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
use std::str;
|
use std::str;
|
||||||
|
@ -594,9 +594,9 @@ fn generate_item_def_id_path(
|
|||||||
root_path: Option<&str>,
|
root_path: Option<&str>,
|
||||||
original_def_kind: DefKind,
|
original_def_kind: DefKind,
|
||||||
) -> Result<(String, ItemType, Vec<Symbol>), HrefError> {
|
) -> Result<(String, ItemType, Vec<Symbol>), HrefError> {
|
||||||
use crate::rustc_trait_selection::infer::TyCtxtInferExt;
|
|
||||||
use crate::rustc_trait_selection::traits::query::normalize::QueryNormalizeExt;
|
|
||||||
use rustc_middle::traits::ObligationCause;
|
use rustc_middle::traits::ObligationCause;
|
||||||
|
use rustc_trait_selection::infer::TyCtxtInferExt;
|
||||||
|
use rustc_trait_selection::traits::query::normalize::QueryNormalizeExt;
|
||||||
|
|
||||||
let tcx = cx.tcx();
|
let tcx = cx.tcx();
|
||||||
let crate_name = tcx.crate_name(def_id.krate);
|
let crate_name = tcx.crate_name(def_id.krate);
|
||||||
|
@ -236,7 +236,7 @@ fn main() {
|
|||||||
let num_threads = if let Some(num) = env::var_os("BUILD_MANIFEST_NUM_THREADS") {
|
let num_threads = if let Some(num) = env::var_os("BUILD_MANIFEST_NUM_THREADS") {
|
||||||
num.to_str().unwrap().parse().expect("invalid number for BUILD_MANIFEST_NUM_THREADS")
|
num.to_str().unwrap().parse().expect("invalid number for BUILD_MANIFEST_NUM_THREADS")
|
||||||
} else {
|
} else {
|
||||||
std::thread::available_parallelism().map_or(1, std::num::NonZeroUsize::get)
|
std::thread::available_parallelism().map_or(1, std::num::NonZero::get)
|
||||||
};
|
};
|
||||||
rayon::ThreadPoolBuilder::new()
|
rayon::ThreadPoolBuilder::new()
|
||||||
.num_threads(num_threads)
|
.num_threads(num_threads)
|
||||||
|
@ -1,10 +1,9 @@
|
|||||||
use crate::rustc_lint::LintContext;
|
|
||||||
use clippy_utils::diagnostics::span_lint_and_then;
|
use clippy_utils::diagnostics::span_lint_and_then;
|
||||||
use clippy_utils::macros::{is_panic, root_macro_call};
|
use clippy_utils::macros::{is_panic, root_macro_call};
|
||||||
use clippy_utils::{is_else_clause, is_parent_stmt, peel_blocks_with_stmt, span_extract_comment, sugg};
|
use clippy_utils::{is_else_clause, is_parent_stmt, peel_blocks_with_stmt, span_extract_comment, sugg};
|
||||||
use rustc_errors::Applicability;
|
use rustc_errors::Applicability;
|
||||||
use rustc_hir::{Expr, ExprKind, UnOp};
|
use rustc_hir::{Expr, ExprKind, UnOp};
|
||||||
use rustc_lint::{LateContext, LateLintPass};
|
use rustc_lint::{LateContext, LateLintPass, LintContext};
|
||||||
use rustc_session::declare_lint_pass;
|
use rustc_session::declare_lint_pass;
|
||||||
|
|
||||||
declare_clippy_lint! {
|
declare_clippy_lint! {
|
||||||
|
@ -9,10 +9,10 @@ use rustc_lint::LateContext;
|
|||||||
use rustc_middle::mir::{FakeReadCause, Mutability};
|
use rustc_middle::mir::{FakeReadCause, Mutability};
|
||||||
use rustc_middle::ty::{self, BorrowKind};
|
use rustc_middle::ty::{self, BorrowKind};
|
||||||
use rustc_span::sym;
|
use rustc_span::sym;
|
||||||
|
use rustc_trait_selection::infer::TyCtxtInferExt;
|
||||||
|
|
||||||
use super::ITER_OVEREAGER_CLONED;
|
use super::ITER_OVEREAGER_CLONED;
|
||||||
use crate::redundant_clone::REDUNDANT_CLONE;
|
use crate::redundant_clone::REDUNDANT_CLONE;
|
||||||
use crate::rustc_trait_selection::infer::TyCtxtInferExt;
|
|
||||||
|
|
||||||
#[derive(Clone, Copy)]
|
#[derive(Clone, Copy)]
|
||||||
pub(super) enum Op<'a> {
|
pub(super) enum Op<'a> {
|
||||||
|
@ -1,4 +1,3 @@
|
|||||||
use crate::rustc_lint::LintContext;
|
|
||||||
use clippy_utils::diagnostics::{span_lint_and_then, span_lint_hir};
|
use clippy_utils::diagnostics::{span_lint_and_then, span_lint_hir};
|
||||||
use clippy_utils::get_parent_expr;
|
use clippy_utils::get_parent_expr;
|
||||||
use clippy_utils::sugg::Sugg;
|
use clippy_utils::sugg::Sugg;
|
||||||
@ -9,7 +8,7 @@ use rustc_hir::intravisit::{Visitor as HirVisitor, Visitor};
|
|||||||
use rustc_hir::{
|
use rustc_hir::{
|
||||||
intravisit as hir_visit, ClosureKind, CoroutineDesugaring, CoroutineKind, CoroutineSource, ExprKind, Node,
|
intravisit as hir_visit, ClosureKind, CoroutineDesugaring, CoroutineKind, CoroutineSource, ExprKind, Node,
|
||||||
};
|
};
|
||||||
use rustc_lint::{LateContext, LateLintPass};
|
use rustc_lint::{LateContext, LateLintPass, LintContext};
|
||||||
use rustc_middle::hir::nested_filter;
|
use rustc_middle::hir::nested_filter;
|
||||||
use rustc_middle::lint::in_external_macro;
|
use rustc_middle::lint::in_external_macro;
|
||||||
use rustc_middle::ty;
|
use rustc_middle::ty;
|
||||||
|
@ -1,9 +1,8 @@
|
|||||||
use crate::rustc_lint::LintContext;
|
|
||||||
use clippy_utils::diagnostics::span_lint_and_sugg;
|
use clippy_utils::diagnostics::span_lint_and_sugg;
|
||||||
use clippy_utils::source::snippet_with_context;
|
use clippy_utils::source::snippet_with_context;
|
||||||
use rustc_errors::Applicability;
|
use rustc_errors::Applicability;
|
||||||
use rustc_hir::{Block, ExprKind};
|
use rustc_hir::{Block, ExprKind};
|
||||||
use rustc_lint::{LateContext, LateLintPass};
|
use rustc_lint::{LateContext, LateLintPass, LintContext};
|
||||||
use rustc_session::declare_lint_pass;
|
use rustc_session::declare_lint_pass;
|
||||||
use rustc_span::{ExpnKind, MacroKind, Span};
|
use rustc_span::{ExpnKind, MacroKind, Span};
|
||||||
|
|
||||||
|
@ -201,8 +201,8 @@ impl SingleComponentPathImports {
|
|||||||
|
|
||||||
if segments.is_empty() {
|
if segments.is_empty() {
|
||||||
// keep track of `use {some_module, some_other_module};` usages
|
// keep track of `use {some_module, some_other_module};` usages
|
||||||
if let UseTreeKind::Nested(trees) = &use_tree.kind {
|
if let UseTreeKind::Nested { items, .. } = &use_tree.kind {
|
||||||
for tree in trees {
|
for tree in items {
|
||||||
let segments = &tree.0.prefix.segments;
|
let segments = &tree.0.prefix.segments;
|
||||||
if segments.len() == 1 {
|
if segments.len() == 1 {
|
||||||
if let UseTreeKind::Simple(None) = tree.0.kind {
|
if let UseTreeKind::Simple(None) = tree.0.kind {
|
||||||
@ -229,8 +229,8 @@ impl SingleComponentPathImports {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// nested case such as `use self::{module1::Struct1, module2::Struct2}`
|
// nested case such as `use self::{module1::Struct1, module2::Struct2}`
|
||||||
if let UseTreeKind::Nested(trees) = &use_tree.kind {
|
if let UseTreeKind::Nested { items, .. } = &use_tree.kind {
|
||||||
for tree in trees {
|
for tree in items {
|
||||||
let segments = &tree.0.prefix.segments;
|
let segments = &tree.0.prefix.segments;
|
||||||
if !segments.is_empty() {
|
if !segments.is_empty() {
|
||||||
imports_reused_with_self.push(segments[0].ident.name);
|
imports_reused_with_self.push(segments[0].ident.name);
|
||||||
|
@ -87,7 +87,7 @@ pub(super) fn check<'tcx>(
|
|||||||
&& is_normalizable(cx, cx.param_env, from_ty)
|
&& is_normalizable(cx, cx.param_env, from_ty)
|
||||||
&& is_normalizable(cx, cx.param_env, to_ty)
|
&& is_normalizable(cx, cx.param_env, to_ty)
|
||||||
// we only want to lint if the target type has a niche that is larger than the one of the source type
|
// we only want to lint if the target type has a niche that is larger than the one of the source type
|
||||||
// e.g. `u8` to `NonZeroU8` should lint, but `NonZeroU8` to `u8` should not
|
// e.g. `u8` to `NonZero<u8>` should lint, but `NonZero<u8>` to `u8` should not
|
||||||
&& let Ok(from_layout) = cx.tcx.layout_of(cx.param_env.and(from_ty))
|
&& let Ok(from_layout) = cx.tcx.layout_of(cx.param_env.and(from_ty))
|
||||||
&& let Ok(to_layout) = cx.tcx.layout_of(cx.param_env.and(to_ty))
|
&& let Ok(to_layout) = cx.tcx.layout_of(cx.param_env.and(to_ty))
|
||||||
&& match (from_layout.largest_niche, to_layout.largest_niche) {
|
&& match (from_layout.largest_niche, to_layout.largest_niche) {
|
||||||
|
@ -257,7 +257,7 @@ declare_clippy_lint! {
|
|||||||
|
|
||||||
declare_clippy_lint! {
|
declare_clippy_lint! {
|
||||||
/// ### What it does
|
/// ### What it does
|
||||||
/// Checks for transmutes from integers to `NonZero*` types, and suggests their `new_unchecked`
|
/// Checks for transmutes from `T` to `NonZero<T>`, and suggests the `new_unchecked`
|
||||||
/// method instead.
|
/// method instead.
|
||||||
///
|
///
|
||||||
/// ### Why is this bad?
|
/// ### Why is this bad?
|
||||||
@ -266,13 +266,13 @@ declare_clippy_lint! {
|
|||||||
///
|
///
|
||||||
/// ### Example
|
/// ### Example
|
||||||
/// ```no_run
|
/// ```no_run
|
||||||
/// # use core::num::NonZeroU32;
|
/// # use core::num::NonZero;
|
||||||
/// let _non_zero: NonZeroU32 = unsafe { std::mem::transmute(123) };
|
/// let _: NonZero<u32> = unsafe { std::mem::transmute(123) };
|
||||||
/// ```
|
/// ```
|
||||||
/// Use instead:
|
/// Use instead:
|
||||||
/// ```no_run
|
/// ```no_run
|
||||||
/// # use core::num::NonZeroU32;
|
/// # use core::num::NonZero;
|
||||||
/// let _non_zero = unsafe { NonZeroU32::new_unchecked(123) };
|
/// let _: NonZero<u32> = unsafe { NonZero::new_unchecked(123) };
|
||||||
/// ```
|
/// ```
|
||||||
#[clippy::version = "1.69.0"]
|
#[clippy::version = "1.69.0"]
|
||||||
pub TRANSMUTE_INT_TO_NON_ZERO,
|
pub TRANSMUTE_INT_TO_NON_ZERO,
|
||||||
|
@ -26,45 +26,22 @@ pub(super) fn check<'tcx>(
|
|||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
|
|
||||||
// FIXME: This can be simplified once `NonZero<T>` is stable.
|
let int_ty = substs.type_at(0);
|
||||||
let coercible_types = [
|
if from_ty != int_ty {
|
||||||
("NonZeroU8", tcx.types.u8),
|
return false;
|
||||||
("NonZeroU16", tcx.types.u16),
|
}
|
||||||
("NonZeroU32", tcx.types.u32),
|
|
||||||
("NonZeroU64", tcx.types.u64),
|
|
||||||
("NonZeroU128", tcx.types.u128),
|
|
||||||
("NonZeroUsize", tcx.types.usize),
|
|
||||||
("NonZeroI8", tcx.types.i8),
|
|
||||||
("NonZeroI16", tcx.types.i16),
|
|
||||||
("NonZeroI32", tcx.types.i32),
|
|
||||||
("NonZeroI64", tcx.types.i64),
|
|
||||||
("NonZeroI128", tcx.types.i128),
|
|
||||||
("NonZeroIsize", tcx.types.isize),
|
|
||||||
];
|
|
||||||
|
|
||||||
let int_type = substs.type_at(0);
|
|
||||||
|
|
||||||
let Some(nonzero_alias) = coercible_types.iter().find_map(|(nonzero_alias, t)| {
|
|
||||||
if *t == int_type && *t == from_ty {
|
|
||||||
Some(nonzero_alias)
|
|
||||||
} else {
|
|
||||||
None
|
|
||||||
}
|
|
||||||
}) else {
|
|
||||||
return false;
|
|
||||||
};
|
|
||||||
|
|
||||||
span_lint_and_then(
|
span_lint_and_then(
|
||||||
cx,
|
cx,
|
||||||
TRANSMUTE_INT_TO_NON_ZERO,
|
TRANSMUTE_INT_TO_NON_ZERO,
|
||||||
e.span,
|
e.span,
|
||||||
format!("transmute from a `{from_ty}` to a `{nonzero_alias}`"),
|
format!("transmute from a `{from_ty}` to a `{}<{int_ty}>`", sym::NonZero),
|
||||||
|diag| {
|
|diag| {
|
||||||
let arg = sugg::Sugg::hir(cx, arg, "..");
|
let arg = sugg::Sugg::hir(cx, arg, "..");
|
||||||
diag.span_suggestion(
|
diag.span_suggestion(
|
||||||
e.span,
|
e.span,
|
||||||
"consider using",
|
"consider using",
|
||||||
format!("{nonzero_alias}::{}({arg})", sym::new_unchecked),
|
format!("{}::{}({arg})", sym::NonZero, sym::new_unchecked),
|
||||||
Applicability::Unspecified,
|
Applicability::Unspecified,
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
@ -36,8 +36,8 @@ declare_lint_pass!(UnnecessarySelfImports => [UNNECESSARY_SELF_IMPORTS]);
|
|||||||
impl EarlyLintPass for UnnecessarySelfImports {
|
impl EarlyLintPass for UnnecessarySelfImports {
|
||||||
fn check_item(&mut self, cx: &EarlyContext<'_>, item: &Item) {
|
fn check_item(&mut self, cx: &EarlyContext<'_>, item: &Item) {
|
||||||
if let ItemKind::Use(use_tree) = &item.kind
|
if let ItemKind::Use(use_tree) = &item.kind
|
||||||
&& let UseTreeKind::Nested(nodes) = &use_tree.kind
|
&& let UseTreeKind::Nested { items, .. } = &use_tree.kind
|
||||||
&& let [(self_tree, _)] = &**nodes
|
&& let [(self_tree, _)] = &**items
|
||||||
&& let [self_seg] = &*self_tree.prefix.segments
|
&& let [self_seg] = &*self_tree.prefix.segments
|
||||||
&& self_seg.ident.name == kw::SelfLower
|
&& self_seg.ident.name == kw::SelfLower
|
||||||
&& let Some(last_segment) = use_tree.prefix.segments.last()
|
&& let Some(last_segment) = use_tree.prefix.segments.last()
|
||||||
|
@ -49,8 +49,8 @@ fn check_use_tree(use_tree: &UseTree, cx: &EarlyContext<'_>, span: Span) {
|
|||||||
unsafe_to_safe_check(old_name, new_name, cx, span);
|
unsafe_to_safe_check(old_name, new_name, cx, span);
|
||||||
},
|
},
|
||||||
UseTreeKind::Simple(None) | UseTreeKind::Glob => {},
|
UseTreeKind::Simple(None) | UseTreeKind::Glob => {},
|
||||||
UseTreeKind::Nested(ref nested_use_tree) => {
|
UseTreeKind::Nested { ref items, .. } => {
|
||||||
for (use_tree, _) in nested_use_tree {
|
for (use_tree, _) in items {
|
||||||
check_use_tree(use_tree, cx, span);
|
check_use_tree(use_tree, cx, span);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -648,7 +648,7 @@ pub fn eq_use_tree_kind(l: &UseTreeKind, r: &UseTreeKind) -> bool {
|
|||||||
match (l, r) {
|
match (l, r) {
|
||||||
(Glob, Glob) => true,
|
(Glob, Glob) => true,
|
||||||
(Simple(l), Simple(r)) => both(l, r, |l, r| eq_id(*l, *r)),
|
(Simple(l), Simple(r)) => both(l, r, |l, r| eq_id(*l, *r)),
|
||||||
(Nested(l), Nested(r)) => over(l, r, |(l, _), (r, _)| eq_use_tree(l, r)),
|
(Nested { items: l, .. }, Nested { items: r, .. }) => over(l, r, |(l, _), (r, _)| eq_use_tree(l, r)),
|
||||||
_ => false,
|
_ => false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use clap::Parser;
|
use clap::Parser;
|
||||||
use std::num::NonZeroUsize;
|
use std::num::NonZero;
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
|
|
||||||
#[derive(Clone, Debug, Parser)]
|
#[derive(Clone, Debug, Parser)]
|
||||||
@ -61,7 +61,7 @@ impl LintcheckConfig {
|
|||||||
config.max_jobs = if config.fix || config.recursive {
|
config.max_jobs = if config.fix || config.recursive {
|
||||||
1
|
1
|
||||||
} else {
|
} else {
|
||||||
std::thread::available_parallelism().map_or(1, NonZeroUsize::get)
|
std::thread::available_parallelism().map_or(1, NonZero::get)
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
|
|
||||||
extern crate proc_macro_derive;
|
extern crate proc_macro_derive;
|
||||||
|
|
||||||
use core::num::{NonZeroUsize, Saturating, Wrapping};
|
use core::num::{NonZero, Saturating, Wrapping};
|
||||||
|
|
||||||
const ONE: i32 = 1;
|
const ONE: i32 = 1;
|
||||||
const ZERO: i32 = 0;
|
const ZERO: i32 = 0;
|
||||||
@ -494,15 +494,15 @@ pub fn issue_11262() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn issue_11392() {
|
pub fn issue_11392() {
|
||||||
fn example_div(unsigned: usize, nonzero_unsigned: NonZeroUsize) -> usize {
|
fn example_div(unsigned: usize, nonzero_unsigned: NonZero<usize>) -> usize {
|
||||||
unsigned / nonzero_unsigned
|
unsigned / nonzero_unsigned
|
||||||
}
|
}
|
||||||
|
|
||||||
fn example_rem(unsigned: usize, nonzero_unsigned: NonZeroUsize) -> usize {
|
fn example_rem(unsigned: usize, nonzero_unsigned: NonZero<usize>) -> usize {
|
||||||
unsigned % nonzero_unsigned
|
unsigned % nonzero_unsigned
|
||||||
}
|
}
|
||||||
|
|
||||||
let (unsigned, nonzero_unsigned) = (0, NonZeroUsize::new(1).unwrap());
|
let (unsigned, nonzero_unsigned) = (0, NonZero::new(1).unwrap());
|
||||||
example_div(unsigned, nonzero_unsigned);
|
example_div(unsigned, nonzero_unsigned);
|
||||||
example_rem(unsigned, nonzero_unsigned);
|
example_rem(unsigned, nonzero_unsigned);
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
#![warn(clippy::eager_transmute)]
|
#![warn(clippy::eager_transmute)]
|
||||||
#![allow(clippy::transmute_int_to_non_zero, clippy::missing_transmute_annotations)]
|
#![allow(clippy::transmute_int_to_non_zero, clippy::missing_transmute_annotations)]
|
||||||
|
|
||||||
use std::num::NonZeroU8;
|
use std::num::NonZero;
|
||||||
|
|
||||||
#[repr(u8)]
|
#[repr(u8)]
|
||||||
enum Opcode {
|
enum Opcode {
|
||||||
@ -85,21 +85,21 @@ macro_rules! impls {
|
|||||||
}
|
}
|
||||||
impls!(NonMaxU8, NonZeroNonMaxU8);
|
impls!(NonMaxU8, NonZeroNonMaxU8);
|
||||||
|
|
||||||
fn niche_tests(v1: u8, v2: NonZeroU8, v3: NonZeroNonMaxU8) {
|
fn niche_tests(v1: u8, v2: NonZero<u8>, v3: NonZeroNonMaxU8) {
|
||||||
// u8 -> NonZeroU8, do lint
|
// u8 -> NonZero<u8>, do lint
|
||||||
let _: Option<NonZeroU8> = (v1 > 0).then(|| unsafe { std::mem::transmute(v1) });
|
let _: Option<NonZero<u8>> = (v1 > 0).then(|| unsafe { std::mem::transmute(v1) });
|
||||||
|
|
||||||
// NonZeroU8 -> u8, don't lint, target type has no niche and therefore a higher validity range
|
// NonZero<u8> -> u8, don't lint, target type has no niche and therefore a higher validity range
|
||||||
let _: Option<u8> = (v2 > NonZeroU8::new(1).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<u8> = (v2 > NonZero::new(1u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroU8 -> NonMaxU8, do lint, different niche
|
// NonZero<u8> -> NonMaxU8, do lint, different niche
|
||||||
let _: Option<NonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
let _: Option<NonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroNonMaxU8 -> NonMaxU8, don't lint, target type has more validity
|
// NonZeroNonMaxU8 -> NonMaxU8, don't lint, target type has more validity
|
||||||
let _: Option<NonMaxU8> = (v3 < 255).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<NonMaxU8> = (v3 < 255).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroU8 -> NonZeroNonMaxU8, do lint, target type has less validity
|
// NonZero<u8> -> NonZeroNonMaxU8, do lint, target type has less validity
|
||||||
let _: Option<NonZeroNonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
let _: Option<NonZeroNonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
#![warn(clippy::eager_transmute)]
|
#![warn(clippy::eager_transmute)]
|
||||||
#![allow(clippy::transmute_int_to_non_zero, clippy::missing_transmute_annotations)]
|
#![allow(clippy::transmute_int_to_non_zero, clippy::missing_transmute_annotations)]
|
||||||
|
|
||||||
use std::num::NonZeroU8;
|
use std::num::NonZero;
|
||||||
|
|
||||||
#[repr(u8)]
|
#[repr(u8)]
|
||||||
enum Opcode {
|
enum Opcode {
|
||||||
@ -85,21 +85,21 @@ macro_rules! impls {
|
|||||||
}
|
}
|
||||||
impls!(NonMaxU8, NonZeroNonMaxU8);
|
impls!(NonMaxU8, NonZeroNonMaxU8);
|
||||||
|
|
||||||
fn niche_tests(v1: u8, v2: NonZeroU8, v3: NonZeroNonMaxU8) {
|
fn niche_tests(v1: u8, v2: NonZero<u8>, v3: NonZeroNonMaxU8) {
|
||||||
// u8 -> NonZeroU8, do lint
|
// u8 -> NonZero<u8>, do lint
|
||||||
let _: Option<NonZeroU8> = (v1 > 0).then_some(unsafe { std::mem::transmute(v1) });
|
let _: Option<NonZero<u8>> = (v1 > 0).then_some(unsafe { std::mem::transmute(v1) });
|
||||||
|
|
||||||
// NonZeroU8 -> u8, don't lint, target type has no niche and therefore a higher validity range
|
// NonZero<u8> -> u8, don't lint, target type has no niche and therefore a higher validity range
|
||||||
let _: Option<u8> = (v2 > NonZeroU8::new(1).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<u8> = (v2 > NonZero::new(1u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroU8 -> NonMaxU8, do lint, different niche
|
// NonZero<u8> -> NonMaxU8, do lint, different niche
|
||||||
let _: Option<NonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<NonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroNonMaxU8 -> NonMaxU8, don't lint, target type has more validity
|
// NonZeroNonMaxU8 -> NonMaxU8, don't lint, target type has more validity
|
||||||
let _: Option<NonMaxU8> = (v3 < 255).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<NonMaxU8> = (v3 < 255).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
|
|
||||||
// NonZeroU8 -> NonZeroNonMaxU8, do lint, target type has less validity
|
// NonZero<u8> -> NonZeroNonMaxU8, do lint, target type has less validity
|
||||||
let _: Option<NonZeroNonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
let _: Option<NonZeroNonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
@ -155,36 +155,36 @@ LL | (op < 4).then(|| std::mem::transmute::<_, Opcode>(op));
|
|||||||
| ~~~~ ++
|
| ~~~~ ++
|
||||||
|
|
||||||
error: this transmute is always evaluated eagerly, even if the condition is false
|
error: this transmute is always evaluated eagerly, even if the condition is false
|
||||||
--> tests/ui/eager_transmute.rs:90:60
|
--> tests/ui/eager_transmute.rs:90:62
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonZeroU8> = (v1 > 0).then_some(unsafe { std::mem::transmute(v1) });
|
LL | let _: Option<NonZero<u8>> = (v1 > 0).then_some(unsafe { std::mem::transmute(v1) });
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
|
||||||
help: consider using `bool::then` to only transmute if the condition holds
|
help: consider using `bool::then` to only transmute if the condition holds
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonZeroU8> = (v1 > 0).then(|| unsafe { std::mem::transmute(v1) });
|
LL | let _: Option<NonZero<u8>> = (v1 > 0).then(|| unsafe { std::mem::transmute(v1) });
|
||||||
| ~~~~ ++
|
| ~~~~ ++
|
||||||
|
|
||||||
error: this transmute is always evaluated eagerly, even if the condition is false
|
error: this transmute is always evaluated eagerly, even if the condition is false
|
||||||
--> tests/ui/eager_transmute.rs:96:86
|
--> tests/ui/eager_transmute.rs:96:86
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
LL | let _: Option<NonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
|
||||||
help: consider using `bool::then` to only transmute if the condition holds
|
help: consider using `bool::then` to only transmute if the condition holds
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
LL | let _: Option<NonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
||||||
| ~~~~ ++
|
| ~~~~ ++
|
||||||
|
|
||||||
error: this transmute is always evaluated eagerly, even if the condition is false
|
error: this transmute is always evaluated eagerly, even if the condition is false
|
||||||
--> tests/ui/eager_transmute.rs:102:93
|
--> tests/ui/eager_transmute.rs:102:93
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonZeroNonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
LL | let _: Option<NonZeroNonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then_some(unsafe { std::mem::transmute(v2) });
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
|
||||||
help: consider using `bool::then` to only transmute if the condition holds
|
help: consider using `bool::then` to only transmute if the condition holds
|
||||||
|
|
|
|
||||||
LL | let _: Option<NonZeroNonMaxU8> = (v2 < NonZeroU8::new(255).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
LL | let _: Option<NonZeroNonMaxU8> = (v2 < NonZero::new(255u8).unwrap()).then(|| unsafe { std::mem::transmute(v2) });
|
||||||
| ~~~~ ++
|
| ~~~~ ++
|
||||||
|
|
||||||
error: aborting due to 17 previous errors
|
error: aborting due to 17 previous errors
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
#![warn(clippy::transmute_int_to_non_zero)]
|
#![warn(clippy::transmute_int_to_non_zero)]
|
||||||
#![allow(clippy::missing_transmute_annotations)]
|
#![allow(clippy::missing_transmute_annotations)]
|
||||||
|
|
||||||
use core::num::*;
|
use core::num::NonZero;
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let int_u8: u8 = 1;
|
let int_u8: u8 = 1;
|
||||||
@ -16,38 +16,38 @@ fn main() {
|
|||||||
let int_i64: i64 = 1;
|
let int_i64: i64 = 1;
|
||||||
let int_i128: i128 = 1;
|
let int_i128: i128 = 1;
|
||||||
|
|
||||||
let _: NonZeroU8 = unsafe { NonZeroU8::new_unchecked(int_u8) };
|
let _: NonZero<u8> = unsafe { NonZero::new_unchecked(int_u8) };
|
||||||
//~^ ERROR: transmute from a `u8` to a `NonZeroU8`
|
//~^ ERROR: transmute from a `u8` to a `NonZero<u8>`
|
||||||
//~| NOTE: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
//~| NOTE: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
||||||
let _: NonZeroU16 = unsafe { NonZeroU16::new_unchecked(int_u16) };
|
let _: NonZero<u16> = unsafe { NonZero::new_unchecked(int_u16) };
|
||||||
//~^ ERROR: transmute from a `u16` to a `NonZeroU16`
|
//~^ ERROR: transmute from a `u16` to a `NonZero<u16>`
|
||||||
let _: NonZeroU32 = unsafe { NonZeroU32::new_unchecked(int_u32) };
|
let _: NonZero<u32> = unsafe { NonZero::new_unchecked(int_u32) };
|
||||||
//~^ ERROR: transmute from a `u32` to a `NonZeroU32`
|
//~^ ERROR: transmute from a `u32` to a `NonZero<u32>`
|
||||||
let _: NonZeroU64 = unsafe { NonZeroU64::new_unchecked(int_u64) };
|
let _: NonZero<u64> = unsafe { NonZero::new_unchecked(int_u64) };
|
||||||
//~^ ERROR: transmute from a `u64` to a `NonZeroU64`
|
//~^ ERROR: transmute from a `u64` to a `NonZero<u64>`
|
||||||
let _: NonZeroU128 = unsafe { NonZeroU128::new_unchecked(int_u128) };
|
let _: NonZero<u128> = unsafe { NonZero::new_unchecked(int_u128) };
|
||||||
//~^ ERROR: transmute from a `u128` to a `NonZeroU128`
|
//~^ ERROR: transmute from a `u128` to a `NonZero<u128>`
|
||||||
|
|
||||||
let _: NonZeroI8 = unsafe { NonZeroI8::new_unchecked(int_i8) };
|
let _: NonZero<i8> = unsafe { NonZero::new_unchecked(int_i8) };
|
||||||
//~^ ERROR: transmute from a `i8` to a `NonZeroI8`
|
//~^ ERROR: transmute from a `i8` to a `NonZero<i8>`
|
||||||
let _: NonZeroI16 = unsafe { NonZeroI16::new_unchecked(int_i16) };
|
let _: NonZero<i16> = unsafe { NonZero::new_unchecked(int_i16) };
|
||||||
//~^ ERROR: transmute from a `i16` to a `NonZeroI16`
|
//~^ ERROR: transmute from a `i16` to a `NonZero<i16>`
|
||||||
let _: NonZeroI32 = unsafe { NonZeroI32::new_unchecked(int_i32) };
|
let _: NonZero<i32> = unsafe { NonZero::new_unchecked(int_i32) };
|
||||||
//~^ ERROR: transmute from a `i32` to a `NonZeroI32`
|
//~^ ERROR: transmute from a `i32` to a `NonZero<i32>`
|
||||||
let _: NonZeroI64 = unsafe { NonZeroI64::new_unchecked(int_i64) };
|
let _: NonZero<i64> = unsafe { NonZero::new_unchecked(int_i64) };
|
||||||
//~^ ERROR: transmute from a `i64` to a `NonZeroI64`
|
//~^ ERROR: transmute from a `i64` to a `NonZero<i64>`
|
||||||
let _: NonZeroI128 = unsafe { NonZeroI128::new_unchecked(int_i128) };
|
let _: NonZero<i128> = unsafe { NonZero::new_unchecked(int_i128) };
|
||||||
//~^ ERROR: transmute from a `i128` to a `NonZeroI128`
|
//~^ ERROR: transmute from a `i128` to a `NonZero<i128>`
|
||||||
|
|
||||||
let _: NonZeroU8 = unsafe { NonZeroU8::new_unchecked(int_u8) };
|
let _: NonZero<u8> = unsafe { NonZero::new_unchecked(int_u8) };
|
||||||
let _: NonZeroU16 = unsafe { NonZeroU16::new_unchecked(int_u16) };
|
let _: NonZero<u16> = unsafe { NonZero::new_unchecked(int_u16) };
|
||||||
let _: NonZeroU32 = unsafe { NonZeroU32::new_unchecked(int_u32) };
|
let _: NonZero<u32> = unsafe { NonZero::new_unchecked(int_u32) };
|
||||||
let _: NonZeroU64 = unsafe { NonZeroU64::new_unchecked(int_u64) };
|
let _: NonZero<u64> = unsafe { NonZero::new_unchecked(int_u64) };
|
||||||
let _: NonZeroU128 = unsafe { NonZeroU128::new_unchecked(int_u128) };
|
let _: NonZero<u128> = unsafe { NonZero::new_unchecked(int_u128) };
|
||||||
|
|
||||||
let _: NonZeroI8 = unsafe { NonZeroI8::new_unchecked(int_i8) };
|
let _: NonZero<i8> = unsafe { NonZero::new_unchecked(int_i8) };
|
||||||
let _: NonZeroI16 = unsafe { NonZeroI16::new_unchecked(int_i16) };
|
let _: NonZero<i16> = unsafe { NonZero::new_unchecked(int_i16) };
|
||||||
let _: NonZeroI32 = unsafe { NonZeroI32::new_unchecked(int_i32) };
|
let _: NonZero<i32> = unsafe { NonZero::new_unchecked(int_i32) };
|
||||||
let _: NonZeroI64 = unsafe { NonZeroI64::new_unchecked(int_i64) };
|
let _: NonZero<i64> = unsafe { NonZero::new_unchecked(int_i64) };
|
||||||
let _: NonZeroI128 = unsafe { NonZeroI128::new_unchecked(int_i128) };
|
let _: NonZero<i128> = unsafe { NonZero::new_unchecked(int_i128) };
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
#![warn(clippy::transmute_int_to_non_zero)]
|
#![warn(clippy::transmute_int_to_non_zero)]
|
||||||
#![allow(clippy::missing_transmute_annotations)]
|
#![allow(clippy::missing_transmute_annotations)]
|
||||||
|
|
||||||
use core::num::*;
|
use core::num::NonZero;
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let int_u8: u8 = 1;
|
let int_u8: u8 = 1;
|
||||||
@ -16,38 +16,38 @@ fn main() {
|
|||||||
let int_i64: i64 = 1;
|
let int_i64: i64 = 1;
|
||||||
let int_i128: i128 = 1;
|
let int_i128: i128 = 1;
|
||||||
|
|
||||||
let _: NonZeroU8 = unsafe { std::mem::transmute(int_u8) };
|
let _: NonZero<u8> = unsafe { std::mem::transmute(int_u8) };
|
||||||
//~^ ERROR: transmute from a `u8` to a `NonZeroU8`
|
//~^ ERROR: transmute from a `u8` to a `NonZero<u8>`
|
||||||
//~| NOTE: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
//~| NOTE: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
||||||
let _: NonZeroU16 = unsafe { std::mem::transmute(int_u16) };
|
let _: NonZero<u16> = unsafe { std::mem::transmute(int_u16) };
|
||||||
//~^ ERROR: transmute from a `u16` to a `NonZeroU16`
|
//~^ ERROR: transmute from a `u16` to a `NonZero<u16>`
|
||||||
let _: NonZeroU32 = unsafe { std::mem::transmute(int_u32) };
|
let _: NonZero<u32> = unsafe { std::mem::transmute(int_u32) };
|
||||||
//~^ ERROR: transmute from a `u32` to a `NonZeroU32`
|
//~^ ERROR: transmute from a `u32` to a `NonZero<u32>`
|
||||||
let _: NonZeroU64 = unsafe { std::mem::transmute(int_u64) };
|
let _: NonZero<u64> = unsafe { std::mem::transmute(int_u64) };
|
||||||
//~^ ERROR: transmute from a `u64` to a `NonZeroU64`
|
//~^ ERROR: transmute from a `u64` to a `NonZero<u64>`
|
||||||
let _: NonZeroU128 = unsafe { std::mem::transmute(int_u128) };
|
let _: NonZero<u128> = unsafe { std::mem::transmute(int_u128) };
|
||||||
//~^ ERROR: transmute from a `u128` to a `NonZeroU128`
|
//~^ ERROR: transmute from a `u128` to a `NonZero<u128>`
|
||||||
|
|
||||||
let _: NonZeroI8 = unsafe { std::mem::transmute(int_i8) };
|
let _: NonZero<i8> = unsafe { std::mem::transmute(int_i8) };
|
||||||
//~^ ERROR: transmute from a `i8` to a `NonZeroI8`
|
//~^ ERROR: transmute from a `i8` to a `NonZero<i8>`
|
||||||
let _: NonZeroI16 = unsafe { std::mem::transmute(int_i16) };
|
let _: NonZero<i16> = unsafe { std::mem::transmute(int_i16) };
|
||||||
//~^ ERROR: transmute from a `i16` to a `NonZeroI16`
|
//~^ ERROR: transmute from a `i16` to a `NonZero<i16>`
|
||||||
let _: NonZeroI32 = unsafe { std::mem::transmute(int_i32) };
|
let _: NonZero<i32> = unsafe { std::mem::transmute(int_i32) };
|
||||||
//~^ ERROR: transmute from a `i32` to a `NonZeroI32`
|
//~^ ERROR: transmute from a `i32` to a `NonZero<i32>`
|
||||||
let _: NonZeroI64 = unsafe { std::mem::transmute(int_i64) };
|
let _: NonZero<i64> = unsafe { std::mem::transmute(int_i64) };
|
||||||
//~^ ERROR: transmute from a `i64` to a `NonZeroI64`
|
//~^ ERROR: transmute from a `i64` to a `NonZero<i64>`
|
||||||
let _: NonZeroI128 = unsafe { std::mem::transmute(int_i128) };
|
let _: NonZero<i128> = unsafe { std::mem::transmute(int_i128) };
|
||||||
//~^ ERROR: transmute from a `i128` to a `NonZeroI128`
|
//~^ ERROR: transmute from a `i128` to a `NonZero<i128>`
|
||||||
|
|
||||||
let _: NonZeroU8 = unsafe { NonZeroU8::new_unchecked(int_u8) };
|
let _: NonZero<u8> = unsafe { NonZero::new_unchecked(int_u8) };
|
||||||
let _: NonZeroU16 = unsafe { NonZeroU16::new_unchecked(int_u16) };
|
let _: NonZero<u16> = unsafe { NonZero::new_unchecked(int_u16) };
|
||||||
let _: NonZeroU32 = unsafe { NonZeroU32::new_unchecked(int_u32) };
|
let _: NonZero<u32> = unsafe { NonZero::new_unchecked(int_u32) };
|
||||||
let _: NonZeroU64 = unsafe { NonZeroU64::new_unchecked(int_u64) };
|
let _: NonZero<u64> = unsafe { NonZero::new_unchecked(int_u64) };
|
||||||
let _: NonZeroU128 = unsafe { NonZeroU128::new_unchecked(int_u128) };
|
let _: NonZero<u128> = unsafe { NonZero::new_unchecked(int_u128) };
|
||||||
|
|
||||||
let _: NonZeroI8 = unsafe { NonZeroI8::new_unchecked(int_i8) };
|
let _: NonZero<i8> = unsafe { NonZero::new_unchecked(int_i8) };
|
||||||
let _: NonZeroI16 = unsafe { NonZeroI16::new_unchecked(int_i16) };
|
let _: NonZero<i16> = unsafe { NonZero::new_unchecked(int_i16) };
|
||||||
let _: NonZeroI32 = unsafe { NonZeroI32::new_unchecked(int_i32) };
|
let _: NonZero<i32> = unsafe { NonZero::new_unchecked(int_i32) };
|
||||||
let _: NonZeroI64 = unsafe { NonZeroI64::new_unchecked(int_i64) };
|
let _: NonZero<i64> = unsafe { NonZero::new_unchecked(int_i64) };
|
||||||
let _: NonZeroI128 = unsafe { NonZeroI128::new_unchecked(int_i128) };
|
let _: NonZero<i128> = unsafe { NonZero::new_unchecked(int_i128) };
|
||||||
}
|
}
|
||||||
|
@ -1,65 +1,65 @@
|
|||||||
error: transmute from a `u8` to a `NonZeroU8`
|
error: transmute from a `u8` to a `NonZero<u8>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:19:33
|
--> tests/ui/transmute_int_to_non_zero.rs:19:35
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroU8 = unsafe { std::mem::transmute(int_u8) };
|
LL | let _: NonZero<u8> = unsafe { std::mem::transmute(int_u8) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroU8::new_unchecked(int_u8)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_u8)`
|
||||||
|
|
|
|
||||||
= note: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
= note: `-D clippy::transmute-int-to-non-zero` implied by `-D warnings`
|
||||||
= help: to override `-D warnings` add `#[allow(clippy::transmute_int_to_non_zero)]`
|
= help: to override `-D warnings` add `#[allow(clippy::transmute_int_to_non_zero)]`
|
||||||
|
|
||||||
error: transmute from a `u16` to a `NonZeroU16`
|
error: transmute from a `u16` to a `NonZero<u16>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:22:34
|
--> tests/ui/transmute_int_to_non_zero.rs:22:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroU16 = unsafe { std::mem::transmute(int_u16) };
|
LL | let _: NonZero<u16> = unsafe { std::mem::transmute(int_u16) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroU16::new_unchecked(int_u16)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_u16)`
|
||||||
|
|
||||||
error: transmute from a `u32` to a `NonZeroU32`
|
error: transmute from a `u32` to a `NonZero<u32>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:24:34
|
--> tests/ui/transmute_int_to_non_zero.rs:24:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroU32 = unsafe { std::mem::transmute(int_u32) };
|
LL | let _: NonZero<u32> = unsafe { std::mem::transmute(int_u32) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroU32::new_unchecked(int_u32)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_u32)`
|
||||||
|
|
||||||
error: transmute from a `u64` to a `NonZeroU64`
|
error: transmute from a `u64` to a `NonZero<u64>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:26:34
|
--> tests/ui/transmute_int_to_non_zero.rs:26:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroU64 = unsafe { std::mem::transmute(int_u64) };
|
LL | let _: NonZero<u64> = unsafe { std::mem::transmute(int_u64) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroU64::new_unchecked(int_u64)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_u64)`
|
||||||
|
|
||||||
error: transmute from a `u128` to a `NonZeroU128`
|
error: transmute from a `u128` to a `NonZero<u128>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:28:35
|
--> tests/ui/transmute_int_to_non_zero.rs:28:37
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroU128 = unsafe { std::mem::transmute(int_u128) };
|
LL | let _: NonZero<u128> = unsafe { std::mem::transmute(int_u128) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroU128::new_unchecked(int_u128)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_u128)`
|
||||||
|
|
||||||
error: transmute from a `i8` to a `NonZeroI8`
|
error: transmute from a `i8` to a `NonZero<i8>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:31:33
|
--> tests/ui/transmute_int_to_non_zero.rs:31:35
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroI8 = unsafe { std::mem::transmute(int_i8) };
|
LL | let _: NonZero<i8> = unsafe { std::mem::transmute(int_i8) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroI8::new_unchecked(int_i8)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_i8)`
|
||||||
|
|
||||||
error: transmute from a `i16` to a `NonZeroI16`
|
error: transmute from a `i16` to a `NonZero<i16>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:33:34
|
--> tests/ui/transmute_int_to_non_zero.rs:33:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroI16 = unsafe { std::mem::transmute(int_i16) };
|
LL | let _: NonZero<i16> = unsafe { std::mem::transmute(int_i16) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroI16::new_unchecked(int_i16)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_i16)`
|
||||||
|
|
||||||
error: transmute from a `i32` to a `NonZeroI32`
|
error: transmute from a `i32` to a `NonZero<i32>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:35:34
|
--> tests/ui/transmute_int_to_non_zero.rs:35:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroI32 = unsafe { std::mem::transmute(int_i32) };
|
LL | let _: NonZero<i32> = unsafe { std::mem::transmute(int_i32) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroI32::new_unchecked(int_i32)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_i32)`
|
||||||
|
|
||||||
error: transmute from a `i64` to a `NonZeroI64`
|
error: transmute from a `i64` to a `NonZero<i64>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:37:34
|
--> tests/ui/transmute_int_to_non_zero.rs:37:36
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroI64 = unsafe { std::mem::transmute(int_i64) };
|
LL | let _: NonZero<i64> = unsafe { std::mem::transmute(int_i64) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroI64::new_unchecked(int_i64)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_i64)`
|
||||||
|
|
||||||
error: transmute from a `i128` to a `NonZeroI128`
|
error: transmute from a `i128` to a `NonZero<i128>`
|
||||||
--> tests/ui/transmute_int_to_non_zero.rs:39:35
|
--> tests/ui/transmute_int_to_non_zero.rs:39:37
|
||||||
|
|
|
|
||||||
LL | let _: NonZeroI128 = unsafe { std::mem::transmute(int_i128) };
|
LL | let _: NonZero<i128> = unsafe { std::mem::transmute(int_i128) };
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZeroI128::new_unchecked(int_i128)`
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: consider using: `NonZero::new_unchecked(int_i128)`
|
||||||
|
|
||||||
error: aborting due to 10 previous errors
|
error: aborting due to 10 previous errors
|
||||||
|
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use crate::rustc_middle::ty::layout::LayoutOf as _;
|
|
||||||
use rustc_middle::mir;
|
use rustc_middle::mir;
|
||||||
|
use rustc_middle::ty::layout::LayoutOf as _;
|
||||||
use rustc_middle::ty::Ty;
|
use rustc_middle::ty::Ty;
|
||||||
use rustc_span::Symbol;
|
use rustc_span::Symbol;
|
||||||
use rustc_target::spec::abi::Abi;
|
use rustc_target::spec::abi::Abi;
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
#![feature(custom_mir)]
|
#![feature(custom_mir)]
|
||||||
|
|
||||||
use std::intrinsics::mir::*;
|
use std::intrinsics::mir::*;
|
||||||
use std::num::NonZeroI32;
|
use std::num::NonZero;
|
||||||
|
|
||||||
// We define our own option type so that we can control the variant indices.
|
// We define our own option type so that we can control the variant indices.
|
||||||
#[allow(unused)]
|
#[allow(unused)]
|
||||||
@ -13,7 +13,7 @@ enum Option<T> {
|
|||||||
use Option::*;
|
use Option::*;
|
||||||
|
|
||||||
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
||||||
fn set_discriminant(ptr: &mut Option<NonZeroI32>) {
|
fn set_discriminant(ptr: &mut Option<NonZero<i32>>) {
|
||||||
mir! {
|
mir! {
|
||||||
{
|
{
|
||||||
// We set the discriminant to `Some`, which is a NOP since this is the niched variant.
|
// We set the discriminant to `Some`, which is a NOP since this is the niched variant.
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use std::num::*;
|
use std::num::NonZero;
|
||||||
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
struct S1(NonZeroI32);
|
struct S1(NonZero<i32>);
|
||||||
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
struct S2(i32);
|
struct S2(i32);
|
||||||
@ -11,6 +11,6 @@ fn callee(_s: S2) {}
|
|||||||
fn main() {
|
fn main() {
|
||||||
let fnptr: fn(S2) = callee;
|
let fnptr: fn(S2) = callee;
|
||||||
let fnptr: fn(S1) = unsafe { std::mem::transmute(fnptr) };
|
let fnptr: fn(S1) = unsafe { std::mem::transmute(fnptr) };
|
||||||
fnptr(S1(NonZeroI32::new(1).unwrap()));
|
fnptr(S1(NonZero::new(1).unwrap()));
|
||||||
//~^ ERROR: calling a function with argument of type S2 passing data of type S1
|
//~^ ERROR: calling a function with argument of type S2 passing data of type S1
|
||||||
}
|
}
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
error: Undefined Behavior: calling a function with argument of type S2 passing data of type S1
|
error: Undefined Behavior: calling a function with argument of type S2 passing data of type S1
|
||||||
--> $DIR/abi_mismatch_repr_C.rs:LL:CC
|
--> $DIR/abi_mismatch_repr_C.rs:LL:CC
|
||||||
|
|
|
|
||||||
LL | fnptr(S1(NonZeroI32::new(1).unwrap()));
|
LL | fnptr(S1(NonZero::new(1).unwrap()));
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ calling a function with argument of type S2 passing data of type S1
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ calling a function with argument of type S2 passing data of type S1
|
||||||
|
|
|
|
||||||
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
|
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
|
||||||
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
|
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
|
||||||
|
@ -2,15 +2,15 @@
|
|||||||
#![feature(core_intrinsics, custom_mir)]
|
#![feature(core_intrinsics, custom_mir)]
|
||||||
|
|
||||||
use std::intrinsics::mir::*;
|
use std::intrinsics::mir::*;
|
||||||
use std::num::NonZeroU32;
|
use std::num::NonZero;
|
||||||
use std::ptr;
|
use std::ptr;
|
||||||
|
|
||||||
// This function supposedly returns a NonZeroU32, but actually returns something invalid in a way that
|
// This function supposedly returns a `NonZero<u32>`, but actually returns something invalid in a way that
|
||||||
// never materializes a bad NonZeroU32 value: we take a pointer to the return place and cast the pointer
|
// never materializes a bad `NonZero<u32>` value: we take a pointer to the return place and cast the pointer
|
||||||
// type. That way we never get an "invalid value constructed" error inside the function, it can
|
// type. That way we never get an "invalid value constructed" error inside the function, it can
|
||||||
// only possibly be detected when the return value is passed to the caller.
|
// only possibly be detected when the return value is passed to the caller.
|
||||||
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
||||||
fn f() -> NonZeroU32 {
|
fn f() -> NonZero<u32> {
|
||||||
mir! {
|
mir! {
|
||||||
{
|
{
|
||||||
let tmp = ptr::addr_of_mut!(RET);
|
let tmp = ptr::addr_of_mut!(RET);
|
||||||
@ -22,7 +22,7 @@ fn f() -> NonZeroU32 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let f: fn() -> u32 = unsafe { std::mem::transmute(f as fn() -> NonZeroU32) };
|
let f: fn() -> u32 = unsafe { std::mem::transmute(f as fn() -> NonZero<u32>) };
|
||||||
// There's a NonZeroU32-to-u32 transmute happening here
|
// There's a `NonZero<u32>` to `u32` transmute happening here.
|
||||||
f(); //~ERROR: expected something greater or equal to 1
|
f(); //~ERROR: expected something greater or equal to 1
|
||||||
}
|
}
|
||||||
|
@ -2,24 +2,24 @@
|
|||||||
#![feature(core_intrinsics, custom_mir)]
|
#![feature(core_intrinsics, custom_mir)]
|
||||||
|
|
||||||
use std::intrinsics::mir::*;
|
use std::intrinsics::mir::*;
|
||||||
use std::num::NonZeroU32;
|
use std::num::NonZero;
|
||||||
use std::ptr;
|
use std::ptr;
|
||||||
|
|
||||||
fn f(c: u32) {
|
fn f(c: u32) {
|
||||||
println!("{c}");
|
println!("{c}");
|
||||||
}
|
}
|
||||||
|
|
||||||
// Call that function in a bad way, with an invalid NonZeroU32, but without
|
// Call that function in a bad way, with an invalid `NonZero<u32>`, but without
|
||||||
// ever materializing this as a NonZeroU32 value outside the call itself.
|
// ever materializing this as a `NonZero<u32>` value outside the call itself.
|
||||||
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
#[custom_mir(dialect = "runtime", phase = "optimized")]
|
||||||
fn call(f: fn(NonZeroU32)) {
|
fn call(f: fn(NonZero<u32>)) {
|
||||||
mir! {
|
mir! {
|
||||||
let _res: ();
|
let _res: ();
|
||||||
{
|
{
|
||||||
let c = 0;
|
let c = 0;
|
||||||
let tmp = ptr::addr_of!(c);
|
let tmp = ptr::addr_of!(c);
|
||||||
let ptr = tmp as *const NonZeroU32;
|
let ptr = tmp as *const NonZero<u32>;
|
||||||
// The call site now is a NonZeroU32-to-u32 transmute.
|
// The call site now is a `NonZero<u32>` to `u32` transmute.
|
||||||
Call(_res = f(*ptr), ReturnTo(retblock), UnwindContinue()) //~ERROR: expected something greater or equal to 1
|
Call(_res = f(*ptr), ReturnTo(retblock), UnwindContinue()) //~ERROR: expected something greater or equal to 1
|
||||||
}
|
}
|
||||||
retblock = {
|
retblock = {
|
||||||
@ -29,6 +29,6 @@ fn call(f: fn(NonZeroU32)) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let f: fn(NonZeroU32) = unsafe { std::mem::transmute(f as fn(u32)) };
|
let f: fn(NonZero<u32>) = unsafe { std::mem::transmute(f as fn(u32)) };
|
||||||
call(f);
|
call(f);
|
||||||
}
|
}
|
||||||
|
@ -70,7 +70,7 @@ fn main() {
|
|||||||
test_abi_compat(0usize, 0u64);
|
test_abi_compat(0usize, 0u64);
|
||||||
test_abi_compat(0isize, 0i64);
|
test_abi_compat(0isize, 0i64);
|
||||||
}
|
}
|
||||||
test_abi_compat(42u32, num::NonZeroU32::new(1).unwrap());
|
test_abi_compat(42u32, num::NonZero::new(1u32).unwrap());
|
||||||
// - `char` and `u32`.
|
// - `char` and `u32`.
|
||||||
test_abi_compat(42u32, 'x');
|
test_abi_compat(42u32, 'x');
|
||||||
// - Reference/pointer types with the same pointee.
|
// - Reference/pointer types with the same pointee.
|
||||||
@ -86,9 +86,9 @@ fn main() {
|
|||||||
// - Guaranteed null-pointer-optimizations (RFC 3391).
|
// - Guaranteed null-pointer-optimizations (RFC 3391).
|
||||||
test_abi_compat(&0u32 as *const u32, Some(&0u32));
|
test_abi_compat(&0u32 as *const u32, Some(&0u32));
|
||||||
test_abi_compat(main as fn(), Some(main as fn()));
|
test_abi_compat(main as fn(), Some(main as fn()));
|
||||||
test_abi_compat(0u32, Some(num::NonZeroU32::new(1).unwrap()));
|
test_abi_compat(0u32, Some(num::NonZero::new(1u32).unwrap()));
|
||||||
test_abi_compat(&0u32 as *const u32, Some(Wrapper(&0u32)));
|
test_abi_compat(&0u32 as *const u32, Some(Wrapper(&0u32)));
|
||||||
test_abi_compat(0u32, Some(Wrapper(num::NonZeroU32::new(1).unwrap())));
|
test_abi_compat(0u32, Some(Wrapper(num::NonZero::new(1u32).unwrap())));
|
||||||
|
|
||||||
// These must work for *any* type, since we guarantee that `repr(transparent)` is ABI-compatible
|
// These must work for *any* type, since we guarantee that `repr(transparent)` is ABI-compatible
|
||||||
// with the wrapped field.
|
// with the wrapped field.
|
||||||
@ -102,7 +102,7 @@ fn main() {
|
|||||||
test_abi_newtype::<[u32; 2]>();
|
test_abi_newtype::<[u32; 2]>();
|
||||||
test_abi_newtype::<[u32; 32]>();
|
test_abi_newtype::<[u32; 32]>();
|
||||||
test_abi_newtype::<Option<i32>>();
|
test_abi_newtype::<Option<i32>>();
|
||||||
test_abi_newtype::<Option<num::NonZeroU32>>();
|
test_abi_newtype::<Option<num::NonZero<u32>>>();
|
||||||
|
|
||||||
// Extra test for assumptions made by arbitrary-self-dyn-receivers.
|
// Extra test for assumptions made by arbitrary-self-dyn-receivers.
|
||||||
// This is interesting since these types are not `repr(transparent)`. So this is not part of our
|
// This is interesting since these types are not `repr(transparent)`. So this is not part of our
|
||||||
|
@ -1,8 +1,8 @@
|
|||||||
//@compile-flags: -Zmiri-num-cpus=1024
|
//@compile-flags: -Zmiri-num-cpus=1024
|
||||||
|
|
||||||
use std::num::NonZeroUsize;
|
use std::num::NonZero;
|
||||||
use std::thread::available_parallelism;
|
use std::thread::available_parallelism;
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
assert_eq!(available_parallelism().unwrap(), NonZeroUsize::new(1024).unwrap());
|
assert_eq!(available_parallelism().unwrap(), NonZero::new(1024).unwrap());
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use std::ffi::OsString;
|
use std::ffi::OsString;
|
||||||
use std::num::NonZeroUsize;
|
use std::num::NonZero;
|
||||||
use std::path::{Path, PathBuf};
|
use std::path::{Path, PathBuf};
|
||||||
use std::sync::OnceLock;
|
use std::sync::OnceLock;
|
||||||
use std::{env, process::Command};
|
use std::{env, process::Command};
|
||||||
@ -76,7 +76,7 @@ fn miri_config(target: &str, path: &str, mode: Mode, with_dependencies: bool) ->
|
|||||||
edition: Some("2021".into()), // keep in sync with `./miri run`
|
edition: Some("2021".into()), // keep in sync with `./miri run`
|
||||||
threads: std::env::var("MIRI_TEST_THREADS")
|
threads: std::env::var("MIRI_TEST_THREADS")
|
||||||
.ok()
|
.ok()
|
||||||
.map(|threads| NonZeroUsize::new(threads.parse().unwrap()).unwrap()),
|
.map(|threads| NonZero::new(threads.parse().unwrap()).unwrap()),
|
||||||
..Config::rustc(path)
|
..Config::rustc(path)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -458,7 +458,9 @@ impl UseTree {
|
|||||||
version,
|
version,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
UseTreeKind::Nested(ref list) => {
|
UseTreeKind::Nested {
|
||||||
|
items: ref list, ..
|
||||||
|
} => {
|
||||||
// Extract comments between nested use items.
|
// Extract comments between nested use items.
|
||||||
// This needs to be done before sorting use items.
|
// This needs to be done before sorting use items.
|
||||||
let items = itemize_list(
|
let items = itemize_list(
|
||||||
|
7
tests/crashes/124436.rs
Normal file
7
tests/crashes/124436.rs
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124436
|
||||||
|
//@ compile-flags: -Zdump-mir=all -Zpolymorphize=on
|
||||||
|
|
||||||
|
pub trait TraitCat {}
|
||||||
|
pub trait TraitDog {}
|
||||||
|
|
||||||
|
pub fn gamma<T: TraitCat + TraitDog>(t: [TraitDog; 32]) {}
|
23
tests/crashes/124440.rs
Normal file
23
tests/crashes/124440.rs
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124440
|
||||||
|
|
||||||
|
#![allow(warnings)]
|
||||||
|
|
||||||
|
trait Foo {}
|
||||||
|
|
||||||
|
impl<F> Foo for F where F: FnMut(&()) {}
|
||||||
|
|
||||||
|
struct Bar<F> {
|
||||||
|
f: F,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<F> Foo for Bar<F> where F: Foo {}
|
||||||
|
|
||||||
|
fn assert_foo<F>(_: F)
|
||||||
|
where
|
||||||
|
Bar<F>: Foo,
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
assert_foo(|_| ());
|
||||||
|
}
|
17
tests/crashes/124464.rs
Normal file
17
tests/crashes/124464.rs
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
//@ known-bug: rust-lang/rust #124464
|
||||||
|
enum TestOption<T> {
|
||||||
|
TestSome(T),
|
||||||
|
TestSome(T),
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct Request {
|
||||||
|
bar: TestOption<u64>,
|
||||||
|
bar: u8,
|
||||||
|
}
|
||||||
|
|
||||||
|
fn default_instance() -> &'static Request {
|
||||||
|
static instance: Request = Request { bar: 17 };
|
||||||
|
&instance
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn main() {}
|
16
tests/crashes/124490.rs
Normal file
16
tests/crashes/124490.rs
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124490
|
||||||
|
use io::{self as std};
|
||||||
|
use std::collections::{self as io};
|
||||||
|
|
||||||
|
mod a {
|
||||||
|
pub mod b {
|
||||||
|
pub mod c {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
use a::*;
|
||||||
|
|
||||||
|
use b::c;
|
||||||
|
use c as b;
|
||||||
|
|
||||||
|
fn main() {}
|
12
tests/crashes/124552.rs
Normal file
12
tests/crashes/124552.rs
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124552
|
||||||
|
|
||||||
|
struct B;
|
||||||
|
|
||||||
|
struct Foo {
|
||||||
|
b: u32,
|
||||||
|
b: B,
|
||||||
|
}
|
||||||
|
|
||||||
|
static BAR: Foo = Foo { b: B };
|
||||||
|
|
||||||
|
fn main() {}
|
46
tests/crashes/124563.rs
Normal file
46
tests/crashes/124563.rs
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124563
|
||||||
|
|
||||||
|
use std::marker::PhantomData;
|
||||||
|
|
||||||
|
pub trait Trait {}
|
||||||
|
|
||||||
|
pub trait Foo {
|
||||||
|
type Trait: Trait;
|
||||||
|
type Bar: Bar;
|
||||||
|
fn foo(&mut self);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct FooImpl<'a, 'b, A: Trait>(PhantomData<&'a &'b A>);
|
||||||
|
|
||||||
|
impl<'a, 'b, T> Foo for FooImpl<'a, 'b, T>
|
||||||
|
where
|
||||||
|
T: Trait,
|
||||||
|
{
|
||||||
|
type Trait = T;
|
||||||
|
type Bar = BarImpl<'a, 'b, T>;
|
||||||
|
|
||||||
|
fn foo(&mut self) {
|
||||||
|
self.enter_scope(|ctx| {
|
||||||
|
BarImpl(ctx);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a, 'b, T> FooImpl<'a, 'b, T>
|
||||||
|
where
|
||||||
|
T: Trait,
|
||||||
|
{
|
||||||
|
fn enter_scope(&mut self, _scope: impl FnOnce(&mut Self)) {}
|
||||||
|
}
|
||||||
|
pub trait Bar {
|
||||||
|
type Foo: Foo;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct BarImpl<'a, 'b, T: Trait>(&'b mut FooImpl<'a, 'b, T>);
|
||||||
|
|
||||||
|
impl<'a, 'b, T> Bar for BarImpl<'a, 'b, T>
|
||||||
|
where
|
||||||
|
T: Trait,
|
||||||
|
{
|
||||||
|
type Foo = FooImpl<'a, 'b, T>;
|
||||||
|
}
|
5
tests/crashes/124583.rs
Normal file
5
tests/crashes/124583.rs
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124583
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let _ = -(-0.0f16);
|
||||||
|
}
|
14
tests/crashes/124702.rs
Normal file
14
tests/crashes/124702.rs
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124702
|
||||||
|
//@ compile-flags: -Znext-solver=coherence
|
||||||
|
trait X {}
|
||||||
|
|
||||||
|
trait Z {
|
||||||
|
type Assoc: Y;
|
||||||
|
}
|
||||||
|
struct A<T>(T);
|
||||||
|
|
||||||
|
impl<T: X> Z for A<T> {
|
||||||
|
type Assoc = T;
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<T> From<<A<A<T>> as Z>::Assoc> for T {}
|
8
tests/crashes/124751.rs
Normal file
8
tests/crashes/124751.rs
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
//@ known-bug: rust-lang/rust#124751
|
||||||
|
//@ compile-flags: -Zunstable-options --edition=2024
|
||||||
|
|
||||||
|
#![feature(gen_blocks)]
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let _ = async gen || {};
|
||||||
|
}
|
@ -99,7 +99,7 @@ fn check_result(abi: &ArgAbi) {
|
|||||||
assert_matches!(layout.variants, VariantsShape::Multiple { .. })
|
assert_matches!(layout.variants, VariantsShape::Multiple { .. })
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Check the niche information about: `NonZeroU8`
|
/// Checks the niche information about `NonZero<u8>`.
|
||||||
fn check_niche(abi: &ArgAbi) {
|
fn check_niche(abi: &ArgAbi) {
|
||||||
assert!(abi.ty.kind().is_struct());
|
assert!(abi.ty.kind().is_struct());
|
||||||
assert_matches!(abi.mode, PassMode::Direct { .. });
|
assert_matches!(abi.mode, PassMode::Direct { .. });
|
||||||
@ -150,12 +150,12 @@ fn generate_input(path: &str) -> std::io::Result<()> {
|
|||||||
#![feature(c_variadic)]
|
#![feature(c_variadic)]
|
||||||
#![allow(unused_variables)]
|
#![allow(unused_variables)]
|
||||||
|
|
||||||
use std::num::NonZeroU8;
|
use std::num::NonZero;
|
||||||
|
|
||||||
pub fn fn_abi(
|
pub fn fn_abi(
|
||||||
ignore: [u8; 0],
|
ignore: [u8; 0],
|
||||||
primitive: char,
|
primitive: char,
|
||||||
niche: NonZeroU8,
|
niche: NonZero<u8>,
|
||||||
) -> Result<usize, &'static str> {{
|
) -> Result<usize, &'static str> {{
|
||||||
// We only care about the signature.
|
// We only care about the signature.
|
||||||
todo!()
|
todo!()
|
||||||
|
@ -1,9 +1,9 @@
|
|||||||
fn main() {
|
fn main() {
|
||||||
let _: std::num::NonZeroU64 = 1;
|
let _: std::num::NonZero<u64> = 1;
|
||||||
//~^ ERROR mismatched types
|
//~^ ERROR mismatched types
|
||||||
//~| HELP consider calling `NonZeroU64::new`
|
//~| HELP consider calling `NonZero::new`
|
||||||
|
|
||||||
let _: Option<std::num::NonZeroU64> = 1;
|
let _: Option<std::num::NonZero<u64>> = 1;
|
||||||
//~^ ERROR mismatched types
|
//~^ ERROR mismatched types
|
||||||
//~| HELP consider calling `NonZeroU64::new`
|
//~| HELP consider calling `NonZero::new`
|
||||||
}
|
}
|
||||||
|
@ -1,32 +1,32 @@
|
|||||||
error[E0308]: mismatched types
|
error[E0308]: mismatched types
|
||||||
--> $DIR/non_zero_assigned_something.rs:2:35
|
--> $DIR/non_zero_assigned_something.rs:2:37
|
||||||
|
|
|
|
||||||
LL | let _: std::num::NonZeroU64 = 1;
|
LL | let _: std::num::NonZero<u64> = 1;
|
||||||
| -------------------- ^ expected `NonZero<u64>`, found integer
|
| ---------------------- ^ expected `NonZero<u64>`, found integer
|
||||||
| |
|
| |
|
||||||
| expected due to this
|
| expected due to this
|
||||||
|
|
|
|
||||||
= note: expected struct `NonZero<u64>`
|
= note: expected struct `NonZero<u64>`
|
||||||
found type `{integer}`
|
found type `{integer}`
|
||||||
help: consider calling `NonZeroU64::new`
|
help: consider calling `NonZero::new`
|
||||||
|
|
|
|
||||||
LL | let _: std::num::NonZeroU64 = NonZeroU64::new(1).unwrap();
|
LL | let _: std::num::NonZero<u64> = NonZero::new(1).unwrap();
|
||||||
| ++++++++++++++++ ++++++++++
|
| +++++++++++++ ++++++++++
|
||||||
|
|
||||||
error[E0308]: mismatched types
|
error[E0308]: mismatched types
|
||||||
--> $DIR/non_zero_assigned_something.rs:6:43
|
--> $DIR/non_zero_assigned_something.rs:6:45
|
||||||
|
|
|
|
||||||
LL | let _: Option<std::num::NonZeroU64> = 1;
|
LL | let _: Option<std::num::NonZero<u64>> = 1;
|
||||||
| ---------------------------- ^ expected `Option<NonZero<u64>>`, found integer
|
| ------------------------------ ^ expected `Option<NonZero<u64>>`, found integer
|
||||||
| |
|
| |
|
||||||
| expected due to this
|
| expected due to this
|
||||||
|
|
|
|
||||||
= note: expected enum `Option<NonZero<u64>>`
|
= note: expected enum `Option<NonZero<u64>>`
|
||||||
found type `{integer}`
|
found type `{integer}`
|
||||||
help: consider calling `NonZeroU64::new`
|
help: consider calling `NonZero::new`
|
||||||
|
|
|
|
||||||
LL | let _: Option<std::num::NonZeroU64> = NonZeroU64::new(1);
|
LL | let _: Option<std::num::NonZero<u64>> = NonZero::new(1);
|
||||||
| ++++++++++++++++ +
|
| +++++++++++++ +
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
|
@ -9,16 +9,14 @@ fn r#async() {} //~ ERROR async
|
|||||||
|
|
||||||
macro_rules! foo {
|
macro_rules! foo {
|
||||||
($foo:ident) => {};
|
($foo:ident) => {};
|
||||||
($r#async:expr, r#async) => {};
|
($async:expr, r#async) => {};
|
||||||
//~^ ERROR async
|
//~^ ERROR async
|
||||||
//~| ERROR async
|
|
||||||
//~| WARN this is accepted in the current edition
|
|
||||||
//~| WARN this is accepted in the current edition
|
//~| WARN this is accepted in the current edition
|
||||||
}
|
}
|
||||||
|
|
||||||
foo!(r#async);
|
foo!(r#async);
|
||||||
//~^ ERROR async
|
//~^ ERROR async
|
||||||
//~| WARN this is accepted in the current edition
|
//~| WARN this is accepted in the current edition
|
||||||
|
|
||||||
mod dont_lint_raw {
|
mod dont_lint_raw {
|
||||||
fn r#async() {}
|
fn r#async() {}
|
||||||
|
@ -11,14 +11,12 @@ macro_rules! foo {
|
|||||||
($foo:ident) => {};
|
($foo:ident) => {};
|
||||||
($async:expr, async) => {};
|
($async:expr, async) => {};
|
||||||
//~^ ERROR async
|
//~^ ERROR async
|
||||||
//~| ERROR async
|
|
||||||
//~| WARN this is accepted in the current edition
|
|
||||||
//~| WARN this is accepted in the current edition
|
//~| WARN this is accepted in the current edition
|
||||||
}
|
}
|
||||||
|
|
||||||
foo!(async);
|
foo!(async);
|
||||||
//~^ ERROR async
|
//~^ ERROR async
|
||||||
//~| WARN this is accepted in the current edition
|
//~| WARN this is accepted in the current edition
|
||||||
|
|
||||||
mod dont_lint_raw {
|
mod dont_lint_raw {
|
||||||
fn r#async() {}
|
fn r#async() {}
|
||||||
|
@ -13,15 +13,6 @@ LL | #![deny(keyword_idents)]
|
|||||||
| ^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^
|
||||||
= note: `#[deny(keyword_idents_2018)]` implied by `#[deny(keyword_idents)]`
|
= note: `#[deny(keyword_idents_2018)]` implied by `#[deny(keyword_idents)]`
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
|
||||||
--> $DIR/async-ident.rs:12:7
|
|
||||||
|
|
|
||||||
LL | ($async:expr, async) => {};
|
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
|
||||||
|
|
|
||||||
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018!
|
|
||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:12:19
|
--> $DIR/async-ident.rs:12:19
|
||||||
|
|
|
|
||||||
@ -32,7 +23,7 @@ LL | ($async:expr, async) => {};
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:19:6
|
--> $DIR/async-ident.rs:17:6
|
||||||
|
|
|
|
||||||
LL | foo!(async);
|
LL | foo!(async);
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -41,7 +32,7 @@ LL | foo!(async);
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:28:11
|
--> $DIR/async-ident.rs:26:11
|
||||||
|
|
|
|
||||||
LL | trait async {}
|
LL | trait async {}
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -50,7 +41,7 @@ LL | trait async {}
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:32:10
|
--> $DIR/async-ident.rs:30:10
|
||||||
|
|
|
|
||||||
LL | impl async for MyStruct {}
|
LL | impl async for MyStruct {}
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -59,7 +50,7 @@ LL | impl async for MyStruct {}
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:38:12
|
--> $DIR/async-ident.rs:36:12
|
||||||
|
|
|
|
||||||
LL | static async: u32 = 0;
|
LL | static async: u32 = 0;
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -68,7 +59,7 @@ LL | static async: u32 = 0;
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:44:11
|
--> $DIR/async-ident.rs:42:11
|
||||||
|
|
|
|
||||||
LL | const async: u32 = 0;
|
LL | const async: u32 = 0;
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -77,7 +68,7 @@ LL | const async: u32 = 0;
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:50:15
|
--> $DIR/async-ident.rs:48:15
|
||||||
|
|
|
|
||||||
LL | impl Foo { fn async() {} }
|
LL | impl Foo { fn async() {} }
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -86,7 +77,7 @@ LL | impl Foo { fn async() {} }
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:55:12
|
--> $DIR/async-ident.rs:53:12
|
||||||
|
|
|
|
||||||
LL | struct async {}
|
LL | struct async {}
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -95,7 +86,7 @@ LL | struct async {}
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:58:9
|
--> $DIR/async-ident.rs:56:9
|
||||||
|
|
|
|
||||||
LL | let async: async = async {};
|
LL | let async: async = async {};
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -104,7 +95,7 @@ LL | let async: async = async {};
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:58:16
|
--> $DIR/async-ident.rs:56:16
|
||||||
|
|
|
|
||||||
LL | let async: async = async {};
|
LL | let async: async = async {};
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -113,7 +104,7 @@ LL | let async: async = async {};
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:58:24
|
--> $DIR/async-ident.rs:56:24
|
||||||
|
|
|
|
||||||
LL | let async: async = async {};
|
LL | let async: async = async {};
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -122,7 +113,7 @@ LL | let async: async = async {};
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:69:19
|
--> $DIR/async-ident.rs:67:19
|
||||||
|
|
|
|
||||||
LL | () => (pub fn async() {})
|
LL | () => (pub fn async() {})
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -131,7 +122,7 @@ LL | () => (pub fn async() {})
|
|||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: `async` is a keyword in the 2018 edition
|
error: `async` is a keyword in the 2018 edition
|
||||||
--> $DIR/async-ident.rs:76:6
|
--> $DIR/async-ident.rs:74:6
|
||||||
|
|
|
|
||||||
LL | (async) => (1)
|
LL | (async) => (1)
|
||||||
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
| ^^^^^ help: you can use a raw identifier to stay compatible: `r#async`
|
||||||
@ -139,5 +130,5 @@ LL | (async) => (1)
|
|||||||
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018!
|
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2018!
|
||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: aborting due to 15 previous errors
|
error: aborting due to 14 previous errors
|
||||||
|
|
||||||
|
13
tests/ui/rust-2024/gen-kw-in-macro.rs
Normal file
13
tests/ui/rust-2024/gen-kw-in-macro.rs
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
//@ check-pass
|
||||||
|
|
||||||
|
#![deny(keyword_idents_2024)]
|
||||||
|
|
||||||
|
macro_rules! foo {
|
||||||
|
($gen:expr) => {
|
||||||
|
$gen
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
foo!(println!("hello, world"));
|
||||||
|
}
|
@ -22,5 +22,14 @@ LL | let gen = r#gen;
|
|||||||
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: `gen` is a keyword in the 2024 edition
|
||||||
|
--> $DIR/gen-kw.rs:19:27
|
||||||
|
|
|
||||||
|
LL | () => { mod test { fn gen() {} } }
|
||||||
|
| ^^^ help: you can use a raw identifier to stay compatible: `r#gen`
|
||||||
|
|
|
||||||
|
= warning: this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
||||||
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
@ -22,5 +22,14 @@ LL | let gen = r#gen;
|
|||||||
= warning: this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
= warning: this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
||||||
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: `gen` is a keyword in the 2024 edition
|
||||||
|
--> $DIR/gen-kw.rs:19:27
|
||||||
|
|
|
||||||
|
LL | () => { mod test { fn gen() {} } }
|
||||||
|
| ^^^ help: you can use a raw identifier to stay compatible: `r#gen`
|
||||||
|
|
|
||||||
|
= warning: this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
||||||
|
= note: for more information, see issue #49716 <https://github.com/rust-lang/rust/issues/49716>
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
@ -14,3 +14,12 @@ fn main() {
|
|||||||
//[e2015]~| WARNING this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
//[e2015]~| WARNING this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
||||||
//[e2018]~| WARNING this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
//[e2018]~| WARNING this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
||||||
}
|
}
|
||||||
|
|
||||||
|
macro_rules! t {
|
||||||
|
() => { mod test { fn gen() {} } }
|
||||||
|
//~^ ERROR `gen` is a keyword in the 2024 edition
|
||||||
|
//[e2015]~| WARNING this is accepted in the current edition (Rust 2015) but is a hard error in Rust 2024!
|
||||||
|
//[e2018]~| WARNING this is accepted in the current edition (Rust 2018) but is a hard error in Rust 2024!
|
||||||
|
}
|
||||||
|
|
||||||
|
t!();
|
||||||
|
35
tests/ui/suggestions/unused-imports.fixed
Normal file
35
tests/ui/suggestions/unused-imports.fixed
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
//@ run-rustfix
|
||||||
|
//@ check-pass
|
||||||
|
|
||||||
|
#![warn(unused_imports)]
|
||||||
|
|
||||||
|
pub mod nested {
|
||||||
|
pub struct A;
|
||||||
|
pub struct B;
|
||||||
|
pub struct C;
|
||||||
|
pub struct D;
|
||||||
|
pub mod even_more {
|
||||||
|
pub struct E;
|
||||||
|
pub struct F;
|
||||||
|
pub struct G;
|
||||||
|
}
|
||||||
|
pub mod another {
|
||||||
|
pub struct H;
|
||||||
|
pub struct I;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
use nested::B;
|
||||||
|
//~^ WARN unused import
|
||||||
|
|
||||||
|
use nested::even_more::F;
|
||||||
|
//~^^^^^^^ WARN unused import
|
||||||
|
|
||||||
|
// Note that the following fix should result in `::{self}`, not `::self`. The latter is invalid
|
||||||
|
// Rust syntax, so the braces should not be removed.
|
||||||
|
use nested::another::{self};
|
||||||
|
//~^ WARN unused import
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let _ = (B, F, another::I);
|
||||||
|
}
|
42
tests/ui/suggestions/unused-imports.rs
Normal file
42
tests/ui/suggestions/unused-imports.rs
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
//@ run-rustfix
|
||||||
|
//@ check-pass
|
||||||
|
|
||||||
|
#![warn(unused_imports)]
|
||||||
|
|
||||||
|
pub mod nested {
|
||||||
|
pub struct A;
|
||||||
|
pub struct B;
|
||||||
|
pub struct C;
|
||||||
|
pub struct D;
|
||||||
|
pub mod even_more {
|
||||||
|
pub struct E;
|
||||||
|
pub struct F;
|
||||||
|
pub struct G;
|
||||||
|
}
|
||||||
|
pub mod another {
|
||||||
|
pub struct H;
|
||||||
|
pub struct I;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
use nested::{A, B, C};
|
||||||
|
//~^ WARN unused import
|
||||||
|
|
||||||
|
use nested::{
|
||||||
|
D,
|
||||||
|
even_more::{
|
||||||
|
E,
|
||||||
|
F,
|
||||||
|
G,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
//~^^^^^^^ WARN unused import
|
||||||
|
|
||||||
|
// Note that the following fix should result in `::{self}`, not `::self`. The latter is invalid
|
||||||
|
// Rust syntax, so the braces should not be removed.
|
||||||
|
use nested::another::{self, I};
|
||||||
|
//~^ WARN unused import
|
||||||
|
|
||||||
|
fn main() {
|
||||||
|
let _ = (B, F, another::I);
|
||||||
|
}
|
32
tests/ui/suggestions/unused-imports.stderr
Normal file
32
tests/ui/suggestions/unused-imports.stderr
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
warning: unused imports: `A`, `C`
|
||||||
|
--> $DIR/unused-imports.rs:22:14
|
||||||
|
|
|
||||||
|
LL | use nested::{A, B, C};
|
||||||
|
| ^ ^
|
||||||
|
|
|
||||||
|
note: the lint level is defined here
|
||||||
|
--> $DIR/unused-imports.rs:4:9
|
||||||
|
|
|
||||||
|
LL | #![warn(unused_imports)]
|
||||||
|
| ^^^^^^^^^^^^^^
|
||||||
|
|
||||||
|
warning: unused imports: `D`, `E`, `G`
|
||||||
|
--> $DIR/unused-imports.rs:26:5
|
||||||
|
|
|
||||||
|
LL | D,
|
||||||
|
| ^
|
||||||
|
LL | even_more::{
|
||||||
|
LL | E,
|
||||||
|
| ^
|
||||||
|
LL | F,
|
||||||
|
LL | G,
|
||||||
|
| ^
|
||||||
|
|
||||||
|
warning: unused import: `I`
|
||||||
|
--> $DIR/unused-imports.rs:37:29
|
||||||
|
|
|
||||||
|
LL | use nested::another::{self, I};
|
||||||
|
| ^
|
||||||
|
|
||||||
|
warning: 3 warnings emitted
|
||||||
|
|
@ -8,7 +8,7 @@
|
|||||||
|
|
||||||
use std::pat::pattern_type;
|
use std::pat::pattern_type;
|
||||||
|
|
||||||
type X = std::num::NonZeroU32;
|
type X = std::num::NonZero<u32>;
|
||||||
type Y = pattern_type!(u32 is 1..);
|
type Y = pattern_type!(u32 is 1..);
|
||||||
type Z = Option<pattern_type!(u32 is 1..)>;
|
type Z = Option<pattern_type!(u32 is 1..)>;
|
||||||
struct NonZeroU32New(pattern_type!(u32 is 1..));
|
struct NonZeroU32New(pattern_type!(u32 is 1..));
|
||||||
|
Loading…
Reference in New Issue
Block a user