Rollup merge of #144977 - fmease:fortify-param-default-checks, r=compiler-errors
Fortify generic param default checks * Hard-reject instead of lint-reject type param defaults in generic assoc consts (GACs) (feature: `generic_const_items`). * In https://github.com/rust-lang/rust/pull/113522, I explicitly handled the free const item case and forgot about the assoc const one. * This led rustc to assume the default of emitting the deny-by-default lint `invalid_type_param_default`. * GCIs are unstable, thus we're not bound by backward compat * Hard-reject instead of lint-reject type param defaults in foreign items. * We already hard-reject generic params on foreign items, so this isn't a breaking change. * There's no reason why we need to lint-reject. * Refactor the way we determine where generic param defaults are allowed: * Don't default to emitting lint `invalid_type_param_defaults` for nodes that aren't explicitly handled but instead panic. * This would've caught my GAC oversight from above much earlier via fuzzing * Prevents us from accidentally stabilizing more invalid type param defaults in the future * Streamline the phrasing of the diagnostic
This commit is contained in:
@@ -223,60 +223,27 @@ pub(super) fn generics_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::Generics {
|
|||||||
"synthetic HIR should have its `generics_of` explicitly fed"
|
"synthetic HIR should have its `generics_of` explicitly fed"
|
||||||
),
|
),
|
||||||
|
|
||||||
_ => span_bug!(tcx.def_span(def_id), "unhandled node {node:?}"),
|
_ => span_bug!(tcx.def_span(def_id), "generics_of: unexpected node kind {node:?}"),
|
||||||
};
|
};
|
||||||
|
|
||||||
enum Defaults {
|
|
||||||
Allowed,
|
|
||||||
// See #36887
|
|
||||||
FutureCompatDisallowed,
|
|
||||||
Deny,
|
|
||||||
}
|
|
||||||
|
|
||||||
let hir_generics = node.generics().unwrap_or(hir::Generics::empty());
|
|
||||||
let (opt_self, allow_defaults) = match node {
|
|
||||||
Node::Item(item) => {
|
|
||||||
match item.kind {
|
|
||||||
ItemKind::Trait(..) | ItemKind::TraitAlias(..) => {
|
|
||||||
// Add in the self type parameter.
|
// Add in the self type parameter.
|
||||||
//
|
let opt_self = if let Node::Item(item) = node
|
||||||
// Something of a hack: use the node id for the trait, also as
|
&& let ItemKind::Trait(..) | ItemKind::TraitAlias(..) = item.kind
|
||||||
// the node id for the Self type parameter.
|
{
|
||||||
let opt_self = Some(ty::GenericParamDef {
|
// Something of a hack: We reuse the node ID of the trait for the self type parameter.
|
||||||
|
Some(ty::GenericParamDef {
|
||||||
index: 0,
|
index: 0,
|
||||||
name: kw::SelfUpper,
|
name: kw::SelfUpper,
|
||||||
def_id: def_id.to_def_id(),
|
def_id: def_id.to_def_id(),
|
||||||
pure_wrt_drop: false,
|
pure_wrt_drop: false,
|
||||||
kind: ty::GenericParamDefKind::Type {
|
kind: ty::GenericParamDefKind::Type { has_default: false, synthetic: false },
|
||||||
has_default: false,
|
})
|
||||||
synthetic: false,
|
} else {
|
||||||
},
|
None
|
||||||
});
|
|
||||||
|
|
||||||
(opt_self, Defaults::Allowed)
|
|
||||||
}
|
|
||||||
ItemKind::TyAlias(..)
|
|
||||||
| ItemKind::Enum(..)
|
|
||||||
| ItemKind::Struct(..)
|
|
||||||
| ItemKind::Union(..) => (None, Defaults::Allowed),
|
|
||||||
ItemKind::Const(..) => (None, Defaults::Deny),
|
|
||||||
_ => (None, Defaults::FutureCompatDisallowed),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Node::OpaqueTy(..) => (None, Defaults::Allowed),
|
|
||||||
|
|
||||||
// GATs
|
|
||||||
Node::TraitItem(item) if matches!(item.kind, TraitItemKind::Type(..)) => {
|
|
||||||
(None, Defaults::Deny)
|
|
||||||
}
|
|
||||||
Node::ImplItem(item) if matches!(item.kind, ImplItemKind::Type(..)) => {
|
|
||||||
(None, Defaults::Deny)
|
|
||||||
}
|
|
||||||
|
|
||||||
_ => (None, Defaults::FutureCompatDisallowed),
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let param_default_policy = param_default_policy(node);
|
||||||
|
let hir_generics = node.generics().unwrap_or(hir::Generics::empty());
|
||||||
let has_self = opt_self.is_some();
|
let has_self = opt_self.is_some();
|
||||||
let mut parent_has_self = false;
|
let mut parent_has_self = false;
|
||||||
let mut own_start = has_self as u32;
|
let mut own_start = has_self as u32;
|
||||||
@@ -312,33 +279,46 @@ pub(super) fn generics_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::Generics {
|
|||||||
prev + type_start
|
prev + type_start
|
||||||
};
|
};
|
||||||
|
|
||||||
const TYPE_DEFAULT_NOT_ALLOWED: &'static str = "defaults for type parameters are only allowed in \
|
own_params.extend(hir_generics.params.iter().filter_map(|param| {
|
||||||
`struct`, `enum`, `type`, or `trait` definitions";
|
const MESSAGE: &str = "defaults for generic parameters are not allowed here";
|
||||||
|
let kind = match param.kind {
|
||||||
own_params.extend(hir_generics.params.iter().filter_map(|param| match param.kind {
|
GenericParamKind::Lifetime { .. } => return None,
|
||||||
GenericParamKind::Lifetime { .. } => None,
|
GenericParamKind::Type { default, synthetic } => {
|
||||||
GenericParamKind::Type { default, synthetic, .. } => {
|
|
||||||
if default.is_some() {
|
if default.is_some() {
|
||||||
match allow_defaults {
|
match param_default_policy.expect("no policy for generic param default") {
|
||||||
Defaults::Allowed => {}
|
ParamDefaultPolicy::Allowed => {}
|
||||||
Defaults::FutureCompatDisallowed => {
|
ParamDefaultPolicy::FutureCompatForbidden => {
|
||||||
tcx.node_span_lint(
|
tcx.node_span_lint(
|
||||||
lint::builtin::INVALID_TYPE_PARAM_DEFAULT,
|
lint::builtin::INVALID_TYPE_PARAM_DEFAULT,
|
||||||
param.hir_id,
|
param.hir_id,
|
||||||
param.span,
|
param.span,
|
||||||
|lint| {
|
|lint| {
|
||||||
lint.primary_message(TYPE_DEFAULT_NOT_ALLOWED);
|
lint.primary_message(MESSAGE);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
Defaults::Deny => {
|
ParamDefaultPolicy::Forbidden => {
|
||||||
tcx.dcx().span_err(param.span, TYPE_DEFAULT_NOT_ALLOWED);
|
tcx.dcx().span_err(param.span, MESSAGE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let kind = ty::GenericParamDefKind::Type { has_default: default.is_some(), synthetic };
|
ty::GenericParamDefKind::Type { has_default: default.is_some(), synthetic }
|
||||||
|
}
|
||||||
|
GenericParamKind::Const { ty: _, default, synthetic } => {
|
||||||
|
if default.is_some() {
|
||||||
|
match param_default_policy.expect("no policy for generic param default") {
|
||||||
|
ParamDefaultPolicy::Allowed => {}
|
||||||
|
ParamDefaultPolicy::FutureCompatForbidden
|
||||||
|
| ParamDefaultPolicy::Forbidden => {
|
||||||
|
tcx.dcx().span_err(param.span, MESSAGE);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ty::GenericParamDefKind::Const { has_default: default.is_some(), synthetic }
|
||||||
|
}
|
||||||
|
};
|
||||||
Some(ty::GenericParamDef {
|
Some(ty::GenericParamDef {
|
||||||
index: next_index(),
|
index: next_index(),
|
||||||
name: param.name.ident().name,
|
name: param.name.ident().name,
|
||||||
@@ -346,26 +326,6 @@ pub(super) fn generics_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::Generics {
|
|||||||
pure_wrt_drop: param.pure_wrt_drop,
|
pure_wrt_drop: param.pure_wrt_drop,
|
||||||
kind,
|
kind,
|
||||||
})
|
})
|
||||||
}
|
|
||||||
GenericParamKind::Const { ty: _, default, synthetic } => {
|
|
||||||
if !matches!(allow_defaults, Defaults::Allowed) && default.is_some() {
|
|
||||||
tcx.dcx().span_err(
|
|
||||||
param.span,
|
|
||||||
"defaults for const parameters are only allowed in \
|
|
||||||
`struct`, `enum`, `type`, or `trait` definitions",
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
let index = next_index();
|
|
||||||
|
|
||||||
Some(ty::GenericParamDef {
|
|
||||||
index,
|
|
||||||
name: param.name.ident().name,
|
|
||||||
def_id: param.def_id.to_def_id(),
|
|
||||||
pure_wrt_drop: param.pure_wrt_drop,
|
|
||||||
kind: ty::GenericParamDefKind::Const { has_default: default.is_some(), synthetic },
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}));
|
}));
|
||||||
|
|
||||||
// provide junk type parameter defs - the only place that
|
// provide junk type parameter defs - the only place that
|
||||||
@@ -438,6 +398,48 @@ pub(super) fn generics_of(tcx: TyCtxt<'_>, def_id: LocalDefId) -> ty::Generics {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy)]
|
||||||
|
enum ParamDefaultPolicy {
|
||||||
|
Allowed,
|
||||||
|
/// Tracked in <https://github.com/rust-lang/rust/issues/36887>.
|
||||||
|
FutureCompatForbidden,
|
||||||
|
Forbidden,
|
||||||
|
}
|
||||||
|
|
||||||
|
fn param_default_policy(node: Node<'_>) -> Option<ParamDefaultPolicy> {
|
||||||
|
use rustc_hir::*;
|
||||||
|
|
||||||
|
Some(match node {
|
||||||
|
Node::Item(item) => match item.kind {
|
||||||
|
ItemKind::Trait(..)
|
||||||
|
| ItemKind::TraitAlias(..)
|
||||||
|
| ItemKind::TyAlias(..)
|
||||||
|
| ItemKind::Enum(..)
|
||||||
|
| ItemKind::Struct(..)
|
||||||
|
| ItemKind::Union(..) => ParamDefaultPolicy::Allowed,
|
||||||
|
ItemKind::Fn { .. } | ItemKind::Impl(_) => ParamDefaultPolicy::FutureCompatForbidden,
|
||||||
|
// Re. GCI, we're not bound by backward compatibility.
|
||||||
|
ItemKind::Const(..) => ParamDefaultPolicy::Forbidden,
|
||||||
|
_ => return None,
|
||||||
|
},
|
||||||
|
Node::TraitItem(item) => match item.kind {
|
||||||
|
// Re. GATs and GACs (generic_const_items), we're not bound by backward compatibility.
|
||||||
|
TraitItemKind::Const(..) | TraitItemKind::Type(..) => ParamDefaultPolicy::Forbidden,
|
||||||
|
TraitItemKind::Fn(..) => ParamDefaultPolicy::FutureCompatForbidden,
|
||||||
|
},
|
||||||
|
Node::ImplItem(item) => match item.kind {
|
||||||
|
// Re. GATs and GACs (generic_const_items), we're not bound by backward compatibility.
|
||||||
|
ImplItemKind::Const(..) | ImplItemKind::Type(..) => ParamDefaultPolicy::Forbidden,
|
||||||
|
ImplItemKind::Fn(..) => ParamDefaultPolicy::FutureCompatForbidden,
|
||||||
|
},
|
||||||
|
// Generic params are (semantically) invalid on foreign items. Still, for maximum forward
|
||||||
|
// compatibility, let's hard-reject defaults on them.
|
||||||
|
Node::ForeignItem(_) => ParamDefaultPolicy::Forbidden,
|
||||||
|
Node::OpaqueTy(..) => ParamDefaultPolicy::Allowed,
|
||||||
|
_ => return None,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
fn has_late_bound_regions<'tcx>(tcx: TyCtxt<'tcx>, node: Node<'tcx>) -> Option<Span> {
|
fn has_late_bound_regions<'tcx>(tcx: TyCtxt<'tcx>, node: Node<'tcx>) -> Option<Span> {
|
||||||
struct LateBoundRegionsDetector<'tcx> {
|
struct LateBoundRegionsDetector<'tcx> {
|
||||||
tcx: TyCtxt<'tcx>,
|
tcx: TyCtxt<'tcx>,
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
struct Foo<const N: usize>;
|
struct Foo<const N: usize>;
|
||||||
|
|
||||||
impl<const N: usize = 1> Foo<N> {}
|
impl<const N: usize = 1> Foo<N> {}
|
||||||
//~^ ERROR defaults for const parameters are only allowed
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/default-on-impl.rs:3:6
|
--> $DIR/default-on-impl.rs:3:6
|
||||||
|
|
|
|
||||||
LL | impl<const N: usize = 1> Foo<N> {}
|
LL | impl<const N: usize = 1> Foo<N> {}
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
#![feature(generic_const_exprs)]
|
#![feature(generic_const_exprs)]
|
||||||
#![allow(incomplete_features)]
|
#![expect(incomplete_features)]
|
||||||
|
|
||||||
trait Trait<T> {
|
trait Trait<T> {
|
||||||
fn fnc<const N: usize = "">(&self) {} //~ERROR defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
fn fnc<const N: usize = "">(&self) {} //~ERROR defaults for generic parameters are not allowed here
|
||||||
//~^ ERROR: mismatched types
|
//~^ ERROR: mismatched types
|
||||||
fn foo<const N: usize = { std::mem::size_of::<T>() }>(&self) {} //~ERROR defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
fn foo<const N: usize = { std::mem::size_of::<T>() }>(&self) {} //~ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {}
|
fn main() {}
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/issue-105257.rs:5:12
|
--> $DIR/issue-105257.rs:5:12
|
||||||
|
|
|
|
||||||
LL | fn fnc<const N: usize = "">(&self) {}
|
LL | fn fnc<const N: usize = "">(&self) {}
|
||||||
| ^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/issue-105257.rs:7:12
|
--> $DIR/issue-105257.rs:7:12
|
||||||
|
|
|
|
||||||
LL | fn foo<const N: usize = { std::mem::size_of::<T>() }>(&self) {}
|
LL | fn foo<const N: usize = { std::mem::size_of::<T>() }>(&self) {}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#![crate_type = "lib"]
|
#![crate_type = "lib"]
|
||||||
|
|
||||||
fn foo<const SIZE: usize = 5usize>() {}
|
fn foo<const SIZE: usize = 5usize>() {}
|
||||||
//~^ ERROR defaults for const parameters are
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/default_function_param.rs:3:8
|
--> $DIR/default_function_param.rs:3:8
|
||||||
|
|
|
|
||||||
LL | fn foo<const SIZE: usize = 5usize>() {}
|
LL | fn foo<const SIZE: usize = 5usize>() {}
|
||||||
|
|||||||
@@ -4,17 +4,17 @@
|
|||||||
|
|
||||||
trait Trait {
|
trait Trait {
|
||||||
type Assoc<T = u32>;
|
type Assoc<T = u32>;
|
||||||
//~^ ERROR defaults for type parameters are only allowed
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Trait for () {
|
impl Trait for () {
|
||||||
type Assoc<T = u32> = u64;
|
type Assoc<T = u32> = u64;
|
||||||
//~^ ERROR defaults for type parameters are only allowed
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Trait for u32 {
|
impl Trait for u32 {
|
||||||
type Assoc<T = u32> = T;
|
type Assoc<T = u32> = T;
|
||||||
//~^ ERROR defaults for type parameters are only allowed
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
trait Other {}
|
trait Other {}
|
||||||
|
|||||||
@@ -1,16 +1,16 @@
|
|||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/type-param-defaults.rs:6:16
|
--> $DIR/type-param-defaults.rs:6:16
|
||||||
|
|
|
|
||||||
LL | type Assoc<T = u32>;
|
LL | type Assoc<T = u32>;
|
||||||
| ^^^^^^^
|
| ^^^^^^^
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/type-param-defaults.rs:11:16
|
--> $DIR/type-param-defaults.rs:11:16
|
||||||
|
|
|
|
||||||
LL | type Assoc<T = u32> = u64;
|
LL | type Assoc<T = u32> = u64;
|
||||||
| ^^^^^^^
|
| ^^^^^^^
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/type-param-defaults.rs:16:16
|
--> $DIR/type-param-defaults.rs:16:16
|
||||||
|
|
|
|
||||||
LL | type Assoc<T = u32> = T;
|
LL | type Assoc<T = u32> = T;
|
||||||
|
|||||||
@@ -7,9 +7,17 @@
|
|||||||
|
|
||||||
// FIXME(default_type_parameter_fallback): Consider reallowing them once they work properly.
|
// FIXME(default_type_parameter_fallback): Consider reallowing them once they work properly.
|
||||||
|
|
||||||
const NONE<T = ()>: Option<T> = None::<T>; //~ ERROR defaults for type parameters are only allowed
|
const NONE<T = ()>: Option<T> = None::<T>;
|
||||||
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
|
|
||||||
fn main() {
|
impl Host {
|
||||||
let _ = NONE;
|
const NADA<T = ()>: Option<T> = None::<T>;
|
||||||
//~^ ERROR type annotations needed
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum Host {}
|
||||||
|
|
||||||
|
fn body0() { let _ = NONE; } //~ ERROR type annotations needed
|
||||||
|
fn body1() { let _ = Host::NADA; } //~ ERROR type annotations needed
|
||||||
|
|
||||||
|
fn main() {}
|
||||||
|
|||||||
@@ -1,20 +1,37 @@
|
|||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/parameter-defaults.rs:10:12
|
--> $DIR/parameter-defaults.rs:10:12
|
||||||
|
|
|
|
||||||
LL | const NONE<T = ()>: Option<T> = None::<T>;
|
LL | const NONE<T = ()>: Option<T> = None::<T>;
|
||||||
| ^^^^^^
|
| ^^^^^^
|
||||||
|
|
||||||
error[E0282]: type annotations needed for `Option<_>`
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/parameter-defaults.rs:13:9
|
--> $DIR/parameter-defaults.rs:14:16
|
||||||
|
|
|
|
||||||
LL | let _ = NONE;
|
LL | const NADA<T = ()>: Option<T> = None::<T>;
|
||||||
|
| ^^^^^^
|
||||||
|
|
||||||
|
error[E0282]: type annotations needed for `Option<_>`
|
||||||
|
--> $DIR/parameter-defaults.rs:20:18
|
||||||
|
|
|
||||||
|
LL | fn body0() { let _ = NONE; }
|
||||||
| ^ ---- type must be known at this point
|
| ^ ---- type must be known at this point
|
||||||
|
|
|
|
||||||
help: consider giving this pattern a type, where the type for type parameter `T` is specified
|
help: consider giving this pattern a type, where the type for type parameter `T` is specified
|
||||||
|
|
|
|
||||||
LL | let _: Option<T> = NONE;
|
LL | fn body0() { let _: Option<T> = NONE; }
|
||||||
| +++++++++++
|
| +++++++++++
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error[E0282]: type annotations needed for `Option<_>`
|
||||||
|
--> $DIR/parameter-defaults.rs:21:18
|
||||||
|
|
|
||||||
|
LL | fn body1() { let _ = Host::NADA; }
|
||||||
|
| ^ ---------- type must be known at this point
|
||||||
|
|
|
||||||
|
help: consider giving this pattern a type, where the type for type parameter `T` is specified
|
||||||
|
|
|
||||||
|
LL | fn body1() { let _: Option<T> = Host::NADA; }
|
||||||
|
| +++++++++++
|
||||||
|
|
||||||
|
error: aborting due to 4 previous errors
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0282`.
|
For more information about this error, try `rustc --explain E0282`.
|
||||||
|
|||||||
@@ -1,7 +1,15 @@
|
|||||||
|
// Ensure that we reject generic parameters on foreign items.
|
||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
fn foo<T>(); //~ ERROR foreign items may not have type parameters
|
fn foo<T>(); //~ ERROR foreign items may not have type parameters
|
||||||
|
|
||||||
|
// Furthermore, check that type parameter defaults lead to a *hard* error,
|
||||||
|
// not just a lint error, for maximum forward compatibility.
|
||||||
|
#[allow(invalid_type_param_default)] // Should have no effect here.
|
||||||
|
fn bar<T = ()>(); //~ ERROR foreign items may not have type parameters
|
||||||
|
//~^ ERROR defaults for generic parameters are not allowed here
|
||||||
}
|
}
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
foo::<i32>(); //~ ERROR requires unsafe
|
unsafe { foo::<i32>() };
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,20 +1,25 @@
|
|||||||
error[E0044]: foreign items may not have type parameters
|
error[E0044]: foreign items may not have type parameters
|
||||||
--> $DIR/generic-extern.rs:2:5
|
--> $DIR/generic-extern.rs:4:5
|
||||||
|
|
|
|
||||||
LL | fn foo<T>();
|
LL | fn foo<T>();
|
||||||
| ^^^^^^^^^^^^ can't have type parameters
|
| ^^^^^^^^^^^^ can't have type parameters
|
||||||
|
|
|
|
||||||
= help: replace the type parameters with concrete types like `u32`
|
= help: replace the type parameters with concrete types like `u32`
|
||||||
|
|
||||||
error[E0133]: call to unsafe function `foo` is unsafe and requires unsafe function or block
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/generic-extern.rs:6:5
|
--> $DIR/generic-extern.rs:9:12
|
||||||
|
|
|
|
||||||
LL | foo::<i32>();
|
LL | fn bar<T = ()>();
|
||||||
| ^^^^^^^^^^^^ call to unsafe function
|
| ^^^^^^
|
||||||
|
|
||||||
|
error[E0044]: foreign items may not have type parameters
|
||||||
|
--> $DIR/generic-extern.rs:9:5
|
||||||
|
|
|
|
||||||
= note: consult the function's documentation for information on how to avoid undefined behavior
|
LL | fn bar<T = ()>();
|
||||||
|
| ^^^^^^^^^^^^^^^^^ can't have type parameters
|
||||||
|
|
|
||||||
|
= help: replace the type parameters with concrete types like `u32`
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
Some errors have detailed explanations: E0044, E0133.
|
For more information about this error, try `rustc --explain E0044`.
|
||||||
For more information about an error, try `rustc --explain E0044`.
|
|
||||||
|
|||||||
22
tests/ui/generics/invalid-type-param-default.rs
Normal file
22
tests/ui/generics/invalid-type-param-default.rs
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
// Ensure that we emit the deny-by-default lint `invalid_type_param_default` in locations where
|
||||||
|
// type parameter defaults were accidentally allowed but don't have any effect whatsoever.
|
||||||
|
//
|
||||||
|
// Tracked in <https://github.com/rust-lang/rust/issues/36887>.
|
||||||
|
// FIXME(default_type_parameter_fallback): Consider reallowing them once they work properly.
|
||||||
|
|
||||||
|
fn avg<T = i32>(_: T) {}
|
||||||
|
//~^ ERROR defaults for generic parameters are not allowed here [invalid_type_param_default]
|
||||||
|
//~| WARN this was previously accepted
|
||||||
|
|
||||||
|
// issue: <https://github.com/rust-lang/rust/issues/26812>
|
||||||
|
fn mdn<T = T::Item>(_: T) {}
|
||||||
|
//~^ ERROR generic parameter defaults cannot reference parameters before they are declared
|
||||||
|
//~| ERROR defaults for generic parameters are not allowed here [invalid_type_param_default]
|
||||||
|
//~| WARN this was previously accepted
|
||||||
|
|
||||||
|
struct S<T>(T);
|
||||||
|
impl<T = i32> S<T> {}
|
||||||
|
//~^ ERROR defaults for generic parameters are not allowed here [invalid_type_param_default]
|
||||||
|
//~| WARN this was previously accepted
|
||||||
|
|
||||||
|
fn main() {}
|
||||||
70
tests/ui/generics/invalid-type-param-default.stderr
Normal file
70
tests/ui/generics/invalid-type-param-default.stderr
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
error[E0128]: generic parameter defaults cannot reference parameters before they are declared
|
||||||
|
--> $DIR/invalid-type-param-default.rs:12:12
|
||||||
|
|
|
||||||
|
LL | fn mdn<T = T::Item>(_: T) {}
|
||||||
|
| ^^^^^^^ cannot reference `T` before it is declared
|
||||||
|
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:7:8
|
||||||
|
|
|
||||||
|
LL | fn avg<T = i32>(_: T) {}
|
||||||
|
| ^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
= note: `#[deny(invalid_type_param_default)]` on by default
|
||||||
|
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:12:8
|
||||||
|
|
|
||||||
|
LL | fn mdn<T = T::Item>(_: T) {}
|
||||||
|
| ^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:18:6
|
||||||
|
|
|
||||||
|
LL | impl<T = i32> S<T> {}
|
||||||
|
| ^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
|
||||||
|
error: aborting due to 4 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0128`.
|
||||||
|
Future incompatibility report: Future breakage diagnostic:
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:7:8
|
||||||
|
|
|
||||||
|
LL | fn avg<T = i32>(_: T) {}
|
||||||
|
| ^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
= note: `#[deny(invalid_type_param_default)]` on by default
|
||||||
|
|
||||||
|
Future breakage diagnostic:
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:12:8
|
||||||
|
|
|
||||||
|
LL | fn mdn<T = T::Item>(_: T) {}
|
||||||
|
| ^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
= note: `#[deny(invalid_type_param_default)]` on by default
|
||||||
|
|
||||||
|
Future breakage diagnostic:
|
||||||
|
error: defaults for generic parameters are not allowed here
|
||||||
|
--> $DIR/invalid-type-param-default.rs:18:6
|
||||||
|
|
|
||||||
|
LL | impl<T = i32> S<T> {}
|
||||||
|
| ^^^^^^^
|
||||||
|
|
|
||||||
|
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
|
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
||||||
|
= note: `#[deny(invalid_type_param_default)]` on by default
|
||||||
|
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
fn mainIterator<_ = _> {}
|
fn mainIterator<_ = _> {}
|
||||||
//~^ ERROR expected identifier, found reserved identifier `_`
|
//~^ ERROR expected identifier, found reserved identifier `_`
|
||||||
//~| ERROR missing parameters for function definition
|
//~| ERROR missing parameters for function definition
|
||||||
//~| ERROR defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions [invalid_type_param_default]
|
//~| ERROR defaults for generic parameters are not allowed here [invalid_type_param_default]
|
||||||
//~| WARNING this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
//~| WARNING this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||||
//~| ERROR the placeholder `_` is not allowed within types on item signatures for functions [E0121]
|
//~| ERROR the placeholder `_` is not allowed within types on item signatures for functions [E0121]
|
||||||
|
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ help: add a parameter list
|
|||||||
LL | fn mainIterator<_ = _>() {}
|
LL | fn mainIterator<_ = _>() {}
|
||||||
| ++
|
| ++
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/overlapping-errors-span-issue-123861.rs:1:17
|
--> $DIR/overlapping-errors-span-issue-123861.rs:1:17
|
||||||
|
|
|
|
||||||
LL | fn mainIterator<_ = _> {}
|
LL | fn mainIterator<_ = _> {}
|
||||||
@@ -35,7 +35,7 @@ error: aborting due to 4 previous errors
|
|||||||
|
|
||||||
For more information about this error, try `rustc --explain E0121`.
|
For more information about this error, try `rustc --explain E0121`.
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
Future incompatibility report: Future breakage diagnostic:
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/overlapping-errors-span-issue-123861.rs:1:17
|
--> $DIR/overlapping-errors-span-issue-123861.rs:1:17
|
||||||
|
|
|
|
||||||
LL | fn mainIterator<_ = _> {}
|
LL | fn mainIterator<_ = _> {}
|
||||||
|
|||||||
@@ -236,17 +236,15 @@ type InTypeAliasGenericParamDefault<T = impl Debug> = T;
|
|||||||
//~^ ERROR `impl Trait` is not allowed in generic parameter defaults
|
//~^ ERROR `impl Trait` is not allowed in generic parameter defaults
|
||||||
|
|
||||||
// Disallowed
|
// Disallowed
|
||||||
impl <T = impl Debug> T {}
|
#[expect(invalid_type_param_default)]
|
||||||
//~^ ERROR defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
impl<T = impl Debug> T {}
|
||||||
//~| WARNING this was previously accepted by the compiler but is being phased out
|
//~^ ERROR `impl Trait` is not allowed in generic parameter defaults
|
||||||
//~| ERROR `impl Trait` is not allowed in generic parameter defaults
|
|
||||||
//~| ERROR no nominal type found
|
//~| ERROR no nominal type found
|
||||||
|
|
||||||
// Disallowed
|
// Disallowed
|
||||||
|
#[expect(invalid_type_param_default)]
|
||||||
fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
||||||
//~^ ERROR defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
//~^ ERROR `impl Trait` is not allowed in generic parameter defaults
|
||||||
//~| WARNING this was previously accepted by the compiler but is being phased out
|
|
||||||
//~| ERROR `impl Trait` is not allowed in generic parameter defaults
|
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let _in_local_variable: impl Fn() = || {};
|
let _in_local_variable: impl Fn() = || {};
|
||||||
|
|||||||
@@ -311,9 +311,9 @@ LL | type InTypeAliasGenericParamDefault<T = impl Debug> = T;
|
|||||||
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
||||||
|
|
||||||
error[E0562]: `impl Trait` is not allowed in generic parameter defaults
|
error[E0562]: `impl Trait` is not allowed in generic parameter defaults
|
||||||
--> $DIR/where-allowed.rs:239:11
|
--> $DIR/where-allowed.rs:240:10
|
||||||
|
|
|
|
||||||
LL | impl <T = impl Debug> T {}
|
LL | impl<T = impl Debug> T {}
|
||||||
| ^^^^^^^^^^
|
| ^^^^^^^^^^
|
||||||
|
|
|
|
||||||
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
||||||
@@ -327,7 +327,7 @@ LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
|||||||
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
= note: `impl Trait` is only allowed in arguments and return types of functions and methods
|
||||||
|
|
||||||
error[E0562]: `impl Trait` is not allowed in the type of variable bindings
|
error[E0562]: `impl Trait` is not allowed in the type of variable bindings
|
||||||
--> $DIR/where-allowed.rs:252:29
|
--> $DIR/where-allowed.rs:250:29
|
||||||
|
|
|
|
||||||
LL | let _in_local_variable: impl Fn() = || {};
|
LL | let _in_local_variable: impl Fn() = || {};
|
||||||
| ^^^^^^^^^
|
| ^^^^^^^^^
|
||||||
@@ -338,7 +338,7 @@ LL | let _in_local_variable: impl Fn() = || {};
|
|||||||
= note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date
|
= note: this compiler was built on YYYY-MM-DD; consider upgrading it if it is out of date
|
||||||
|
|
||||||
error[E0562]: `impl Trait` is not allowed in closure return types
|
error[E0562]: `impl Trait` is not allowed in closure return types
|
||||||
--> $DIR/where-allowed.rs:254:46
|
--> $DIR/where-allowed.rs:252:46
|
||||||
|
|
|
|
||||||
LL | let _in_return_in_local_variable = || -> impl Fn() { || {} };
|
LL | let _in_return_in_local_variable = || -> impl Fn() { || {} };
|
||||||
| ^^^^^^^^^
|
| ^^^^^^^^^
|
||||||
@@ -368,25 +368,6 @@ LL - fn in_trait_impl_return() -> impl Debug { () }
|
|||||||
LL + fn in_trait_impl_return() -> <() as DummyTrait>::Out { () }
|
LL + fn in_trait_impl_return() -> <() as DummyTrait>::Out { () }
|
||||||
|
|
|
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/where-allowed.rs:246:36
|
|
||||||
|
|
|
||||||
LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
|
||||||
| ^^^^^^^^^^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/where-allowed.rs:239:7
|
|
||||||
|
|
|
||||||
LL | impl <T = impl Debug> T {}
|
|
||||||
| ^^^^^^^^^^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
|
|
||||||
error[E0283]: type annotations needed
|
error[E0283]: type annotations needed
|
||||||
--> $DIR/where-allowed.rs:46:57
|
--> $DIR/where-allowed.rs:46:57
|
||||||
|
|
|
|
||||||
@@ -408,10 +389,10 @@ LL | fn in_impl_Fn_return_in_return() -> &'static impl Fn() -> impl Debug { pani
|
|||||||
where Args: Tuple, F: Fn<Args>, A: Allocator, F: ?Sized;
|
where Args: Tuple, F: Fn<Args>, A: Allocator, F: ?Sized;
|
||||||
|
|
||||||
error[E0118]: no nominal type found for inherent implementation
|
error[E0118]: no nominal type found for inherent implementation
|
||||||
--> $DIR/where-allowed.rs:239:1
|
--> $DIR/where-allowed.rs:240:1
|
||||||
|
|
|
|
||||||
LL | impl <T = impl Debug> T {}
|
LL | impl<T = impl Debug> T {}
|
||||||
| ^^^^^^^^^^^^^^^^^^^^^^^ impl requires a nominal type
|
| ^^^^^^^^^^^^^^^^^^^^^^ impl requires a nominal type
|
||||||
|
|
|
|
||||||
= note: either implement a trait on it or create a newtype to wrap it instead
|
= note: either implement a trait on it or create a newtype to wrap it instead
|
||||||
|
|
||||||
@@ -431,29 +412,21 @@ LL | type InTypeAlias<R> = impl Debug;
|
|||||||
|
|
|
|
||||||
= note: `InTypeAlias` must be used in combination with a concrete type within the same crate
|
= note: `InTypeAlias` must be used in combination with a concrete type within the same crate
|
||||||
|
|
||||||
error: aborting due to 50 previous errors
|
error: aborting due to 48 previous errors
|
||||||
|
|
||||||
Some errors have detailed explanations: E0053, E0118, E0283, E0562, E0658, E0666.
|
Some errors have detailed explanations: E0053, E0118, E0283, E0562, E0658, E0666.
|
||||||
For more information about an error, try `rustc --explain E0053`.
|
For more information about an error, try `rustc --explain E0053`.
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
Future incompatibility report: Future breakage diagnostic:
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
warning: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/where-allowed.rs:246:36
|
--> $DIR/where-allowed.rs:246:36
|
||||||
|
|
|
|
||||||
LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
LL | fn in_method_generic_param_default<T = impl Debug>(_: T) {}
|
||||||
| ^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
Future breakage diagnostic:
|
Future breakage diagnostic:
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
warning: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/where-allowed.rs:239:7
|
--> $DIR/where-allowed.rs:240:6
|
||||||
|
|
|
|
||||||
LL | impl <T = impl Debug> T {}
|
LL | impl<T = impl Debug> T {}
|
||||||
| ^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +0,0 @@
|
|||||||
fn avg<T=T::Item>(_: T) {}
|
|
||||||
//~^ ERROR generic parameter defaults cannot reference parameters before they are declared
|
|
||||||
//~| ERROR defaults for type parameters
|
|
||||||
//~| WARN previously accepted
|
|
||||||
|
|
||||||
fn main() {}
|
|
||||||
@@ -1,30 +0,0 @@
|
|||||||
error[E0128]: generic parameter defaults cannot reference parameters before they are declared
|
|
||||||
--> $DIR/issue-26812.rs:1:10
|
|
||||||
|
|
|
||||||
LL | fn avg<T=T::Item>(_: T) {}
|
|
||||||
| ^^^^^^^ cannot reference `T` before it is declared
|
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/issue-26812.rs:1:8
|
|
||||||
|
|
|
||||||
LL | fn avg<T=T::Item>(_: T) {}
|
|
||||||
| ^^^^^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
|
||||||
|
|
||||||
For more information about this error, try `rustc --explain E0128`.
|
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/issue-26812.rs:1:8
|
|
||||||
|
|
|
||||||
LL | fn avg<T=T::Item>(_: T) {}
|
|
||||||
| ^^^^^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
@@ -14,7 +14,7 @@ fn b<const C: u8()>() {}
|
|||||||
// Paren generic args in AnonymousReportError
|
// Paren generic args in AnonymousReportError
|
||||||
fn c<T = u8()>() {}
|
fn c<T = u8()>() {}
|
||||||
//~^ ERROR parenthesized type parameters may only be used with a `Fn` trait
|
//~^ ERROR parenthesized type parameters may only be used with a `Fn` trait
|
||||||
//~| ERROR defaults for type parameters are only allowed in
|
//~| ERROR defaults for generic parameters are not allowed here
|
||||||
//~| WARN this was previously accepted
|
//~| WARN this was previously accepted
|
||||||
|
|
||||||
// Elided lifetime in path in ConstGeneric
|
// Elided lifetime in path in ConstGeneric
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ error[E0214]: parenthesized type parameters may only be used with a `Fn` trait
|
|||||||
LL | fn c<T = u8()>() {}
|
LL | fn c<T = u8()>() {}
|
||||||
| ^^^^ only `Fn` traits may use parentheses
|
| ^^^^ only `Fn` traits may use parentheses
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/unusual-rib-combinations.rs:15:6
|
--> $DIR/unusual-rib-combinations.rs:15:6
|
||||||
|
|
|
|
||||||
LL | fn c<T = u8()>() {}
|
LL | fn c<T = u8()>() {}
|
||||||
@@ -43,7 +43,7 @@ error: aborting due to 6 previous errors
|
|||||||
Some errors have detailed explanations: E0106, E0214, E0308, E0770.
|
Some errors have detailed explanations: E0106, E0214, E0308, E0770.
|
||||||
For more information about an error, try `rustc --explain E0106`.
|
For more information about an error, try `rustc --explain E0106`.
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
Future incompatibility report: Future breakage diagnostic:
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/unusual-rib-combinations.rs:15:6
|
--> $DIR/unusual-rib-combinations.rs:15:6
|
||||||
|
|
|
|
||||||
LL | fn c<T = u8()>() {}
|
LL | fn c<T = u8()>() {}
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ impl X<N> {}
|
|||||||
//~| ERROR unresolved item provided when a constant was expected
|
//~| ERROR unresolved item provided when a constant was expected
|
||||||
impl<T, const A: u8 = 2> X<N> {}
|
impl<T, const A: u8 = 2> X<N> {}
|
||||||
//~^ ERROR cannot find type `N` in this scope
|
//~^ ERROR cannot find type `N` in this scope
|
||||||
//~| ERROR defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
//~| ERROR defaults for generic parameters are not allowed here
|
||||||
//~| ERROR unresolved item provided when a constant was expected
|
//~| ERROR unresolved item provided when a constant was expected
|
||||||
|
|
||||||
fn foo(_: T) where T: Send {}
|
fn foo(_: T) where T: Send {}
|
||||||
|
|||||||
@@ -103,7 +103,7 @@ help: if this generic argument was intended as a const parameter, surround it wi
|
|||||||
LL | impl X<{ N }> {}
|
LL | impl X<{ N }> {}
|
||||||
| + +
|
| + +
|
||||||
|
|
||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/missing-type-parameter2.rs:6:9
|
--> $DIR/missing-type-parameter2.rs:6:9
|
||||||
|
|
|
|
||||||
LL | impl<T, const A: u8 = 2> X<N> {}
|
LL | impl<T, const A: u8 = 2> X<N> {}
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ error: aborting due to 1 previous error
|
|||||||
|
|
||||||
For more information about this error, try `rustc --explain E0282`.
|
For more information about this error, try `rustc --explain E0282`.
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
Future incompatibility report: Future breakage diagnostic:
|
||||||
warning: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
warning: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/unbounded-type-param-in-fn-with-assoc-type.rs:3:11
|
--> $DIR/unbounded-type-param-in-fn-with-assoc-type.rs:3:11
|
||||||
|
|
|
|
||||||
LL | fn foo<T, U = u64>() -> (T, U) {
|
LL | fn foo<T, U = u64>() -> (T, U) {
|
||||||
|
|||||||
@@ -1,12 +0,0 @@
|
|||||||
#![allow(unused)]
|
|
||||||
|
|
||||||
fn avg<T=i32>(_: T) {}
|
|
||||||
//~^ ERROR defaults for type parameters are only allowed
|
|
||||||
//~| WARN this was previously accepted
|
|
||||||
|
|
||||||
struct S<T>(T);
|
|
||||||
impl<T=i32> S<T> {}
|
|
||||||
//~^ ERROR defaults for type parameters are only allowed
|
|
||||||
//~| WARN this was previously accepted
|
|
||||||
|
|
||||||
fn main() {}
|
|
||||||
@@ -1,43 +0,0 @@
|
|||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/default_type_parameter_in_fn_or_impl.rs:3:8
|
|
||||||
|
|
|
||||||
LL | fn avg<T=i32>(_: T) {}
|
|
||||||
| ^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/default_type_parameter_in_fn_or_impl.rs:8:6
|
|
||||||
|
|
|
||||||
LL | impl<T=i32> S<T> {}
|
|
||||||
| ^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
|
|
||||||
error: aborting due to 2 previous errors
|
|
||||||
|
|
||||||
Future incompatibility report: Future breakage diagnostic:
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/default_type_parameter_in_fn_or_impl.rs:3:8
|
|
||||||
|
|
|
||||||
LL | fn avg<T=i32>(_: T) {}
|
|
||||||
| ^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
Future breakage diagnostic:
|
|
||||||
error: defaults for type parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
|
||||||
--> $DIR/default_type_parameter_in_fn_or_impl.rs:8:6
|
|
||||||
|
|
|
||||||
LL | impl<T=i32> S<T> {}
|
|
||||||
| ^^^^^
|
|
||||||
|
|
|
||||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
|
||||||
= note: for more information, see issue #36887 <https://github.com/rust-lang/rust/issues/36887>
|
|
||||||
= note: `#[deny(invalid_type_param_default)]` on by default
|
|
||||||
|
|
||||||
@@ -4,7 +4,7 @@ trait Trait<const N: dyn Trait = bar> {
|
|||||||
fn fnc<const N: dyn Trait = u32>(&self) -> dyn Trait {
|
fn fnc<const N: dyn Trait = u32>(&self) -> dyn Trait {
|
||||||
//~^ ERROR the name `N` is already used for a generic parameter in this item's generic parameters
|
//~^ ERROR the name `N` is already used for a generic parameter in this item's generic parameters
|
||||||
//~| ERROR expected value, found builtin type `u32`
|
//~| ERROR expected value, found builtin type `u32`
|
||||||
//~| ERROR defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
//~| ERROR defaults for generic parameters are not allowed here
|
||||||
bar
|
bar
|
||||||
//~^ ERROR cannot find value `bar` in this scope
|
//~^ ERROR cannot find value `bar` in this scope
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -39,7 +39,7 @@ LL | trait Trait<const N: dyn Trait = bar> {
|
|||||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
= note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information
|
= note: see https://rustc-dev-guide.rust-lang.org/overview.html#queries and https://rustc-dev-guide.rust-lang.org/query.html for more information
|
||||||
|
|
||||||
error: defaults for const parameters are only allowed in `struct`, `enum`, `type`, or `trait` definitions
|
error: defaults for generic parameters are not allowed here
|
||||||
--> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:12
|
--> $DIR/ice-hir-wf-check-anon-const-issue-122199.rs:4:12
|
||||||
|
|
|
|
||||||
LL | fn fnc<const N: dyn Trait = u32>(&self) -> dyn Trait {
|
LL | fn fnc<const N: dyn Trait = u32>(&self) -> dyn Trait {
|
||||||
|
|||||||
Reference in New Issue
Block a user