authorbors <bors@rust-lang.org> 2026-06-04 03:56:06 UTC
committerbors <bors@rust-lang.org> 2026-06-04 03:56:06 UTC
log49b19d32b9f01a5aa606f3bf2e90e6e0aa462c03
treec5c51c2ee4bbfaa831dff2efe95feaf38f0bb799
parent76dfce2cb2d3f7b7f34d62e6ffe044f7e7d76948
parentaa15473ad1512b32a8a1c1ccac5be182b45e449f

Auto merge of #157404 - jhpratt:rollup-npYd5Y2, r=jhpratt

Rollup of 3 pull requests Successful merges: - rust-lang/rust#156210 (Emit retags in codegen to support BorrowSanitizer (part 2)) - rust-lang/rust#157317 (Fix ICE when wrong intra-doc link on type alias) - rust-lang/rust#157391 (Reorganize `tests/ui/issues` [4/N])

46 files changed, 511 insertions(+), 303 deletions(-)

compiler/rustc_codegen_ssa/src/mir/block.rs+21-4
......@@ -264,6 +264,12 @@ impl<'a, 'tcx> TerminatorCodegenHelper<'tcx> {
264264 bx.lifetime_end(tmp, size);
265265 }
266266 fx.store_return(bx, ret_dest, &fn_abi.ret, invokeret);
267
268 // If the return value was retagged as it was stored,
269 // then we might be in a different basic block now.
270 // Update the cached block for `target` to point to this new
271 // block, where codegen will continue.
272 fx.cached_llbbs[target] = CachedLlbb::Some(bx.llbb());
267273 }
268274 MergingSucc::False
269275 } else {
......@@ -2186,19 +2192,27 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
21862192 llval: Bx::Value,
21872193 ) {
21882194 use self::ReturnDest::*;
2189
2195 let retags_enabled = bx.tcx().sess.opts.unstable_opts.codegen_emit_retag.is_some();
21902196 match dest {
21912197 Nothing => (),
2192 Store(dst) => bx.store_arg(ret_abi, llval, dst),
2198 Store(dst) => {
2199 bx.store_arg(ret_abi, llval, dst);
2200 if retags_enabled {
2201 self.codegen_retag_place(bx, dst, false);
2202 }
2203 }
21932204 IndirectOperand(tmp, index) => {
2194 let op = bx.load_operand(tmp);
2205 let mut op = bx.load_operand(tmp);
21952206 tmp.storage_dead(bx);
2207 if retags_enabled {
2208 op = self.codegen_retag_operand(bx, op, false);
2209 }
21962210 self.overwrite_local(index, LocalRef::Operand(op));
21972211 self.debug_introduce_local(bx, index);
21982212 }
21992213 DirectOperand(index) => {
22002214 // If there is a cast, we have to store and reload.
2201 let op = if let PassMode::Cast { .. } = ret_abi.mode {
2215 let mut op = if let PassMode::Cast { .. } = ret_abi.mode {
22022216 let tmp = PlaceRef::alloca(bx, ret_abi.layout);
22032217 tmp.storage_live(bx);
22042218 bx.store_arg(ret_abi, llval, tmp);
......@@ -2208,6 +2222,9 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
22082222 } else {
22092223 OperandRef::from_immediate_or_packed_pair(bx, llval, ret_abi.layout)
22102224 };
2225 if retags_enabled {
2226 op = self.codegen_retag_operand(bx, op, false);
2227 }
22112228 self.overwrite_local(index, LocalRef::Operand(op));
22122229 self.debug_introduce_local(bx, index);
22132230 }
compiler/rustc_codegen_ssa/src/mir/mod.rs+28-1
......@@ -24,6 +24,7 @@ mod locals;
2424pub mod naked_asm;
2525pub mod operand;
2626pub mod place;
27mod retag;
2728mod rvalue;
2829mod statement;
2930
......@@ -425,7 +426,7 @@ fn arg_local_refs<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
425426 return vec![];
426427 }
427428
428 let args = mir
429 let mut args = mir
429430 .args_iter()
430431 .enumerate()
431432 .map(|(arg_index, local)| {
......@@ -562,6 +563,32 @@ fn arg_local_refs<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
562563 }
563564 })
564565 .collect::<Vec<_>>();
566 if bx.tcx().sess.opts.unstable_opts.codegen_emit_retag.is_some() {
567 args = args
568 .iter()
569 .map(|arg| match arg {
570 &LocalRef::Place(place_ref) => {
571 fx.codegen_retag_place(bx, place_ref, true);
572 LocalRef::Place(place_ref)
573 }
574 &LocalRef::UnsizedPlace(place_ref) => {
575 let operand = bx.load_operand(place_ref);
576 let retagged = fx.codegen_retag_operand(bx, operand, true);
577 assert!(matches!(retagged.val, OperandValue::Pair(_, _)));
578 retagged.val.store(bx, place_ref);
579 LocalRef::UnsizedPlace(place_ref)
580 }
581 &LocalRef::Operand(operand_ref) => {
582 let retagged = fx.codegen_retag_operand(bx, operand_ref, true);
583 LocalRef::Operand(retagged)
584 }
585 LocalRef::PendingOperand => LocalRef::PendingOperand,
586 })
587 .collect::<Vec<_>>();
588 // If we branched during retagging, then we need to update the
589 // start block to the new location.
590 fx.cached_llbbs[mir::START_BLOCK] = CachedLlbb::Some(bx.llbb());
591 }
565592
566593 if fx.instance.def.requires_caller_location(bx.tcx()) {
567594 let mir_args = if let Some(num_untupled) = num_untupled {
compiler/rustc_codegen_ssa/src/mir/retag.rs created+34
......@@ -0,0 +1,34 @@
1//! Experimental support for emitting retags as function calls in generated code.
2
3use rustc_middle::mir::{Rvalue, WithRetag};
4
5use crate::mir::FunctionCx;
6use crate::mir::operand::OperandRef;
7use crate::mir::place::PlaceRef;
8use crate::traits::BuilderMethods;
9
10pub(crate) fn rvalue_needs_retag(rvalue: &Rvalue<'_>) -> bool {
11 // `Ref` has its own internal retagging
12 !matches!(rvalue, Rvalue::Ref(..)) && !matches!(rvalue, Rvalue::Use(.., WithRetag::No))
13}
14
15impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
16 /// Retags the pointers within an [`OperandRef`].
17 pub(crate) fn codegen_retag_operand(
18 &mut self,
19 _bx: &mut Bx,
20 operand: OperandRef<'tcx, Bx::Value>,
21 _is_fn_entry: bool,
22 ) -> OperandRef<'tcx, Bx::Value> {
23 operand
24 }
25
26 /// Retags the pointers within a [`PlaceRef`].
27 pub(crate) fn codegen_retag_place(
28 &mut self,
29 _bx: &mut Bx,
30 _place_ref: PlaceRef<'tcx, Bx::Value>,
31 _is_fn_entry: bool,
32 ) {
33 }
34}
compiler/rustc_codegen_ssa/src/mir/rvalue.rs+6-1
......@@ -522,7 +522,12 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
522522 let mk_ref = move |tcx: TyCtxt<'tcx>, ty: Ty<'tcx>| {
523523 Ty::new_ref(tcx, tcx.lifetimes.re_erased, ty, bk.to_mutbl_lossy())
524524 };
525 self.codegen_place_to_pointer(bx, place, mk_ref)
525 let op = self.codegen_place_to_pointer(bx, place, mk_ref);
526 if self.cx.tcx().sess.opts.unstable_opts.codegen_emit_retag.is_some() {
527 self.codegen_retag_operand(bx, op, false)
528 } else {
529 op
530 }
526531 }
527532
528533 // Note: Exclusive reborrowing is always equal to a memcpy, as the types do not change.
compiler/rustc_codegen_ssa/src/mir/statement.rs+22-3
......@@ -3,6 +3,7 @@ use rustc_middle::{bug, span_bug, ty};
33use tracing::instrument;
44
55use super::{FunctionCx, LocalRef};
6use crate::mir::retag;
67use crate::traits::*;
78
89impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
......@@ -12,9 +13,17 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
1213 self.set_debug_loc(bx, statement.source_info);
1314 match statement.kind {
1415 mir::StatementKind::Assign((ref place, ref rvalue)) => {
16 let needs_retag = bx.tcx().sess.opts.unstable_opts.codegen_emit_retag.is_some()
17 && retag::rvalue_needs_retag(rvalue);
18
1519 if let Some(index) = place.as_local() {
1620 match self.locals[index] {
17 LocalRef::Place(cg_dest) => self.codegen_rvalue(bx, cg_dest, rvalue),
21 LocalRef::Place(cg_dest) => {
22 self.codegen_rvalue(bx, cg_dest, rvalue);
23 if needs_retag {
24 self.codegen_retag_place(bx, cg_dest, false);
25 }
26 }
1827 LocalRef::UnsizedPlace(cg_indirect_dest) => {
1928 let ty = cg_indirect_dest.layout.ty;
2029 span_bug!(
......@@ -24,7 +33,10 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
2433 );
2534 }
2635 LocalRef::PendingOperand => {
27 let operand = self.codegen_rvalue_operand(bx, rvalue);
36 let mut operand = self.codegen_rvalue_operand(bx, rvalue);
37 if needs_retag {
38 operand = self.codegen_retag_operand(bx, operand, false);
39 }
2840 self.overwrite_local(index, LocalRef::Operand(operand));
2941 self.debug_introduce_local(bx, index);
3042 }
......@@ -39,12 +51,19 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
3951
4052 // If the type is zero-sized, it's already been set here,
4153 // but we still need to make sure we codegen the operand
42 self.codegen_rvalue_operand(bx, rvalue);
54 // and emit a retag.
55 let operand = self.codegen_rvalue_operand(bx, rvalue);
56 if needs_retag {
57 self.codegen_retag_operand(bx, operand, false);
58 }
4359 }
4460 }
4561 } else {
4662 let cg_dest = self.codegen_place(bx, place.as_ref());
4763 self.codegen_rvalue(bx, cg_dest, rvalue);
64 if needs_retag {
65 self.codegen_retag_place(bx, cg_dest, false);
66 }
4867 }
4968 }
5069 mir::StatementKind::SetDiscriminant { ref place, variant_index } => {
compiler/rustc_interface/src/tests.rs+4-3
......@@ -10,9 +10,9 @@ use rustc_errors::ColorConfig;
1010use rustc_errors::emitter::HumanReadableErrorType;
1111use rustc_hir::attrs::{CollapseMacroDebuginfo, NativeLibKind};
1212use rustc_session::config::{
13 AnnotateMoves, AutoDiff, BranchProtection, CFGuard, Cfg, CoverageLevel, CoverageOptions,
14 DebugInfo, DumpMonoStatsFormat, ErrorOutputType, ExternEntry, ExternLocation, Externs,
15 FmtDebug, FunctionReturn, IncrementalStateAssertion, InliningThreshold, Input,
13 AnnotateMoves, AutoDiff, BranchProtection, CFGuard, Cfg, CodegenRetagOptions, CoverageLevel,
14 CoverageOptions, DebugInfo, DumpMonoStatsFormat, ErrorOutputType, ExternEntry, ExternLocation,
15 Externs, FmtDebug, FunctionReturn, IncrementalStateAssertion, InliningThreshold, Input,
1616 InstrumentCoverage, InstrumentXRay, LinkSelfContained, LinkerPluginLto, LocationDetail, LtoCli,
1717 MirIncludeSpans, NextSolverConfig, Offload, Options, OutFileName, OutputType, OutputTypes,
1818 PAuthKey, PacRet, Passes, PatchableFunctionEntry, Polonius, ProcMacroExecutionStrategy, Strip,
......@@ -772,6 +772,7 @@ fn test_unstable_options_tracking_hash() {
772772 })
773773 );
774774 tracked!(codegen_backend, Some("abc".to_string()));
775 tracked!(codegen_emit_retag, Some(CodegenRetagOptions::default()));
775776 tracked!(
776777 coverage_options,
777778 CoverageOptions {
compiler/rustc_session/src/config.rs+17-6
......@@ -200,6 +200,15 @@ pub enum Offload {
200200 Test,
201201}
202202
203/// The different settings that the `-Z codegen-emit-retag` flag can have.
204#[derive(Copy, Clone, Debug, Default, PartialEq, Hash, Encodable, Decodable)]
205pub struct CodegenRetagOptions {
206 /// Track interior mutable data on the level of references, instead of on the byte level.
207 pub no_precise_im: bool,
208 /// Track `UnsafePinned` data on the level of references, instead of on the byte level.
209 pub no_precise_pin: bool,
210}
211
203212/// The different settings that the `-Z autodiff` flag can have.
204213#[derive(Clone, PartialEq, Hash, Debug, Encodable, Decodable)]
205214pub enum AutoDiff {
......@@ -3045,12 +3054,13 @@ pub(crate) mod dep_tracking {
30453054 };
30463055
30473056 use super::{
3048 AnnotateMoves, AutoDiff, BranchProtection, CFGuard, CFProtection, CoverageOptions,
3049 CrateType, DebugInfo, DebugInfoCompression, ErrorOutputType, FmtDebug, FunctionReturn,
3050 InliningThreshold, InstrumentCoverage, InstrumentXRay, LinkerPluginLto, LocationDetail,
3051 LtoCli, MirStripDebugInfo, NextSolverConfig, Offload, OptLevel, OutFileName, OutputType,
3052 OutputTypes, PatchableFunctionEntry, Polonius, ResolveDocLinks, SourceFileHashAlgorithm,
3053 SplitDwarfKind, SwitchWithOptPath, SymbolManglingVersion, WasiExecModel,
3057 AnnotateMoves, AutoDiff, BranchProtection, CFGuard, CFProtection, CodegenRetagOptions,
3058 CoverageOptions, CrateType, DebugInfo, DebugInfoCompression, ErrorOutputType, FmtDebug,
3059 FunctionReturn, InliningThreshold, InstrumentCoverage, InstrumentXRay, LinkerPluginLto,
3060 LocationDetail, LtoCli, MirStripDebugInfo, NextSolverConfig, Offload, OptLevel,
3061 OutFileName, OutputType, OutputTypes, PatchableFunctionEntry, Polonius, ResolveDocLinks,
3062 SourceFileHashAlgorithm, SplitDwarfKind, SwitchWithOptPath, SymbolManglingVersion,
3063 WasiExecModel,
30543064 };
30553065 use crate::lint;
30563066 use crate::utils::NativeLib;
......@@ -3154,6 +3164,7 @@ pub(crate) mod dep_tracking {
31543164 InliningThreshold,
31553165 FunctionReturn,
31563166 Align,
3167 CodegenRetagOptions
31573168 );
31583169
31593170 impl<T1, T2> DepTrackingHash for (T1, T2)
compiler/rustc_session/src/options.rs+27
......@@ -783,6 +783,8 @@ mod desc {
783783 pub(crate) const parse_dump_mono_stats: &str = "`markdown` (default) or `json`";
784784 pub(crate) const parse_instrument_coverage: &str = parse_bool;
785785 pub(crate) const parse_coverage_options: &str = "`block` | `branch` | `condition`";
786 pub(crate) const parse_codegen_retag_options: &str =
787 "either no value or a comma-separated list of settings: `no-precise-im`, `no-precise-pin`";
786788 pub(crate) const parse_instrument_xray: &str = "either a boolean (`yes`, `no`, `on`, `off`, etc), or a comma separated list of settings: `always` or `never` (mutually exclusive), `ignore-loops`, `instruction-threshold=N`, `skip-entry`, `skip-exit`";
787789 pub(crate) const parse_unpretty: &str = "`string` or `string=string`";
788790 pub(crate) const parse_treat_err_as_bug: &str = "either no value or a non-negative number";
......@@ -1523,6 +1525,29 @@ pub mod parse {
15231525 true
15241526 }
15251527
1528 pub(crate) fn parse_codegen_retag_options(
1529 slot: &mut Option<CodegenRetagOptions>,
1530 v: Option<&str>,
1531 ) -> bool {
1532 let mut no_precise_im = false;
1533 let mut no_precise_pin = false;
1534 if let Some(opt_list) = v.map(|s| s.split(',')) {
1535 for opt in opt_list {
1536 match opt {
1537 "no-precise-im" => {
1538 no_precise_im = true;
1539 }
1540 "no-precise-pin" => {
1541 no_precise_pin = true;
1542 }
1543 _ => return false,
1544 }
1545 }
1546 }
1547 *slot = Some(CodegenRetagOptions { no_precise_im, no_precise_pin });
1548 true
1549 }
1550
15261551 pub(crate) fn parse_coverage_options(slot: &mut CoverageOptions, v: Option<&str>) -> bool {
15271552 let Some(v) = v else { return true };
15281553
......@@ -2242,6 +2267,8 @@ options! {
22422267 "hash algorithm of source files used to check freshness in cargo (`blake3` or `sha256`)"),
22432268 codegen_backend: Option<String> = (None, parse_opt_string, [TRACKED],
22442269 "the backend to use"),
2270 codegen_emit_retag: Option<CodegenRetagOptions> = (None, parse_codegen_retag_options, [TRACKED],
2271 "emit retag function calls in generated code"),
22452272 codegen_source_order: bool = (false, parse_bool, [UNTRACKED],
22462273 "emit mono items in the order of spans in source files (default: no)"),
22472274 contract_checks: Option<bool> = (None, parse_opt_bool, [TRACKED],
compiler/rustc_session/src/session.rs+2
......@@ -553,6 +553,8 @@ impl Session {
553553 // HWAddressSanitizer and KernelHWAddressSanitizer will use lifetimes to detect use after
554554 // scope bugs in the future.
555555 || self.sanitizers().intersects(SanitizerSet::ADDRESS | SanitizerSet::KERNELADDRESS | SanitizerSet::MEMORY | SanitizerSet::HWADDRESS | SanitizerSet::KERNELHWADDRESS)
556 // Lifetimes are necessary for retagging semantics.
557 || self.opts.unstable_opts.codegen_emit_retag.is_some()
556558 }
557559
558560 pub fn diagnostic_width(&self) -> usize {
src/librustdoc/passes/collect_intra_doc_links.rs+6-1
......@@ -328,7 +328,12 @@ impl<'tcx> LinkCollector<'_, 'tcx> {
328328 })
329329 }
330330 }
331 _ => unreachable!(),
331 _ => Err(UnresolvedPath {
332 item_id,
333 module_id,
334 partial_res: Some(Res::Def(DefKind::TyAlias, did)),
335 unresolved: variant_name.to_string().into(),
336 }),
332337 }
333338 }
334339 _ => Err(UnresolvedPath {
tests/rustdoc-ui/intra-doc/ty-alias-field.rs created+11
......@@ -0,0 +1,11 @@
1#![deny(rustdoc::broken_intra_doc_links)]
2//~^ NOTE the lint level is defined here
3
4/// [Self::a::b]
5//~^ ERROR unresolved link to `Self::a::b`
6//~| NOTE the struct `MyStruct` has no field or associated item named `a`
7pub struct MyStruct;
8/// [Self::a::b]
9//~^ ERROR unresolved link to `Self::a::b`
10//~| NOTE the type alias `MyAlias` has no associated item named `a`
11pub type MyAlias = MyStruct;
tests/rustdoc-ui/intra-doc/ty-alias-field.stderr created+20
......@@ -0,0 +1,20 @@
1error: unresolved link to `Self::a::b`
2 --> $DIR/ty-alias-field.rs:4:6
3 |
4LL | /// [Self::a::b]
5 | ^^^^^^^^^^ the struct `MyStruct` has no field or associated item named `a`
6 |
7note: the lint level is defined here
8 --> $DIR/ty-alias-field.rs:1:9
9 |
10LL | #![deny(rustdoc::broken_intra_doc_links)]
11 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
12
13error: unresolved link to `Self::a::b`
14 --> $DIR/ty-alias-field.rs:8:6
15 |
16LL | /// [Self::a::b]
17 | ^^^^^^^^^^ the type alias `MyAlias` has no associated item named `a`
18
19error: aborting due to 2 previous errors
20
tests/ui/associated-types/assoc-type-unsatisfied-bound.rs created+12
......@@ -0,0 +1,12 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18611>.
2
3fn add_state(op: <isize as HasState>::State) {
4//~^ ERROR `isize: HasState` is not satisfied
5//~| ERROR `isize: HasState` is not satisfied
6}
7
8trait HasState {
9 type State;
10}
11
12fn main() {}
tests/ui/associated-types/assoc-type-unsatisfied-bound.stderr created+28
......@@ -0,0 +1,28 @@
1error[E0277]: the trait bound `isize: HasState` is not satisfied
2 --> $DIR/assoc-type-unsatisfied-bound.rs:3:18
3 |
4LL | fn add_state(op: <isize as HasState>::State) {
5 | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize`
6 |
7help: this trait has no implementations, consider adding one
8 --> $DIR/assoc-type-unsatisfied-bound.rs:8:1
9 |
10LL | trait HasState {
11 | ^^^^^^^^^^^^^^
12
13error[E0277]: the trait bound `isize: HasState` is not satisfied
14 --> $DIR/assoc-type-unsatisfied-bound.rs:3:18
15 |
16LL | fn add_state(op: <isize as HasState>::State) {
17 | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize`
18 |
19help: this trait has no implementations, consider adding one
20 --> $DIR/assoc-type-unsatisfied-bound.rs:8:1
21 |
22LL | trait HasState {
23 | ^^^^^^^^^^^^^^
24 = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
25
26error: aborting due to 2 previous errors
27
28For more information about this error, try `rustc --explain E0277`.
tests/ui/box/box-deref-match-arm.rs created+19
......@@ -0,0 +1,19 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18845>.
2//!
3//! This used to generate invalid IR in that even if we took the
4//! `false` branch we'd still try to free the Box from the other
5//! arm. This was due to treating `*Box::new(9)` as an rvalue datum
6//! instead of as a place.
7
8//@ run-pass
9
10fn test(foo: bool) -> u8 {
11 match foo {
12 true => *Box::new(9),
13 false => 0
14 }
15}
16
17fn main() {
18 assert_eq!(9, test(true));
19}
tests/ui/cross-crate/auxiliary/inline-fn-with-trait-method-as-value.rs created+19
......@@ -0,0 +1,19 @@
1//! Auxiliary crate for <https://github.com/rust-lang/rust/issues/18501>.
2
3#![crate_type = "rlib"]
4struct Foo;
5
6trait Tr {
7 fn tr(&self);
8}
9
10impl Tr for Foo {
11 fn tr(&self) {}
12}
13
14fn take_method<T>(f: fn(&T), t: &T) {}
15
16#[inline]
17pub fn pass_method() {
18 take_method(Tr::tr, &Foo);
19}
tests/ui/cross-crate/inline-fn-with-trait-method-as-value.rs created+15
......@@ -0,0 +1,15 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18501>.
2//!
3//! Test that we don't ICE when inlining a function from another
4//! crate that uses a trait method as a value due to incorrectly
5//! translating the def ID of the trait during AST decoding.
6
7//@ run-pass
8
9//@ aux-build:inline-fn-with-trait-method-as-value.rs
10
11extern crate inline_fn_with_trait_method_as_value as issue;
12
13fn main() {
14 issue::pass_method();
15}
tests/ui/dst/dyn-fn-type-in-generic-enum.rs created+14
......@@ -0,0 +1,14 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18919>.
2
3type FuncType<'f> = dyn Fn(&isize) -> isize + 'f;
4
5fn ho_func(f: Option<FuncType>) {
6 //~^ ERROR the size for values of type
7}
8
9enum Option<T> {
10 Some(T),
11 None,
12}
13
14fn main() {}
tests/ui/dst/dyn-fn-type-in-generic-enum.stderr created+23
......@@ -0,0 +1,23 @@
1error[E0277]: the size for values of type `dyn for<'a> Fn(&'a isize) -> isize` cannot be known at compilation time
2 --> $DIR/dyn-fn-type-in-generic-enum.rs:5:15
3 |
4LL | fn ho_func(f: Option<FuncType>) {
5 | ^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
6 |
7 = help: the trait `Sized` is not implemented for `dyn for<'a> Fn(&'a isize) -> isize`
8note: required by an implicit `Sized` bound in `Option`
9 --> $DIR/dyn-fn-type-in-generic-enum.rs:9:13
10 |
11LL | enum Option<T> {
12 | ^ required by the implicit `Sized` requirement on this type parameter in `Option`
13help: you could relax the implicit `Sized` bound on `T` if it were used through indirection like `&T` or `Box<T>`
14 --> $DIR/dyn-fn-type-in-generic-enum.rs:9:13
15 |
16LL | enum Option<T> {
17 | ^ this could be changed to `T: ?Sized`...
18LL | Some(T),
19 | - ...if indirection were used here: `Box<T>`
20
21error: aborting due to 1 previous error
22
23For more information about this error, try `rustc --explain E0277`.
tests/ui/dyn-compatibility/dyn-incompatible-supertrait.rs created+24
......@@ -0,0 +1,24 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18959>.
2
3pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
4pub trait Bar: Foo { }
5impl<T: Foo> Bar for T { }
6
7pub struct Thing;
8impl Foo for Thing {
9 fn foo<T>(&self, _: &T) {}
10}
11
12#[inline(never)]
13fn foo(b: &dyn Bar) {
14 //~^ ERROR E0038
15 b.foo(&0)
16}
17
18fn main() {
19 let mut thing = Thing;
20 let test: &dyn Bar = &mut thing;
21 //~^ ERROR E0038
22 foo(test);
23 //~^ ERROR E0038
24}
tests/ui/dyn-compatibility/dyn-incompatible-supertrait.stderr created+51
......@@ -0,0 +1,51 @@
1error[E0038]: the trait `Bar` is not dyn compatible
2 --> $DIR/dyn-incompatible-supertrait.rs:13:12
3 |
4LL | fn foo(b: &dyn Bar) {
5 | ^^^^^^^ `Bar` is not dyn compatible
6 |
7note: for a trait to be dyn compatible it needs to allow building a vtable
8 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
9 --> $DIR/dyn-incompatible-supertrait.rs:3:20
10 |
11LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
12 | ^^^ ...because method `foo` has generic type parameters
13LL | pub trait Bar: Foo { }
14 | --- this trait is not dyn compatible...
15 = help: consider moving `foo` to another trait
16
17error[E0038]: the trait `Bar` is not dyn compatible
18 --> $DIR/dyn-incompatible-supertrait.rs:20:20
19 |
20LL | let test: &dyn Bar = &mut thing;
21 | ^^^ `Bar` is not dyn compatible
22 |
23note: for a trait to be dyn compatible it needs to allow building a vtable
24 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
25 --> $DIR/dyn-incompatible-supertrait.rs:3:20
26 |
27LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
28 | ^^^ ...because method `foo` has generic type parameters
29LL | pub trait Bar: Foo { }
30 | --- this trait is not dyn compatible...
31 = help: consider moving `foo` to another trait
32
33error[E0038]: the trait `Bar` is not dyn compatible
34 --> $DIR/dyn-incompatible-supertrait.rs:22:9
35 |
36LL | foo(test);
37 | ^^^^ `Bar` is not dyn compatible
38 |
39note: for a trait to be dyn compatible it needs to allow building a vtable
40 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
41 --> $DIR/dyn-incompatible-supertrait.rs:3:20
42 |
43LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
44 | ^^^ ...because method `foo` has generic type parameters
45LL | pub trait Bar: Foo { }
46 | --- this trait is not dyn compatible...
47 = help: consider moving `foo` to another trait
48
49error: aborting due to 3 previous errors
50
51For more information about this error, try `rustc --explain E0038`.
tests/ui/issues/auxiliary/issue-18501.rs deleted-17
......@@ -1,17 +0,0 @@
1#![crate_type = "rlib"]
2struct Foo;
3
4trait Tr {
5 fn tr(&self);
6}
7
8impl Tr for Foo {
9 fn tr(&self) {}
10}
11
12fn take_method<T>(f: fn(&T), t: &T) {}
13
14#[inline]
15pub fn pass_method() {
16 take_method(Tr::tr, &Foo);
17}
tests/ui/issues/auxiliary/issue-18711.rs deleted-5
......@@ -1,5 +0,0 @@
1#![crate_type = "rlib"]
2
3pub fn inner<F>(f: F) -> F {
4 (move || f)()
5}
tests/ui/issues/auxiliary/issue-18913-1.rs deleted-6
......@@ -1,6 +0,0 @@
1//@ no-prefer-dynamic
2
3#![crate_type = "rlib"]
4#![crate_name = "foo"]
5
6pub fn foo() -> i32 { 0 }
tests/ui/issues/auxiliary/issue-18913-2.rs deleted-6
......@@ -1,6 +0,0 @@
1//@ no-prefer-dynamic
2
3#![crate_type = "rlib"]
4#![crate_name = "foo"]
5
6pub fn foo() -> i32 { 1 }
tests/ui/issues/issue-18501.rs deleted-12
......@@ -1,12 +0,0 @@
1//@ run-pass
2// Test that we don't ICE when inlining a function from another
3// crate that uses a trait method as a value due to incorrectly
4// translating the def ID of the trait during AST decoding.
5
6//@ aux-build:issue-18501.rs
7
8extern crate issue_18501 as issue;
9
10fn main() {
11 issue::pass_method();
12}
tests/ui/issues/issue-18611.rs deleted-10
......@@ -1,10 +0,0 @@
1fn add_state(op: <isize as HasState>::State) {
2//~^ ERROR `isize: HasState` is not satisfied
3//~| ERROR `isize: HasState` is not satisfied
4}
5
6trait HasState {
7 type State;
8}
9
10fn main() {}
tests/ui/issues/issue-18611.stderr deleted-28
......@@ -1,28 +0,0 @@
1error[E0277]: the trait bound `isize: HasState` is not satisfied
2 --> $DIR/issue-18611.rs:1:18
3 |
4LL | fn add_state(op: <isize as HasState>::State) {
5 | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize`
6 |
7help: this trait has no implementations, consider adding one
8 --> $DIR/issue-18611.rs:6:1
9 |
10LL | trait HasState {
11 | ^^^^^^^^^^^^^^
12
13error[E0277]: the trait bound `isize: HasState` is not satisfied
14 --> $DIR/issue-18611.rs:1:18
15 |
16LL | fn add_state(op: <isize as HasState>::State) {
17 | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize`
18 |
19help: this trait has no implementations, consider adding one
20 --> $DIR/issue-18611.rs:6:1
21 |
22LL | trait HasState {
23 | ^^^^^^^^^^^^^^
24 = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
25
26error: aborting due to 2 previous errors
27
28For more information about this error, try `rustc --explain E0277`.
tests/ui/issues/issue-18711.rs deleted-11
......@@ -1,11 +0,0 @@
1//@ run-pass
2// Test that we don't panic on a RefCell borrow conflict in certain
3// code paths involving unboxed closures.
4
5
6//@ aux-build:issue-18711.rs
7extern crate issue_18711 as issue;
8
9fn main() {
10 (|| issue::inner(()))();
11}
tests/ui/issues/issue-18845.rs deleted-16
......@@ -1,16 +0,0 @@
1//@ run-pass
2// This used to generate invalid IR in that even if we took the
3// `false` branch we'd still try to free the Box from the other
4// arm. This was due to treating `*Box::new(9)` as an rvalue datum
5// instead of as a place.
6
7fn test(foo: bool) -> u8 {
8 match foo {
9 true => *Box::new(9),
10 false => 0
11 }
12}
13
14fn main() {
15 assert_eq!(9, test(true));
16}
tests/ui/issues/issue-18859.rs deleted-16
......@@ -1,16 +0,0 @@
1//@ run-pass
2
3mod foo {
4 pub mod bar {
5 pub mod baz {
6 pub fn name() -> &'static str {
7 module_path!()
8 }
9 }
10 }
11}
12
13fn main() {
14 assert_eq!(module_path!(), "issue_18859");
15 assert_eq!(foo::bar::baz::name(), "issue_18859::foo::bar::baz");
16}
tests/ui/issues/issue-18906.rs deleted-29
......@@ -1,29 +0,0 @@
1//@ check-pass
2#![allow(dead_code)]
3
4pub trait Borrow<Borrowed: ?Sized> {
5 fn borrow(&self) -> &Borrowed;
6}
7
8impl<T: Sized> Borrow<T> for T {
9 fn borrow(&self) -> &T { self }
10}
11
12trait Foo {
13 fn foo(&self, other: &Self);
14}
15
16fn bar<K, Q>(k: &K, q: &Q) where K: Borrow<Q>, Q: Foo {
17 q.foo(k.borrow())
18}
19
20struct MyTree<K>(K);
21
22impl<K> MyTree<K> {
23 // This caused a failure in #18906
24 fn bar<Q>(k: &K, q: &Q) where K: Borrow<Q>, Q: Foo {
25 q.foo(k.borrow())
26 }
27}
28
29fn main() {}
tests/ui/issues/issue-18913.rs deleted-9
......@@ -1,9 +0,0 @@
1//@ run-pass
2//@ aux-build:issue-18913-1.rs
3//@ aux-build:issue-18913-2.rs
4
5extern crate foo;
6
7fn main() {
8 assert_eq!(foo::foo(), 1);
9}
tests/ui/issues/issue-18919.rs deleted-12
......@@ -1,12 +0,0 @@
1type FuncType<'f> = dyn Fn(&isize) -> isize + 'f;
2
3fn ho_func(f: Option<FuncType>) {
4 //~^ ERROR the size for values of type
5}
6
7enum Option<T> {
8 Some(T),
9 None,
10}
11
12fn main() {}
tests/ui/issues/issue-18919.stderr deleted-23
......@@ -1,23 +0,0 @@
1error[E0277]: the size for values of type `dyn for<'a> Fn(&'a isize) -> isize` cannot be known at compilation time
2 --> $DIR/issue-18919.rs:3:15
3 |
4LL | fn ho_func(f: Option<FuncType>) {
5 | ^^^^^^^^^^^^^^^^ doesn't have a size known at compile-time
6 |
7 = help: the trait `Sized` is not implemented for `dyn for<'a> Fn(&'a isize) -> isize`
8note: required by an implicit `Sized` bound in `Option`
9 --> $DIR/issue-18919.rs:7:13
10 |
11LL | enum Option<T> {
12 | ^ required by the implicit `Sized` requirement on this type parameter in `Option`
13help: you could relax the implicit `Sized` bound on `T` if it were used through indirection like `&T` or `Box<T>`
14 --> $DIR/issue-18919.rs:7:13
15 |
16LL | enum Option<T> {
17 | ^ this could be changed to `T: ?Sized`...
18LL | Some(T),
19 | - ...if indirection were used here: `Box<T>`
20
21error: aborting due to 1 previous error
22
23For more information about this error, try `rustc --explain E0277`.
tests/ui/issues/issue-18959.rs deleted-22
......@@ -1,22 +0,0 @@
1pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
2pub trait Bar: Foo { }
3impl<T: Foo> Bar for T { }
4
5pub struct Thing;
6impl Foo for Thing {
7 fn foo<T>(&self, _: &T) {}
8}
9
10#[inline(never)]
11fn foo(b: &dyn Bar) {
12 //~^ ERROR E0038
13 b.foo(&0)
14}
15
16fn main() {
17 let mut thing = Thing;
18 let test: &dyn Bar = &mut thing;
19 //~^ ERROR E0038
20 foo(test);
21 //~^ ERROR E0038
22}
tests/ui/issues/issue-18959.stderr deleted-51
......@@ -1,51 +0,0 @@
1error[E0038]: the trait `Bar` is not dyn compatible
2 --> $DIR/issue-18959.rs:11:12
3 |
4LL | fn foo(b: &dyn Bar) {
5 | ^^^^^^^ `Bar` is not dyn compatible
6 |
7note: for a trait to be dyn compatible it needs to allow building a vtable
8 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
9 --> $DIR/issue-18959.rs:1:20
10 |
11LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
12 | ^^^ ...because method `foo` has generic type parameters
13LL | pub trait Bar: Foo { }
14 | --- this trait is not dyn compatible...
15 = help: consider moving `foo` to another trait
16
17error[E0038]: the trait `Bar` is not dyn compatible
18 --> $DIR/issue-18959.rs:18:20
19 |
20LL | let test: &dyn Bar = &mut thing;
21 | ^^^ `Bar` is not dyn compatible
22 |
23note: for a trait to be dyn compatible it needs to allow building a vtable
24 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
25 --> $DIR/issue-18959.rs:1:20
26 |
27LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
28 | ^^^ ...because method `foo` has generic type parameters
29LL | pub trait Bar: Foo { }
30 | --- this trait is not dyn compatible...
31 = help: consider moving `foo` to another trait
32
33error[E0038]: the trait `Bar` is not dyn compatible
34 --> $DIR/issue-18959.rs:20:9
35 |
36LL | foo(test);
37 | ^^^^ `Bar` is not dyn compatible
38 |
39note: for a trait to be dyn compatible it needs to allow building a vtable
40 for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
41 --> $DIR/issue-18959.rs:1:20
42 |
43LL | pub trait Foo { fn foo<T>(&self, ext_thing: &T); }
44 | ^^^ ...because method `foo` has generic type parameters
45LL | pub trait Bar: Foo { }
46 | --- this trait is not dyn compatible...
47 = help: consider moving `foo` to another trait
48
49error: aborting due to 3 previous errors
50
51For more information about this error, try `rustc --explain E0038`.
tests/ui/issues/issue-18988.rs deleted-11
......@@ -1,11 +0,0 @@
1//@ check-pass
2#![allow(dead_code)]
3pub trait Foo : Send { }
4
5pub struct MyFoo {
6 children: Vec<Box<dyn Foo>>,
7}
8
9impl Foo for MyFoo { }
10
11pub fn main() { }
tests/ui/linking/auxiliary/duplicate-rlib-crate-name-precedence-1.rs created+8
......@@ -0,0 +1,8 @@
1//! Auxiliary crate for <https://github.com/rust-lang/rust/issues/18913>.
2
3//@ no-prefer-dynamic
4
5#![crate_type = "rlib"]
6#![crate_name = "foo"]
7
8pub fn foo() -> i32 { 0 }
tests/ui/linking/auxiliary/duplicate-rlib-crate-name-precedence-2.rs created+8
......@@ -0,0 +1,8 @@
1//! Auxiliary crate for <https://github.com/rust-lang/rust/issues/18913>.
2
3//@ no-prefer-dynamic
4
5#![crate_type = "rlib"]
6#![crate_name = "foo"]
7
8pub fn foo() -> i32 { 1 }
tests/ui/linking/duplicate-rlib-crate-name-precedence.rs created+11
......@@ -0,0 +1,11 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18913>.
2
3//@ run-pass
4//@ aux-build:duplicate-rlib-crate-name-precedence-1.rs
5//@ aux-build:duplicate-rlib-crate-name-precedence-2.rs
6
7extern crate foo;
8
9fn main() {
10 assert_eq!(foo::foo(), 1);
11}
tests/ui/macros/module-path-in-nested-modules.rs created+18
......@@ -0,0 +1,18 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18859>.
2
3//@ run-pass
4
5mod foo {
6 pub mod bar {
7 pub mod baz {
8 pub fn name() -> &'static str {
9 module_path!()
10 }
11 }
12 }
13}
14
15fn main() {
16 assert_eq!(module_path!(), "module_path_in_nested_modules");
17 assert_eq!(foo::bar::baz::name(), "module_path_in_nested_modules::foo::bar::baz");
18}
tests/ui/traits/object/trait-object-with-send-supertrait.rs created+13
......@@ -0,0 +1,13 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18988>.
2
3//@ check-pass
4#![allow(dead_code)]
5pub trait Foo : Send { }
6
7pub struct MyFoo {
8 children: Vec<Box<dyn Foo>>,
9}
10
11impl Foo for MyFoo { }
12
13pub fn main() { }
tests/ui/unboxed-closures/auxiliary/cross-crate-generic-fn-in-closure.rs created+7
......@@ -0,0 +1,7 @@
1//! Auxiliary crate for <https://github.com/rust-lang/rust/issues/18711>.
2
3#![crate_type = "rlib"]
4
5pub fn inner<F>(f: F) -> F {
6 (move || f)()
7}
tests/ui/unboxed-closures/cross-crate-generic-fn-in-closure.rs created+12
......@@ -0,0 +1,12 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18711>.
2//! Test that we don't panic on a RefCell borrow conflict in certain
3//! code paths involving unboxed closures.
4
5//@ run-pass
6
7//@ aux-build:cross-crate-generic-fn-in-closure.rs
8extern crate cross_crate_generic_fn_in_closure as issue;
9
10fn main() {
11 (|| issue::inner(()))();
12}
tests/ui/where-clauses/impl-method-where-clause-resolution.rs created+31
......@@ -0,0 +1,31 @@
1//! Regression test for <https://github.com/rust-lang/rust/issues/18906>.
2
3//@ check-pass
4#![allow(dead_code)]
5
6pub trait Borrow<Borrowed: ?Sized> {
7 fn borrow(&self) -> &Borrowed;
8}
9
10impl<T: Sized> Borrow<T> for T {
11 fn borrow(&self) -> &T { self }
12}
13
14trait Foo {
15 fn foo(&self, other: &Self);
16}
17
18fn bar<K, Q>(k: &K, q: &Q) where K: Borrow<Q>, Q: Foo {
19 q.foo(k.borrow())
20}
21
22struct MyTree<K>(K);
23
24impl<K> MyTree<K> {
25 // This caused a failure in #18906
26 fn bar<Q>(k: &K, q: &Q) where K: Borrow<Q>, Q: Foo {
27 q.foo(k.borrow())
28 }
29}
30
31fn main() {}