Skip to content

Commit ea950d0

Browse files
committed
adjust tests
1 parent ac34812 commit ea950d0

12 files changed

+98
-67
lines changed

tests/fail/copy_half_a_pointer.rs

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
#![allow(dead_code)]
2+
3+
// We use packed structs to get around alignment restrictions
4+
#[repr(packed)]
5+
struct Data {
6+
pad: u8,
7+
ptr: &'static i32,
8+
}
9+
10+
static G: i32 = 0;
11+
12+
fn main() {
13+
let mut d = Data { pad: 0, ptr: &G };
14+
15+
// Get a pointer to the beginning of the Data struct (one u8 byte, then the pointer bytes).
16+
let d_alias = &mut d as *mut _ as *mut *const u8;
17+
unsafe {
18+
let _x = d_alias.read_unaligned(); //~ERROR: unable to copy parts of a pointer
19+
}
20+
}

tests/fail/copy_half_a_pointer.stderr

+14
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
error: unsupported operation: unable to copy parts of a pointer from memory at ALLOC+0x8
2+
--> $DIR/copy_half_a_pointer.rs:LL:CC
3+
|
4+
LL | let _x = d_alias.read_unaligned();
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^ unable to copy parts of a pointer from memory at ALLOC+0x8
6+
|
7+
= help: this is likely not a bug in the program; it indicates that the program performed an operation that the interpreter does not support
8+
= note: backtrace:
9+
= note: inside `main` at $DIR/copy_half_a_pointer.rs:LL:CC
10+
11+
note: some details are omitted, run with `MIRIFLAGS=-Zmiri-backtrace=full` for a verbose backtrace
12+
13+
error: aborting due to previous error
14+

tests/fail/intrinsics/raw_eq_on_ptr.rs

+1-2
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,5 @@ extern "rust-intrinsic" {
66

77
fn main() {
88
let x = &0;
9-
// FIXME: the error message is not great (should be UB rather than 'unsupported')
10-
unsafe { raw_eq(&x, &x) }; //~ERROR: unsupported operation
9+
unsafe { raw_eq(&x, &x) }; //~ERROR: `raw_eq` on bytes with provenance
1110
}

tests/fail/intrinsics/raw_eq_on_ptr.stderr

+4-3
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
1-
error: unsupported operation: unable to turn pointer into raw bytes
1+
error: Undefined Behavior: `raw_eq` on bytes with provenance
22
--> $DIR/raw_eq_on_ptr.rs:LL:CC
33
|
44
LL | unsafe { raw_eq(&x, &x) };
5-
| ^^^^^^^^^^^^^^ unable to turn pointer into raw bytes
5+
| ^^^^^^^^^^^^^^ `raw_eq` on bytes with provenance
66
|
7-
= help: this is likely not a bug in the program; it indicates that the program performed an operation that the interpreter does not support
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
89
= note: backtrace:
910
= note: inside `main` at $DIR/raw_eq_on_ptr.rs:LL:CC
1011

tests/fail/reading_half_a_pointer.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ fn main() {
2424
// starts 1 byte to the right, so using it would actually be wrong!
2525
let d_alias = &mut w.data as *mut _ as *mut *const u8;
2626
unsafe {
27-
let _x = *d_alias; //~ ERROR: unable to turn pointer into raw bytes
27+
let x = *d_alias;
28+
let _val = *x; //~ERROR: is a dangling pointer (it has no provenance)
2829
}
2930
}

tests/fail/reading_half_a_pointer.stderr

+5-4
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,11 @@
1-
error: unsupported operation: unable to turn pointer into raw bytes
1+
error: Undefined Behavior: dereferencing pointer failed: $HEX[noalloc] is a dangling pointer (it has no provenance)
22
--> $DIR/reading_half_a_pointer.rs:LL:CC
33
|
4-
LL | let _x = *d_alias;
5-
| ^^^^^^^^ unable to turn pointer into raw bytes
4+
LL | let _val = *x;
5+
| ^^ dereferencing pointer failed: $HEX[noalloc] is a dangling pointer (it has no provenance)
66
|
7-
= help: this is likely not a bug in the program; it indicates that the program performed an operation that the interpreter does not support
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
89
= note: backtrace:
910
= note: inside `main` at $DIR/reading_half_a_pointer.rs:LL:CC
1011

tests/fail/transmute_fat1.rs

-13
This file was deleted.

tests/fail/transmute_fat1.stderr

-15
This file was deleted.

tests/fail/validity/ptr_integer_array_transmute.rs

-4
This file was deleted.

tests/fail/validity/ptr_integer_array_transmute.stderr

-15
This file was deleted.

tests/pass/transmute_fat.rs

-10
This file was deleted.

tests/pass/transmute_ptr.rs

+52
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
#![feature(strict_provenance)]
2+
use std::{mem, ptr};
3+
4+
fn t1() {
5+
// If we are careful, we can exploit data layout...
6+
// This is a tricky case since we are transmuting a ScalarPair type to a non-ScalarPair type.
7+
let raw = unsafe { mem::transmute::<&[u8], [*const u8; 2]>(&[42]) };
8+
let ptr: *const u8 = unsafe { mem::transmute_copy(&raw) };
9+
assert_eq!(unsafe { *ptr }, 42);
10+
}
11+
12+
#[cfg(target_pointer_width = "64")]
13+
const PTR_SIZE: usize = 8;
14+
#[cfg(target_pointer_width = "32")]
15+
const PTR_SIZE: usize = 4;
16+
17+
fn t2() {
18+
let bad = unsafe { mem::transmute::<&[u8], [u8; 2 * PTR_SIZE]>(&[1u8]) };
19+
let _val = bad[0] + bad[bad.len() - 1];
20+
}
21+
22+
fn ptr_integer_array() {
23+
let r = &mut 42;
24+
let _i: [usize; 1] = unsafe { mem::transmute(r) };
25+
26+
let x: [u8; PTR_SIZE] = unsafe { mem::transmute(&0) };
27+
}
28+
29+
fn ptr_in_two_halves() {
30+
unsafe {
31+
let ptr = &0 as *const i32;
32+
let arr = [ptr; 2];
33+
// We want to do a scalar read of a pointer at offset PTR_SIZE/2 into this array. But we
34+
// cannot use a packed struct or `read_unaligned`, as those use the memcpy code path in
35+
// Miri. So instead we shift the entire array by a bit and then the actual read we want to
36+
// do is perfectly aligned.
37+
let mut target_arr = [ptr::null::<i32>(); 3];
38+
let target = target_arr.as_mut_ptr().cast::<u8>();
39+
target.add(PTR_SIZE / 2).cast::<[*const i32; 2]>().write_unaligned(arr);
40+
// Now target_arr[1] is a mix of the two `ptr` we had stored in `arr`.
41+
let strange_ptr = target_arr[1];
42+
// Check that the provenance works out.
43+
assert_eq!(*strange_ptr.with_addr(ptr.addr()), 0);
44+
}
45+
}
46+
47+
fn main() {
48+
t1();
49+
t2();
50+
ptr_integer_array();
51+
ptr_in_two_halves();
52+
}

0 commit comments

Comments
 (0)