mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-25 08:13:41 +00:00
Auto merge of #104179 - Manishearth:rollup-yvsx5hh, r=Manishearth
Rollup of 7 pull requests Successful merges: - #100508 (avoid making substs of type aliases late bound when used as fn args) - #101381 (Test that target feature mix up with homogeneous floats is sound) - #103353 (Fix Access Violation when using lld & ThinLTO on windows-msvc) - #103521 (Avoid possible infinite loop when next_point reaching the end of file) - #103559 (first move on a nested span_label) - #103778 (Update several crates for improved support of the new targets) - #103827 (Properly remap and check for substs compatibility in `confirm_impl_trait_in_trait_candidate`) Failed merges: r? `@ghost` `@rustbot` modify labels: rollup
This commit is contained in:
commit
91385d5776
64
Cargo.lock
64
Cargo.lock
@ -2496,7 +2496,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f"
|
||||
dependencies = [
|
||||
"lock_api",
|
||||
"parking_lot_core 0.9.3",
|
||||
"parking_lot_core 0.9.4",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -2515,15 +2515,15 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot_core"
|
||||
version = "0.9.3"
|
||||
version = "0.9.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929"
|
||||
checksum = "4dc9e0dc2adc1c69d09143aff38d3d30c5c3f0df0dad82e6d25547af174ebec0"
|
||||
dependencies = [
|
||||
"cfg-if 1.0.0",
|
||||
"libc",
|
||||
"redox_syscall",
|
||||
"smallvec",
|
||||
"windows-sys 0.36.1",
|
||||
"windows-sys 0.42.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -2748,9 +2748,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "psm"
|
||||
version = "0.1.16"
|
||||
version = "0.1.21"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cd136ff4382c4753fc061cb9e4712ab2af263376b95bbd5bd8cd50c020b78e69"
|
||||
checksum = "5787f7cda34e3033a72192c018bc5883100330f362ef279a8cbccfce8bb4e874"
|
||||
dependencies = [
|
||||
"cc",
|
||||
]
|
||||
@ -4651,9 +4651,9 @@ checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3"
|
||||
|
||||
[[package]]
|
||||
name = "stacker"
|
||||
version = "0.1.14"
|
||||
version = "0.1.15"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "90939d5171a4420b3ff5fbc8954d641e7377335454c259dcb80786f3f21dc9b4"
|
||||
checksum = "c886bd4480155fd3ef527d45e9ac8dd7118a898a46530b7b94c3e21866259fce"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"cfg-if 1.0.0",
|
||||
@ -5473,17 +5473,25 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2"
|
||||
checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7"
|
||||
dependencies = [
|
||||
"windows_aarch64_msvc 0.36.1",
|
||||
"windows_i686_gnu 0.36.1",
|
||||
"windows_i686_msvc 0.36.1",
|
||||
"windows_x86_64_gnu 0.36.1",
|
||||
"windows_x86_64_msvc 0.36.1",
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc 0.42.0",
|
||||
"windows_i686_gnu 0.42.0",
|
||||
"windows_i686_msvc 0.42.0",
|
||||
"windows_x86_64_gnu 0.42.0",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc 0.42.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "41d2aa71f6f0cbe00ae5167d90ef3cfe66527d6f613ca78ac8024c3ccab9a19e"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.28.0"
|
||||
@ -5492,9 +5500,9 @@ checksum = "52695a41e536859d5308cc613b4a022261a274390b25bd29dfff4bf08505f3c2"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47"
|
||||
checksum = "dd0f252f5a35cac83d6311b2e795981f5ee6e67eb1f9a7f64eb4500fbc4dcdb4"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
@ -5504,9 +5512,9 @@ checksum = "f54725ac23affef038fecb177de6c9bf065787c2f432f79e3c373da92f3e1d8a"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6"
|
||||
checksum = "fbeae19f6716841636c28d695375df17562ca208b2b7d0dc47635a50ae6c5de7"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
@ -5516,9 +5524,9 @@ checksum = "51d5158a43cc43623c0729d1ad6647e62fa384a3d135fd15108d37c683461f64"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024"
|
||||
checksum = "84c12f65daa39dd2babe6e442988fc329d6243fdce47d7d2d155b8d874862246"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
@ -5528,9 +5536,15 @@ checksum = "bc31f409f565611535130cfe7ee8e6655d3fa99c1c61013981e491921b5ce954"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1"
|
||||
checksum = "bf7b1b21b5362cbc318f686150e5bcea75ecedc74dd157d874d754a2ca44b0ed"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "09d525d2ba30eeb3297665bd434a54297e4170c7f1a44cad4ef58095b4cd2028"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
@ -5540,9 +5554,9 @@ checksum = "3f2b8c7cbd3bfdddd9ab98769f9746a7fad1bca236554cd032b78d768bc0e89f"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.36.1"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680"
|
||||
checksum = "f40009d85759725a34da6d89a94e63d7bdc50a862acf0dbc7c8e488f1edcb6f5"
|
||||
|
||||
[[package]]
|
||||
name = "xattr"
|
||||
|
@ -724,13 +724,19 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
|
||||
borrow_span,
|
||||
&self.describe_any_place(borrow.borrowed_place.as_ref()),
|
||||
);
|
||||
|
||||
borrow_spans.var_span_label(
|
||||
borrow_spans.var_subdiag(
|
||||
&mut err,
|
||||
{
|
||||
|var_span| {
|
||||
use crate::session_diagnostics::CaptureVarCause::*;
|
||||
let place = &borrow.borrowed_place;
|
||||
let desc_place = self.describe_any_place(place.as_ref());
|
||||
format!("borrow occurs due to use of {}{}", desc_place, borrow_spans.describe())
|
||||
match borrow_spans {
|
||||
UseSpans::ClosureUse { generator_kind, .. } => match generator_kind {
|
||||
Some(_) => BorrowUsePlaceGenerator { place: desc_place, var_span },
|
||||
None => BorrowUsePlaceClosure { place: desc_place, var_span },
|
||||
},
|
||||
_ => BorrowUsePlace { place: desc_place, var_span },
|
||||
}
|
||||
},
|
||||
"mutable",
|
||||
);
|
||||
|
@ -623,6 +623,26 @@ impl UseSpans<'_> {
|
||||
}
|
||||
}
|
||||
|
||||
/// Add a subdiagnostic to the use of the captured variable, if it exists.
|
||||
pub(super) fn var_subdiag(
|
||||
self,
|
||||
err: &mut Diagnostic,
|
||||
f: impl Fn(Span) -> crate::session_diagnostics::CaptureVarCause,
|
||||
kind_desc: impl Into<String>,
|
||||
) {
|
||||
if let UseSpans::ClosureUse { capture_kind_span, path_span, .. } = self {
|
||||
if capture_kind_span == path_span {
|
||||
err.subdiagnostic(f(capture_kind_span));
|
||||
} else {
|
||||
err.subdiagnostic(crate::session_diagnostics::CaptureVarKind {
|
||||
kind_desc: kind_desc.into(),
|
||||
kind_span: capture_kind_span,
|
||||
});
|
||||
err.subdiagnostic(f(path_span));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns `false` if this place is not used in a closure.
|
||||
pub(super) fn for_closure(&self) -> bool {
|
||||
match *self {
|
||||
|
@ -148,3 +148,33 @@ pub(crate) enum RequireStaticErr {
|
||||
multi_span: MultiSpan,
|
||||
},
|
||||
}
|
||||
|
||||
#[derive(Subdiagnostic)]
|
||||
#[label(borrowck_capture_kind_label)]
|
||||
pub(crate) struct CaptureVarKind {
|
||||
pub kind_desc: String,
|
||||
#[primary_span]
|
||||
pub kind_span: Span,
|
||||
}
|
||||
|
||||
#[derive(Subdiagnostic)]
|
||||
pub(crate) enum CaptureVarCause {
|
||||
#[label(borrowck_var_borrow_by_use_place)]
|
||||
BorrowUsePlace {
|
||||
place: String,
|
||||
#[primary_span]
|
||||
var_span: Span,
|
||||
},
|
||||
#[label(borrowck_var_borrow_by_use_place_in_generator)]
|
||||
BorrowUsePlaceGenerator {
|
||||
place: String,
|
||||
#[primary_span]
|
||||
var_span: Span,
|
||||
},
|
||||
#[label(borrowck_var_borrow_by_use_place_in_closure)]
|
||||
BorrowUsePlaceClosure {
|
||||
place: String,
|
||||
#[primary_span]
|
||||
var_span: Span,
|
||||
},
|
||||
}
|
||||
|
@ -19,6 +19,7 @@ use rustc_middle::mir::mono::MonoItem;
|
||||
use rustc_middle::ty::layout::LayoutOf;
|
||||
use rustc_middle::ty::{self, Instance, Ty};
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_session::config::Lto;
|
||||
use rustc_target::abi::{
|
||||
AddressSpace, Align, HasDataLayout, Primitive, Scalar, Size, WrappingRange,
|
||||
};
|
||||
@ -303,7 +304,8 @@ impl<'ll> CodegenCx<'ll, '_> {
|
||||
// ThinLTO can't handle this workaround in all cases, so we don't
|
||||
// emit the attrs. Instead we make them unnecessary by disallowing
|
||||
// dynamic linking when linker plugin based LTO is enabled.
|
||||
!self.tcx.sess.opts.cg.linker_plugin_lto.enabled();
|
||||
!self.tcx.sess.opts.cg.linker_plugin_lto.enabled() &&
|
||||
self.tcx.sess.lto() != Lto::Thin;
|
||||
|
||||
// If this assertion triggers, there's something wrong with commandline
|
||||
// argument validation.
|
||||
|
@ -23,7 +23,7 @@ rustc_macros = { path = "../rustc_macros" }
|
||||
rustc_serialize = { path = "../rustc_serialize" }
|
||||
smallvec = { version = "1.8.1", features = ["const_generics", "union", "may_dangle"] }
|
||||
stable_deref_trait = "1.0.0"
|
||||
stacker = "0.1.14"
|
||||
stacker = "0.1.15"
|
||||
tempfile = "3.2"
|
||||
thin-vec = "0.2.9"
|
||||
tracing = "0.1"
|
||||
|
@ -58,3 +58,15 @@ borrowck_returned_lifetime_short =
|
||||
|
||||
borrowck_used_impl_require_static =
|
||||
the used `impl` has a `'static` requirement
|
||||
|
||||
borrowck_capture_kind_label =
|
||||
capture is {$kind_desc} because of use here
|
||||
|
||||
borrowck_var_borrow_by_use_place_in_generator =
|
||||
borrow occurs due to use of {$place} in closure in generator
|
||||
|
||||
borrowck_var_borrow_by_use_place_in_closure =
|
||||
borrow occurs due to use of {$place} in closure
|
||||
|
||||
borrowck_var_borrow_by_use_place =
|
||||
borrow occurs due to use of {$place}
|
||||
|
@ -18,7 +18,7 @@ use rustc_middle::bug;
|
||||
use rustc_middle::hir::map::Map;
|
||||
use rustc_middle::hir::nested_filter;
|
||||
use rustc_middle::middle::resolve_lifetime::*;
|
||||
use rustc_middle::ty::{self, DefIdTree, TyCtxt};
|
||||
use rustc_middle::ty::{self, DefIdTree, TyCtxt, TypeSuperVisitable, TypeVisitor};
|
||||
use rustc_span::def_id::DefId;
|
||||
use rustc_span::symbol::{sym, Ident};
|
||||
use rustc_span::Span;
|
||||
@ -1781,7 +1781,7 @@ fn is_late_bound_map(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<&FxIndexSet<
|
||||
|
||||
let mut late_bound = FxIndexSet::default();
|
||||
|
||||
let mut constrained_by_input = ConstrainedCollector::default();
|
||||
let mut constrained_by_input = ConstrainedCollector { regions: Default::default(), tcx };
|
||||
for arg_ty in decl.inputs {
|
||||
constrained_by_input.visit_ty(arg_ty);
|
||||
}
|
||||
@ -1834,12 +1834,65 @@ fn is_late_bound_map(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<&FxIndexSet<
|
||||
debug!(?late_bound);
|
||||
return Some(tcx.arena.alloc(late_bound));
|
||||
|
||||
#[derive(Default)]
|
||||
struct ConstrainedCollector {
|
||||
/// Visits a `ty::Ty` collecting information about what generic parameters are constrained.
|
||||
///
|
||||
/// The visitor does not operate on `hir::Ty` so that it can be called on the rhs of a `type Alias<...> = ...;`
|
||||
/// which may live in a separate crate so there would not be any hir available. Instead we use the `type_of`
|
||||
/// query to obtain a `ty::Ty` which will be present even in cross crate scenarios. It also naturally
|
||||
/// handles cycle detection as we go through the query system.
|
||||
///
|
||||
/// This is necessary in the first place for the following case:
|
||||
/// ```
|
||||
/// type Alias<'a, T> = <T as Trait<'a>>::Assoc;
|
||||
/// fn foo<'a>(_: Alias<'a, ()>) -> Alias<'a, ()> { ... }
|
||||
/// ```
|
||||
///
|
||||
/// If we conservatively considered `'a` unconstrained then we could break users who had written code before
|
||||
/// we started correctly handling aliases. If we considered `'a` constrained then it would become late bound
|
||||
/// causing an error during astconv as the `'a` is not constrained by the input type `<() as Trait<'a>>::Assoc`
|
||||
/// but appears in the output type `<() as Trait<'a>>::Assoc`.
|
||||
///
|
||||
/// We must therefore "look into" the `Alias` to see whether we should consider `'a` constrained or not.
|
||||
///
|
||||
/// See #100508 #85533 #47511 for additional context
|
||||
struct ConstrainedCollectorPostAstConv {
|
||||
arg_is_constrained: Box<[bool]>,
|
||||
}
|
||||
|
||||
use std::ops::ControlFlow;
|
||||
use ty::Ty;
|
||||
impl<'tcx> TypeVisitor<'tcx> for ConstrainedCollectorPostAstConv {
|
||||
fn visit_ty(&mut self, t: Ty<'tcx>) -> ControlFlow<!> {
|
||||
match t.kind() {
|
||||
ty::Param(param_ty) => {
|
||||
self.arg_is_constrained[param_ty.index as usize] = true;
|
||||
}
|
||||
ty::Projection(_) => return ControlFlow::Continue(()),
|
||||
_ => (),
|
||||
}
|
||||
t.super_visit_with(self)
|
||||
}
|
||||
|
||||
fn visit_const(&mut self, _: ty::Const<'tcx>) -> ControlFlow<!> {
|
||||
ControlFlow::Continue(())
|
||||
}
|
||||
|
||||
fn visit_region(&mut self, r: ty::Region<'tcx>) -> ControlFlow<!> {
|
||||
debug!("r={:?}", r.kind());
|
||||
if let ty::RegionKind::ReEarlyBound(region) = r.kind() {
|
||||
self.arg_is_constrained[region.index as usize] = true;
|
||||
}
|
||||
|
||||
ControlFlow::Continue(())
|
||||
}
|
||||
}
|
||||
|
||||
struct ConstrainedCollector<'tcx> {
|
||||
tcx: TyCtxt<'tcx>,
|
||||
regions: FxHashSet<LocalDefId>,
|
||||
}
|
||||
|
||||
impl<'v> Visitor<'v> for ConstrainedCollector {
|
||||
impl<'v> Visitor<'v> for ConstrainedCollector<'_> {
|
||||
fn visit_ty(&mut self, ty: &'v hir::Ty<'v>) {
|
||||
match ty.kind {
|
||||
hir::TyKind::Path(
|
||||
@ -1850,6 +1903,47 @@ fn is_late_bound_map(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Option<&FxIndexSet<
|
||||
// (defined above)
|
||||
}
|
||||
|
||||
hir::TyKind::Path(hir::QPath::Resolved(
|
||||
None,
|
||||
hir::Path { res: Res::Def(DefKind::TyAlias, alias_def), segments, span },
|
||||
)) => {
|
||||
// See comments on `ConstrainedCollectorPostAstConv` for why this arm does not just consider
|
||||
// substs to be unconstrained.
|
||||
let generics = self.tcx.generics_of(alias_def);
|
||||
let mut walker = ConstrainedCollectorPostAstConv {
|
||||
arg_is_constrained: vec![false; generics.params.len()].into_boxed_slice(),
|
||||
};
|
||||
walker.visit_ty(self.tcx.type_of(alias_def));
|
||||
|
||||
match segments.last() {
|
||||
Some(hir::PathSegment { args: Some(args), .. }) => {
|
||||
let tcx = self.tcx;
|
||||
for constrained_arg in
|
||||
args.args.iter().enumerate().flat_map(|(n, arg)| {
|
||||
match walker.arg_is_constrained.get(n) {
|
||||
Some(true) => Some(arg),
|
||||
Some(false) => None,
|
||||
None => {
|
||||
tcx.sess.delay_span_bug(
|
||||
*span,
|
||||
format!(
|
||||
"Incorrect generic arg count for alias {:?}",
|
||||
alias_def
|
||||
),
|
||||
);
|
||||
None
|
||||
}
|
||||
}
|
||||
})
|
||||
{
|
||||
self.visit_generic_arg(constrained_arg);
|
||||
}
|
||||
}
|
||||
Some(_) => (),
|
||||
None => bug!("Path with no segments or self type"),
|
||||
}
|
||||
}
|
||||
|
||||
hir::TyKind::Path(hir::QPath::Resolved(None, ref path)) => {
|
||||
// consider only the lifetimes on the final
|
||||
// segment; I am not sure it's even currently
|
||||
|
@ -430,7 +430,9 @@ impl<'tcx> TyCtxt<'tcx> {
|
||||
(ty::Projection(_), ty::Projection(_)) => {
|
||||
diag.note("an associated type was expected, but a different one was found");
|
||||
}
|
||||
(ty::Param(p), ty::Projection(proj)) | (ty::Projection(proj), ty::Param(p)) => {
|
||||
(ty::Param(p), ty::Projection(proj)) | (ty::Projection(proj), ty::Param(p))
|
||||
if self.def_kind(proj.item_def_id) != DefKind::ImplTraitPlaceholder =>
|
||||
{
|
||||
let generics = self.generics_of(body_owner_def_id);
|
||||
let p_span = self.def_span(generics.type_param(p, self).def_id);
|
||||
if !sp.contains(p_span) {
|
||||
|
@ -855,7 +855,8 @@ impl SourceMap {
|
||||
/// Returns a new span representing the next character after the end-point of this span.
|
||||
/// Special cases:
|
||||
/// - if span is a dummy one, returns the same span
|
||||
/// - if next_point reached the end of source, return span with lo = hi
|
||||
/// - if next_point reached the end of source, return a span exceeding the end of source,
|
||||
/// which means sm.span_to_snippet(next_point) will get `Err`
|
||||
/// - respect multi-byte characters
|
||||
pub fn next_point(&self, sp: Span) -> Span {
|
||||
if sp.is_dummy() {
|
||||
@ -864,9 +865,6 @@ impl SourceMap {
|
||||
let start_of_next_point = sp.hi().0;
|
||||
|
||||
let width = self.find_width_of_character_at_span(sp, true);
|
||||
if width == 0 {
|
||||
return Span::new(sp.hi(), sp.hi(), sp.ctxt(), None);
|
||||
}
|
||||
// If the width is 1, then the next span should only contain the next char besides current ending.
|
||||
// However, in the case of a multibyte character, where the width != 1, the next span should
|
||||
// span multiple bytes to include the whole character.
|
||||
@ -938,7 +936,7 @@ impl SourceMap {
|
||||
// Ensure indexes are also not malformed.
|
||||
if start_index > end_index || end_index > source_len - 1 {
|
||||
debug!("find_width_of_character_at_span: source indexes are malformed");
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
let src = local_begin.sf.external_src.borrow();
|
||||
|
@ -511,16 +511,17 @@ fn test_next_point() {
|
||||
assert_eq!(span.lo().0, 4);
|
||||
assert_eq!(span.hi().0, 5);
|
||||
|
||||
// A non-empty span at the last byte should advance to create an empty
|
||||
// span pointing at the end of the file.
|
||||
// Reaching to the end of file, return a span that will get error with `span_to_snippet`
|
||||
let span = Span::with_root_ctxt(BytePos(4), BytePos(5));
|
||||
let span = sm.next_point(span);
|
||||
assert_eq!(span.lo().0, 5);
|
||||
assert_eq!(span.hi().0, 5);
|
||||
assert_eq!(span.hi().0, 6);
|
||||
assert!(sm.span_to_snippet(span).is_err());
|
||||
|
||||
// Empty span pointing just past the last byte.
|
||||
// Reaching to the end of file, return a span that will get error with `span_to_snippet`
|
||||
let span = Span::with_root_ctxt(BytePos(5), BytePos(5));
|
||||
let span = sm.next_point(span);
|
||||
assert_eq!(span.lo().0, 5);
|
||||
assert_eq!(span.hi().0, 5);
|
||||
assert_eq!(span.hi().0, 6);
|
||||
assert!(sm.span_to_snippet(span).is_err());
|
||||
}
|
||||
|
@ -2187,7 +2187,7 @@ fn confirm_impl_candidate<'cx, 'tcx>(
|
||||
// Verify that the trait item and its implementation have compatible substs lists
|
||||
fn check_substs_compatible<'tcx>(
|
||||
tcx: TyCtxt<'tcx>,
|
||||
assoc_ty: &ty::AssocItem,
|
||||
assoc_item: &ty::AssocItem,
|
||||
substs: ty::SubstsRef<'tcx>,
|
||||
) -> bool {
|
||||
fn check_substs_compatible_inner<'tcx>(
|
||||
@ -2219,7 +2219,10 @@ fn check_substs_compatible<'tcx>(
|
||||
true
|
||||
}
|
||||
|
||||
check_substs_compatible_inner(tcx, tcx.generics_of(assoc_ty.def_id), substs.as_slice())
|
||||
let generics = tcx.generics_of(assoc_item.def_id);
|
||||
// Chop off any additional substs (RPITIT) substs
|
||||
let substs = &substs[0..generics.count().min(substs.len())];
|
||||
check_substs_compatible_inner(tcx, generics, substs)
|
||||
}
|
||||
|
||||
fn confirm_impl_trait_in_trait_candidate<'tcx>(
|
||||
@ -2248,11 +2251,27 @@ fn confirm_impl_trait_in_trait_candidate<'tcx>(
|
||||
};
|
||||
}
|
||||
|
||||
let impl_fn_def_id = leaf_def.item.def_id;
|
||||
// Rebase from {trait}::{fn}::{opaque} to {impl}::{fn}::{opaque},
|
||||
// since `data.substs` are the impl substs.
|
||||
let impl_fn_substs =
|
||||
obligation.predicate.substs.rebase_onto(tcx, tcx.parent(trait_fn_def_id), data.substs);
|
||||
let impl_fn_substs = translate_substs(
|
||||
selcx.infcx(),
|
||||
obligation.param_env,
|
||||
data.impl_def_id,
|
||||
impl_fn_substs,
|
||||
leaf_def.defining_node,
|
||||
);
|
||||
|
||||
if !check_substs_compatible(tcx, &leaf_def.item, impl_fn_substs) {
|
||||
let err = tcx.ty_error_with_message(
|
||||
obligation.cause.span,
|
||||
"impl method and trait method have different parameters",
|
||||
);
|
||||
return Progress { term: err.into(), obligations };
|
||||
}
|
||||
|
||||
let impl_fn_def_id = leaf_def.item.def_id;
|
||||
|
||||
let cause = ObligationCause::new(
|
||||
obligation.cause.span,
|
||||
|
@ -224,13 +224,13 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "fd-lock"
|
||||
version = "3.0.6"
|
||||
version = "3.0.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e11dcc7e4d79a8c89b9ab4c6f5c30b1fc4a83c420792da3542fd31179ed5f517"
|
||||
checksum = "0c93a581058d957dc4176875aad04f82f81613e6611d64aa1a9c755bdfb16711"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"rustix",
|
||||
"windows-sys",
|
||||
"windows-sys 0.42.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -528,7 +528,7 @@ dependencies = [
|
||||
"io-lifetimes",
|
||||
"libc",
|
||||
"linux-raw-sys",
|
||||
"windows-sys",
|
||||
"windows-sys 0.36.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -721,43 +721,100 @@ version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2"
|
||||
dependencies = [
|
||||
"windows_aarch64_msvc",
|
||||
"windows_i686_gnu",
|
||||
"windows_i686_msvc",
|
||||
"windows_x86_64_gnu",
|
||||
"windows_x86_64_msvc",
|
||||
"windows_aarch64_msvc 0.36.1",
|
||||
"windows_i686_gnu 0.36.1",
|
||||
"windows_i686_msvc 0.36.1",
|
||||
"windows_x86_64_gnu 0.36.1",
|
||||
"windows_x86_64_msvc 0.36.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc 0.42.0",
|
||||
"windows_i686_gnu 0.42.0",
|
||||
"windows_i686_msvc 0.42.0",
|
||||
"windows_x86_64_gnu 0.42.0",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc 0.42.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "41d2aa71f6f0cbe00ae5167d90ef3cfe66527d6f613ca78ac8024c3ccab9a19e"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dd0f252f5a35cac83d6311b2e795981f5ee6e67eb1f9a7f64eb4500fbc4dcdb4"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fbeae19f6716841636c28d695375df17562ca208b2b7d0dc47635a50ae6c5de7"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "84c12f65daa39dd2babe6e442988fc329d6243fdce47d7d2d155b8d874862246"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bf7b1b21b5362cbc318f686150e5bcea75ecedc74dd157d874d754a2ca44b0ed"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "09d525d2ba30eeb3297665bd434a54297e4170c7f1a44cad4ef58095b4cd2028"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.42.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f40009d85759725a34da6d89a94e63d7bdc50a862acf0dbc7c8e488f1edcb6f5"
|
||||
|
||||
[[package]]
|
||||
name = "xattr"
|
||||
version = "0.2.3"
|
||||
|
@ -36,7 +36,7 @@ test = false
|
||||
|
||||
[dependencies]
|
||||
cmake = "0.1.38"
|
||||
fd-lock = "3.0.6"
|
||||
fd-lock = "3.0.7"
|
||||
filetime = "0.2"
|
||||
getopts = "0.2.19"
|
||||
cc = "1.0.69"
|
||||
|
13
src/test/codegen/auxiliary/static_dllimport_aux.rs
Normal file
13
src/test/codegen/auxiliary/static_dllimport_aux.rs
Normal file
@ -0,0 +1,13 @@
|
||||
use std::sync::atomic::{AtomicPtr, Ordering};
|
||||
|
||||
#[inline(always)]
|
||||
pub fn memrchr() {
|
||||
fn detect() {}
|
||||
|
||||
static CROSS_CRATE_STATIC_ITEM: AtomicPtr<()> = AtomicPtr::new(detect as *mut ());
|
||||
|
||||
unsafe {
|
||||
let fun = CROSS_CRATE_STATIC_ITEM.load(Ordering::SeqCst);
|
||||
std::mem::transmute::<*mut (), fn()>(fun)()
|
||||
}
|
||||
}
|
15
src/test/codegen/issue-81408-dllimport-thinlto-windows.rs
Normal file
15
src/test/codegen/issue-81408-dllimport-thinlto-windows.rs
Normal file
@ -0,0 +1,15 @@
|
||||
// compile-flags: -O -C lto=thin -C prefer-dynamic=no
|
||||
// only-windows
|
||||
// aux-build:static_dllimport_aux.rs
|
||||
|
||||
// Test that on Windows, when performing ThinLTO, we do not mark cross-crate static items with
|
||||
// dllimport because lld does not fix the symbol names for us.
|
||||
|
||||
extern crate static_dllimport_aux;
|
||||
|
||||
// CHECK-LABEL: @{{.+}}CROSS_CRATE_STATIC_ITEM{{.+}} =
|
||||
// CHECK-SAME: external local_unnamed_addr global %"{{.+}}AtomicPtr
|
||||
|
||||
pub fn main() {
|
||||
static_dllimport_aux::memrchr();
|
||||
}
|
192
src/test/ui/abi/homogenous-floats-target-feature-mixup.rs
Normal file
192
src/test/ui/abi/homogenous-floats-target-feature-mixup.rs
Normal file
@ -0,0 +1,192 @@
|
||||
// This test check that even if we mixup target feature of function with homogenous floats,
|
||||
// the abi is sound and still produce the right answer.
|
||||
//
|
||||
// This is basically the same test as src/test/ui/simd/target-feature-mixup.rs but for floats and
|
||||
// without #[repr(simd)]
|
||||
|
||||
// run-pass
|
||||
// ignore-emscripten
|
||||
// ignore-sgx no processes
|
||||
|
||||
#![feature(avx512_target_feature)]
|
||||
|
||||
#![allow(overflowing_literals)]
|
||||
#![allow(unused_variables)]
|
||||
|
||||
use std::process::{Command, ExitStatus};
|
||||
use std::env;
|
||||
|
||||
fn main() {
|
||||
if let Some(level) = env::args().nth(1) {
|
||||
return test::main(&level)
|
||||
}
|
||||
|
||||
match std::env::var("TARGET") {
|
||||
Ok(s) => {
|
||||
// Skip this tests on i586-unknown-linux-gnu where sse2 is disabled
|
||||
if s.contains("i586") {
|
||||
return
|
||||
}
|
||||
}
|
||||
Err(_) => return,
|
||||
}
|
||||
|
||||
let me = env::current_exe().unwrap();
|
||||
for level in ["sse", "avx", "avx512"].iter() {
|
||||
let status = Command::new(&me).arg(level).status().unwrap();
|
||||
if status.success() {
|
||||
println!("success with {}", level);
|
||||
continue
|
||||
}
|
||||
|
||||
// We don't actually know if our computer has the requisite target features
|
||||
// for the test below. Testing for that will get added to libstd later so
|
||||
// for now just assume sigill means this is a machine that can't run this test.
|
||||
if is_sigill(status) {
|
||||
println!("sigill with {}, assuming spurious", level);
|
||||
continue
|
||||
}
|
||||
panic!("invalid status at {}: {}", level, status);
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(unix)]
|
||||
fn is_sigill(status: ExitStatus) -> bool {
|
||||
use std::os::unix::prelude::*;
|
||||
status.signal() == Some(4)
|
||||
}
|
||||
|
||||
#[cfg(windows)]
|
||||
fn is_sigill(status: ExitStatus) -> bool {
|
||||
status.code() == Some(0xc000001d)
|
||||
}
|
||||
|
||||
#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
|
||||
#[allow(nonstandard_style)]
|
||||
mod test {
|
||||
#[derive(PartialEq, Debug, Clone, Copy)]
|
||||
struct f32x2(f32, f32);
|
||||
|
||||
#[derive(PartialEq, Debug, Clone, Copy)]
|
||||
struct f32x4(f32, f32, f32, f32);
|
||||
|
||||
#[derive(PartialEq, Debug, Clone, Copy)]
|
||||
struct f32x8(f32, f32, f32, f32, f32, f32, f32, f32);
|
||||
|
||||
pub fn main(level: &str) {
|
||||
unsafe {
|
||||
main_normal(level);
|
||||
main_sse(level);
|
||||
if level == "sse" {
|
||||
return
|
||||
}
|
||||
main_avx(level);
|
||||
if level == "avx" {
|
||||
return
|
||||
}
|
||||
main_avx512(level);
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! mains {
|
||||
($(
|
||||
$(#[$attr:meta])*
|
||||
unsafe fn $main:ident(level: &str) {
|
||||
...
|
||||
}
|
||||
)*) => ($(
|
||||
$(#[$attr])*
|
||||
unsafe fn $main(level: &str) {
|
||||
let m128 = f32x2(1., 2.);
|
||||
let m256 = f32x4(3., 4., 5., 6.);
|
||||
let m512 = f32x8(7., 8., 9., 10., 11., 12., 13., 14.);
|
||||
assert_eq!(id_sse_128(m128), m128);
|
||||
assert_eq!(id_sse_256(m256), m256);
|
||||
assert_eq!(id_sse_512(m512), m512);
|
||||
|
||||
if level == "sse" {
|
||||
return
|
||||
}
|
||||
assert_eq!(id_avx_128(m128), m128);
|
||||
assert_eq!(id_avx_256(m256), m256);
|
||||
assert_eq!(id_avx_512(m512), m512);
|
||||
|
||||
if level == "avx" {
|
||||
return
|
||||
}
|
||||
assert_eq!(id_avx512_128(m128), m128);
|
||||
assert_eq!(id_avx512_256(m256), m256);
|
||||
assert_eq!(id_avx512_512(m512), m512);
|
||||
}
|
||||
)*)
|
||||
}
|
||||
|
||||
mains! {
|
||||
unsafe fn main_normal(level: &str) { ... }
|
||||
#[target_feature(enable = "sse2")]
|
||||
unsafe fn main_sse(level: &str) { ... }
|
||||
#[target_feature(enable = "avx")]
|
||||
unsafe fn main_avx(level: &str) { ... }
|
||||
#[target_feature(enable = "avx512bw")]
|
||||
unsafe fn main_avx512(level: &str) { ... }
|
||||
}
|
||||
|
||||
#[target_feature(enable = "sse2")]
|
||||
unsafe fn id_sse_128(a: f32x2) -> f32x2 {
|
||||
assert_eq!(a, f32x2(1., 2.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "sse2")]
|
||||
unsafe fn id_sse_256(a: f32x4) -> f32x4 {
|
||||
assert_eq!(a, f32x4(3., 4., 5., 6.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "sse2")]
|
||||
unsafe fn id_sse_512(a: f32x8) -> f32x8 {
|
||||
assert_eq!(a, f32x8(7., 8., 9., 10., 11., 12., 13., 14.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx")]
|
||||
unsafe fn id_avx_128(a: f32x2) -> f32x2 {
|
||||
assert_eq!(a, f32x2(1., 2.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx")]
|
||||
unsafe fn id_avx_256(a: f32x4) -> f32x4 {
|
||||
assert_eq!(a, f32x4(3., 4., 5., 6.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx")]
|
||||
unsafe fn id_avx_512(a: f32x8) -> f32x8 {
|
||||
assert_eq!(a, f32x8(7., 8., 9., 10., 11., 12., 13., 14.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx512bw")]
|
||||
unsafe fn id_avx512_128(a: f32x2) -> f32x2 {
|
||||
assert_eq!(a, f32x2(1., 2.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx512bw")]
|
||||
unsafe fn id_avx512_256(a: f32x4) -> f32x4 {
|
||||
assert_eq!(a, f32x4(3., 4., 5., 6.));
|
||||
a.clone()
|
||||
}
|
||||
|
||||
#[target_feature(enable = "avx512bw")]
|
||||
unsafe fn id_avx512_512(a: f32x8) -> f32x8 {
|
||||
assert_eq!(a, f32x8(7., 8., 9., 10., 11., 12., 13., 14.));
|
||||
a.clone()
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(any(target_arch = "x86", target_arch = "x86_64")))]
|
||||
mod test {
|
||||
pub fn main(level: &str) {}
|
||||
}
|
17
src/test/ui/impl-trait/in-trait/generics-mismatch.rs
Normal file
17
src/test/ui/impl-trait/in-trait/generics-mismatch.rs
Normal file
@ -0,0 +1,17 @@
|
||||
#![feature(return_position_impl_trait_in_trait)]
|
||||
#![allow(incomplete_features)]
|
||||
|
||||
struct U;
|
||||
|
||||
trait Foo {
|
||||
fn bar(&self) -> impl Sized;
|
||||
}
|
||||
|
||||
impl Foo for U {
|
||||
fn bar<T>(&self) {}
|
||||
//~^ ERROR method `bar` has 1 type parameter but its trait declaration has 0 type parameters
|
||||
}
|
||||
|
||||
fn main() {
|
||||
U.bar();
|
||||
}
|
12
src/test/ui/impl-trait/in-trait/generics-mismatch.stderr
Normal file
12
src/test/ui/impl-trait/in-trait/generics-mismatch.stderr
Normal file
@ -0,0 +1,12 @@
|
||||
error[E0049]: method `bar` has 1 type parameter but its trait declaration has 0 type parameters
|
||||
--> $DIR/generics-mismatch.rs:11:12
|
||||
|
|
||||
LL | fn bar(&self) -> impl Sized;
|
||||
| - expected 0 type parameters
|
||||
...
|
||||
LL | fn bar<T>(&self) {}
|
||||
| ^ found 1 type parameter
|
||||
|
||||
error: aborting due to previous error
|
||||
|
||||
For more information about this error, try `rustc --explain E0049`.
|
26
src/test/ui/impl-trait/in-trait/specialization-broken.rs
Normal file
26
src/test/ui/impl-trait/in-trait/specialization-broken.rs
Normal file
@ -0,0 +1,26 @@
|
||||
// FIXME(compiler-errors): I'm not exactly sure if this is expected to pass or not.
|
||||
// But we fixed an ICE anyways.
|
||||
|
||||
#![feature(specialization)]
|
||||
#![feature(return_position_impl_trait_in_trait)]
|
||||
#![allow(incomplete_features)]
|
||||
|
||||
trait Foo {
|
||||
fn bar(&self) -> impl Sized;
|
||||
}
|
||||
|
||||
default impl<U> Foo for U
|
||||
where
|
||||
U: Copy,
|
||||
{
|
||||
fn bar(&self) -> U {
|
||||
//~^ ERROR method `bar` has an incompatible type for trait
|
||||
*self
|
||||
}
|
||||
}
|
||||
|
||||
impl Foo for i32 {}
|
||||
|
||||
fn main() {
|
||||
1i32.bar();
|
||||
}
|
23
src/test/ui/impl-trait/in-trait/specialization-broken.stderr
Normal file
23
src/test/ui/impl-trait/in-trait/specialization-broken.stderr
Normal file
@ -0,0 +1,23 @@
|
||||
error[E0053]: method `bar` has an incompatible type for trait
|
||||
--> $DIR/specialization-broken.rs:16:22
|
||||
|
|
||||
LL | default impl<U> Foo for U
|
||||
| - this type parameter
|
||||
...
|
||||
LL | fn bar(&self) -> U {
|
||||
| ^
|
||||
| |
|
||||
| expected associated type, found type parameter `U`
|
||||
| help: change the output type to match the trait: `impl Sized`
|
||||
|
|
||||
note: type in trait
|
||||
--> $DIR/specialization-broken.rs:9:22
|
||||
|
|
||||
LL | fn bar(&self) -> impl Sized;
|
||||
| ^^^^^^^^^^
|
||||
= note: expected fn pointer `fn(&U) -> impl Sized`
|
||||
found fn pointer `fn(&U) -> U`
|
||||
|
||||
error: aborting due to previous error
|
||||
|
||||
For more information about this error, try `rustc --explain E0053`.
|
@ -0,0 +1,24 @@
|
||||
// check-pass
|
||||
|
||||
#![feature(specialization)]
|
||||
#![feature(return_position_impl_trait_in_trait)]
|
||||
#![allow(incomplete_features)]
|
||||
|
||||
trait Foo {
|
||||
fn bar(&self) -> impl Sized;
|
||||
}
|
||||
|
||||
impl<U> Foo for U
|
||||
where
|
||||
U: Copy,
|
||||
{
|
||||
fn bar(&self) -> U {
|
||||
*self
|
||||
}
|
||||
}
|
||||
|
||||
impl Foo for i32 {}
|
||||
|
||||
fn main() {
|
||||
let _: i32 = 1i32.bar();
|
||||
}
|
@ -1,18 +0,0 @@
|
||||
error[E0581]: return type references an anonymous lifetime, which is not constrained by the fn input types
|
||||
--> $DIR/issue-47511.rs:8:15
|
||||
|
|
||||
LL | fn f(_: X) -> X {
|
||||
| ^
|
||||
|
|
||||
= note: lifetimes appearing in an associated or opaque type are not considered constrained
|
||||
= note: consider introducing a named lifetime parameter
|
||||
|
||||
error[E0581]: return type references lifetime `'a`, which is not constrained by the fn input types
|
||||
--> $DIR/issue-47511.rs:12:23
|
||||
|
|
||||
LL | fn g<'a>(_: X<'a>) -> X<'a> {
|
||||
| ^^^^^
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0581`.
|
@ -0,0 +1,5 @@
|
||||
pub trait Trait<'a> {
|
||||
type Assoc;
|
||||
}
|
||||
|
||||
pub type Alias<'a, T> = <T as Trait<'a>>::Assoc;
|
10
src/test/ui/late-bound-lifetimes/cross_crate_alias.rs
Normal file
10
src/test/ui/late-bound-lifetimes/cross_crate_alias.rs
Normal file
@ -0,0 +1,10 @@
|
||||
// aux-build:upstream_alias.rs
|
||||
// check-pass
|
||||
|
||||
extern crate upstream_alias;
|
||||
|
||||
fn foo<'a, T: for<'b> upstream_alias::Trait<'b>>(_: upstream_alias::Alias<'a, T>) -> &'a () {
|
||||
todo!()
|
||||
}
|
||||
|
||||
fn main() {}
|
@ -0,0 +1,24 @@
|
||||
// check-pass
|
||||
|
||||
trait Gats<'a> {
|
||||
type Assoc;
|
||||
type Assoc2;
|
||||
}
|
||||
|
||||
trait Trait: for<'a> Gats<'a> {
|
||||
fn foo<'a>(_: &mut <Self as Gats<'a>>::Assoc) -> <Self as Gats<'a>>::Assoc2;
|
||||
}
|
||||
|
||||
impl<'a> Gats<'a> for () {
|
||||
type Assoc = &'a u32;
|
||||
type Assoc2 = ();
|
||||
}
|
||||
|
||||
type GatsAssoc<'a, T> = <T as Gats<'a>>::Assoc;
|
||||
type GatsAssoc2<'a, T> = <T as Gats<'a>>::Assoc2;
|
||||
|
||||
impl Trait for () {
|
||||
fn foo<'a>(_: &mut GatsAssoc<'a, Self>) -> GatsAssoc2<'a, Self> {}
|
||||
}
|
||||
|
||||
fn main() {}
|
@ -1,9 +1,4 @@
|
||||
// check-fail
|
||||
// known-bug: #47511
|
||||
|
||||
// Regression test for #47511: anonymous lifetimes can appear
|
||||
// unconstrained in a return type, but only if they appear just once
|
||||
// in the input, as the input to a projection.
|
||||
// check-pass
|
||||
|
||||
fn f(_: X) -> X {
|
||||
unimplemented!()
|
16
src/test/ui/late-bound-lifetimes/late_bound_through_alias.rs
Normal file
16
src/test/ui/late-bound-lifetimes/late_bound_through_alias.rs
Normal file
@ -0,0 +1,16 @@
|
||||
// check-pass
|
||||
|
||||
fn f(_: X) -> X {
|
||||
unimplemented!()
|
||||
}
|
||||
|
||||
fn g<'a>(_: X<'a>) -> X<'a> {
|
||||
unimplemented!()
|
||||
}
|
||||
|
||||
type X<'a> = &'a ();
|
||||
|
||||
fn main() {
|
||||
let _: for<'a> fn(X<'a>) -> X<'a> = g;
|
||||
let _: for<'a> fn(X<'a>) -> X<'a> = f;
|
||||
}
|
12
src/test/ui/late-bound-lifetimes/mismatched_arg_count.rs
Normal file
12
src/test/ui/late-bound-lifetimes/mismatched_arg_count.rs
Normal file
@ -0,0 +1,12 @@
|
||||
// ensures that we don't ICE when there are too many args supplied to the alias.
|
||||
|
||||
trait Trait<'a> {
|
||||
type Assoc;
|
||||
}
|
||||
|
||||
type Alias<'a, T> = <T as Trait<'a>>::Assoc;
|
||||
|
||||
fn bar<'a, T: Trait<'a>>(_: Alias<'a, 'a, T>) {}
|
||||
//~^ error: this type alias takes 1 lifetime argument but 2 lifetime arguments were supplied
|
||||
|
||||
fn main() {}
|
17
src/test/ui/late-bound-lifetimes/mismatched_arg_count.stderr
Normal file
17
src/test/ui/late-bound-lifetimes/mismatched_arg_count.stderr
Normal file
@ -0,0 +1,17 @@
|
||||
error[E0107]: this type alias takes 1 lifetime argument but 2 lifetime arguments were supplied
|
||||
--> $DIR/mismatched_arg_count.rs:9:29
|
||||
|
|
||||
LL | fn bar<'a, T: Trait<'a>>(_: Alias<'a, 'a, T>) {}
|
||||
| ^^^^^ -- help: remove this lifetime argument
|
||||
| |
|
||||
| expected 1 lifetime argument
|
||||
|
|
||||
note: type alias defined here, with 1 lifetime parameter: `'a`
|
||||
--> $DIR/mismatched_arg_count.rs:7:6
|
||||
|
|
||||
LL | type Alias<'a, T> = <T as Trait<'a>>::Assoc;
|
||||
| ^^^^^ --
|
||||
|
||||
error: aborting due to previous error
|
||||
|
||||
For more information about this error, try `rustc --explain E0107`.
|
5
src/test/ui/parser/issue-103451.rs
Normal file
5
src/test/ui/parser/issue-103451.rs
Normal file
@ -0,0 +1,5 @@
|
||||
// error-pattern: this file contains an unclosed delimiter
|
||||
// error-pattern: expected value, found struct `R`
|
||||
struct R { }
|
||||
struct S {
|
||||
x: [u8; R
|
32
src/test/ui/parser/issue-103451.stderr
Normal file
32
src/test/ui/parser/issue-103451.stderr
Normal file
@ -0,0 +1,32 @@
|
||||
error: this file contains an unclosed delimiter
|
||||
--> $DIR/issue-103451.rs:5:15
|
||||
|
|
||||
LL | struct S {
|
||||
| - unclosed delimiter
|
||||
LL | x: [u8; R
|
||||
| - ^
|
||||
| |
|
||||
| unclosed delimiter
|
||||
|
||||
error: this file contains an unclosed delimiter
|
||||
--> $DIR/issue-103451.rs:5:15
|
||||
|
|
||||
LL | struct S {
|
||||
| - unclosed delimiter
|
||||
LL | x: [u8; R
|
||||
| - ^
|
||||
| |
|
||||
| unclosed delimiter
|
||||
|
||||
error[E0423]: expected value, found struct `R`
|
||||
--> $DIR/issue-103451.rs:5:13
|
||||
|
|
||||
LL | struct R { }
|
||||
| ------------ `R` defined here
|
||||
LL | struct S {
|
||||
LL | x: [u8; R
|
||||
| ^ help: use struct literal syntax instead: `R {}`
|
||||
|
||||
error: aborting due to 3 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0423`.
|
Loading…
Reference in New Issue
Block a user