Skip to content

Commit 863b4e6

Browse files
authored
Merge pull request #4203 from RalfJung/rustup
Rustup
2 parents 939ae79 + 58affb3 commit 863b4e6

File tree

9 files changed

+90
-20
lines changed

9 files changed

+90
-20
lines changed

rust-version

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
17c1c329a5512d718b67ef6797538b154016cd34
1+
e0be1a02626abef2878cb7f4aaef7ae409477112

src/intrinsics/mod.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -146,60 +146,60 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
146146
this.write_scalar(Scalar::from_bool(branch), dest)?;
147147
}
148148

149-
"floorf16" | "ceilf16" | "truncf16" | "roundf16" | "rintf16" => {
149+
"floorf16" | "ceilf16" | "truncf16" | "roundf16" | "round_ties_even_f16" => {
150150
let [f] = check_intrinsic_arg_count(args)?;
151151
let f = this.read_scalar(f)?.to_f16()?;
152152
let mode = match intrinsic_name {
153153
"floorf16" => Round::TowardNegative,
154154
"ceilf16" => Round::TowardPositive,
155155
"truncf16" => Round::TowardZero,
156156
"roundf16" => Round::NearestTiesToAway,
157-
"rintf16" => Round::NearestTiesToEven,
157+
"round_ties_even_f16" => Round::NearestTiesToEven,
158158
_ => bug!(),
159159
};
160160
let res = f.round_to_integral(mode).value;
161161
let res = this.adjust_nan(res, &[f]);
162162
this.write_scalar(res, dest)?;
163163
}
164-
"floorf32" | "ceilf32" | "truncf32" | "roundf32" | "rintf32" => {
164+
"floorf32" | "ceilf32" | "truncf32" | "roundf32" | "round_ties_even_f32" => {
165165
let [f] = check_intrinsic_arg_count(args)?;
166166
let f = this.read_scalar(f)?.to_f32()?;
167167
let mode = match intrinsic_name {
168168
"floorf32" => Round::TowardNegative,
169169
"ceilf32" => Round::TowardPositive,
170170
"truncf32" => Round::TowardZero,
171171
"roundf32" => Round::NearestTiesToAway,
172-
"rintf32" => Round::NearestTiesToEven,
172+
"round_ties_even_f32" => Round::NearestTiesToEven,
173173
_ => bug!(),
174174
};
175175
let res = f.round_to_integral(mode).value;
176176
let res = this.adjust_nan(res, &[f]);
177177
this.write_scalar(res, dest)?;
178178
}
179-
"floorf64" | "ceilf64" | "truncf64" | "roundf64" | "rintf64" => {
179+
"floorf64" | "ceilf64" | "truncf64" | "roundf64" | "round_ties_even_f64" => {
180180
let [f] = check_intrinsic_arg_count(args)?;
181181
let f = this.read_scalar(f)?.to_f64()?;
182182
let mode = match intrinsic_name {
183183
"floorf64" => Round::TowardNegative,
184184
"ceilf64" => Round::TowardPositive,
185185
"truncf64" => Round::TowardZero,
186186
"roundf64" => Round::NearestTiesToAway,
187-
"rintf64" => Round::NearestTiesToEven,
187+
"round_ties_even_f64" => Round::NearestTiesToEven,
188188
_ => bug!(),
189189
};
190190
let res = f.round_to_integral(mode).value;
191191
let res = this.adjust_nan(res, &[f]);
192192
this.write_scalar(res, dest)?;
193193
}
194-
"floorf128" | "ceilf128" | "truncf128" | "roundf128" | "rintf128" => {
194+
"floorf128" | "ceilf128" | "truncf128" | "roundf128" | "round_ties_even_f128" => {
195195
let [f] = check_intrinsic_arg_count(args)?;
196196
let f = this.read_scalar(f)?.to_f128()?;
197197
let mode = match intrinsic_name {
198198
"floorf128" => Round::TowardNegative,
199199
"ceilf128" => Round::TowardPositive,
200200
"truncf128" => Round::TowardZero,
201201
"roundf128" => Round::NearestTiesToAway,
202-
"rintf128" => Round::NearestTiesToEven,
202+
"round_ties_even_f128" => Round::NearestTiesToEven,
203203
_ => bug!(),
204204
};
205205
let res = f.round_to_integral(mode).value;

src/lib.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
#![cfg_attr(bootstrap, feature(trait_upcasting))]
21
#![feature(rustc_private)]
32
#![feature(cfg_match)]
43
#![feature(cell_update)]
@@ -17,7 +16,6 @@
1716
#![feature(unqualified_local_imports)]
1817
#![feature(derive_coerce_pointee)]
1918
#![feature(arbitrary_self_types)]
20-
#![feature(unsigned_is_multiple_of)]
2119
#![feature(extract_if)]
2220
// Configure clippy and other lints
2321
#![allow(
Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
//@normalize-stderr-test: "\d+ < \d+" -> "$$ADDR < $$ADDR"
2-
#![feature(ptr_sub_ptr)]
3-
42
fn main() {
53
let arr = [0u8; 8];
64
let ptr1 = arr.as_ptr();
75
let ptr2 = ptr1.wrapping_add(4);
8-
let _val = unsafe { ptr1.sub_ptr(ptr2) }; //~ERROR: first pointer has smaller address than second
6+
let _val = unsafe { ptr1.offset_from_unsigned(ptr2) }; //~ERROR: first pointer has smaller address than second
97
}

tests/fail/intrinsics/ptr_offset_from_unsigned_neg.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
error: Undefined Behavior: `ptr_offset_from_unsigned` called when first pointer has smaller address than second: $ADDR < $ADDR
22
--> tests/fail/intrinsics/ptr_offset_from_unsigned_neg.rs:LL:CC
33
|
4-
LL | let _val = unsafe { ptr1.sub_ptr(ptr2) };
5-
| ^^^^^^^^^^^^^^^^^^ `ptr_offset_from_unsigned` called when first pointer has smaller address than second: $ADDR < $ADDR
4+
LL | let _val = unsafe { ptr1.offset_from_unsigned(ptr2) };
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `ptr_offset_from_unsigned` called when first pointer has smaller address than second: $ADDR < $ADDR
66
|
77
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
88
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
// Test that transmuting from `&dyn Trait<fn(&'static ())>` to `&dyn Trait<for<'a> fn(&'a ())>` is UB.
2+
//
3+
// The vtable of `() as Trait<fn(&'static ())>` and `() as Trait<for<'a> fn(&'a ())>` can have
4+
// different entries and, because in the former the entry for `foo` is vacant, this test will
5+
// segfault at runtime.
6+
7+
trait Trait<U> {
8+
fn foo(&self)
9+
where
10+
U: HigherRanked,
11+
{
12+
}
13+
}
14+
impl<T, U> Trait<U> for T {}
15+
16+
trait HigherRanked {}
17+
impl HigherRanked for for<'a> fn(&'a ()) {}
18+
19+
// 2nd candidate is required so that selecting `(): Trait<fn(&'static ())>` will
20+
// evaluate the candidates and fail the leak check instead of returning the
21+
// only applicable candidate.
22+
trait Unsatisfied {}
23+
impl<T: Unsatisfied> HigherRanked for T {}
24+
25+
fn main() {
26+
let x: &dyn Trait<fn(&'static ())> = &();
27+
let y: &dyn Trait<for<'a> fn(&'a ())> = unsafe { std::mem::transmute(x) };
28+
//~^ ERROR: wrong trait in wide pointer vtable
29+
y.foo();
30+
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
error: Undefined Behavior: constructing invalid value: wrong trait in wide pointer vtable: expected `Trait<for<'a> fn(&'a ())>`, but encountered `Trait<fn(&())>`
2+
--> tests/fail/validity/dyn-transmute-inner-binder.rs:LL:CC
3+
|
4+
LL | let y: &dyn Trait<for<'a> fn(&'a ())> = unsafe { std::mem::transmute(x) };
5+
| ^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: wrong trait in wide pointer vtable: expected `Trait<for<'a> fn(&'a ())>`, but encountered `Trait<fn(&())>`
6+
|
7+
= help: this indicates a bug in the program: it performed an invalid operation, and caused Undefined Behavior
8+
= help: see https://doc.rust-lang.org/nightly/reference/behavior-considered-undefined.html for further information
9+
= note: BACKTRACE:
10+
= note: inside `main` at tests/fail/validity/dyn-transmute-inner-binder.rs:LL:CC
11+
12+
note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace
13+
14+
error: aborting due to 1 previous error
15+

tests/pass/dyn-upcast.rs

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ fn main() {
99
drop_principal();
1010
modulo_binder();
1111
modulo_assoc();
12+
bidirectional_subtyping();
1213
}
1314

1415
fn vtable_nop_cast() {
@@ -531,3 +532,32 @@ fn modulo_assoc() {
531532

532533
(&() as &dyn Trait as &dyn Middle<()>).say_hello(&0);
533534
}
535+
536+
fn bidirectional_subtyping() {
537+
// Test that transmuting between subtypes of dyn traits is fine, even in the
538+
// "wrong direction", i.e. going from a lower-ranked to a higher-ranked dyn trait.
539+
// Note that compared to the `dyn-transmute-inner-binder` test, the `for` is on the
540+
// *outside* here!
541+
542+
trait Trait<U: ?Sized> {}
543+
impl<T, U: ?Sized> Trait<U> for T {}
544+
545+
struct Wrapper<T: ?Sized>(T);
546+
547+
let x: &dyn Trait<fn(&'static ())> = &();
548+
let _y: &dyn for<'a> Trait<fn(&'a ())> = unsafe { std::mem::transmute(x) };
549+
550+
let x: &dyn for<'a> Trait<fn(&'a ())> = &();
551+
let _y: &dyn Trait<fn(&'static ())> = unsafe { std::mem::transmute(x) };
552+
553+
let x: &dyn Trait<dyn Trait<fn(&'static ())>> = &();
554+
let _y: &dyn for<'a> Trait<dyn Trait<fn(&'a ())>> = unsafe { std::mem::transmute(x) };
555+
556+
let x: &dyn for<'a> Trait<dyn Trait<fn(&'a ())>> = &();
557+
let _y: &dyn Trait<dyn Trait<fn(&'static ())>> = unsafe { std::mem::transmute(x) };
558+
559+
// This lowers to a ptr-to-ptr cast (which behaves like a transmute)
560+
// and not an unsizing coercion:
561+
let x: *const dyn for<'a> Trait<&'a ()> = &();
562+
let _y: *const Wrapper<dyn Trait<&'static ()>> = x as _;
563+
}

tests/pass/ptr_offset.rs

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
//@compile-flags: -Zmiri-permissive-provenance
2-
#![feature(ptr_sub_ptr)]
32
use std::{mem, ptr};
43

54
fn main() {
@@ -22,7 +21,7 @@ fn smoke() {
2221
let _val = ptr.wrapping_sub(0);
2322
let _val = unsafe { ptr.sub(0) };
2423
let _val = unsafe { ptr.offset_from(ptr) };
25-
let _val = unsafe { ptr.sub_ptr(ptr) };
24+
let _val = unsafe { ptr.offset_from_unsigned(ptr) };
2625
}
2726

2827
fn test_offset_from() {
@@ -33,14 +32,14 @@ fn test_offset_from() {
3332
let y = x.offset(12);
3433

3534
assert_eq!(y.offset_from(x), 12);
36-
assert_eq!(y.sub_ptr(x), 12);
35+
assert_eq!(y.offset_from_unsigned(x), 12);
3736
assert_eq!(x.offset_from(y), -12);
3837
assert_eq!((y as *const u32).offset_from(x as *const u32), 12 / 4);
3938
assert_eq!((x as *const u32).offset_from(y as *const u32), -12 / 4);
4039

4140
let x = (((x as usize) * 2) / 2) as *const u8;
4241
assert_eq!(y.offset_from(x), 12);
43-
assert_eq!(y.sub_ptr(x), 12);
42+
assert_eq!(y.offset_from_unsigned(x), 12);
4443
assert_eq!(x.offset_from(y), -12);
4544
}
4645
}

0 commit comments

Comments
 (0)