diff options
| author | Patrick Walton <pcwalton@mimiga.net> | 2013-04-22 16:22:36 -0700 |
|---|---|---|
| committer | Patrick Walton <pcwalton@mimiga.net> | 2013-04-29 14:30:53 -0700 |
| commit | b6277f8140a496bed371e97ea1e260858e77fb41 (patch) | |
| tree | c85ae630368d3b5a1d0fb2b55ed585115b735c5a /src/libcore | |
| parent | b0522a497ccfcc7b124d77121d8f076af7f09b71 (diff) | |
| download | rust-b6277f8140a496bed371e97ea1e260858e77fb41.tar.gz rust-b6277f8140a496bed371e97ea1e260858e77fb41.zip | |
librustc: Implement `reinterpret_cast` in terms of `transmute`.
Diffstat (limited to 'src/libcore')
| -rw-r--r-- | src/libcore/cast.rs | 36 |
1 files changed, 36 insertions, 0 deletions
diff --git a/src/libcore/cast.rs b/src/libcore/cast.rs index 1d214f402f5..620f716a63d 100644 --- a/src/libcore/cast.rs +++ b/src/libcore/cast.rs @@ -10,21 +10,48 @@ //! Unsafe casting functions +use sys; +use unstable; + pub mod rusti { #[abi = "rust-intrinsic"] #[link_name = "rusti"] pub extern "rust-intrinsic" { fn forget<T>(+x: T); + + #[cfg(stage0)] fn reinterpret_cast<T, U>(&&e: T) -> U; + + #[cfg(stage1)] + #[cfg(stage2)] + #[cfg(stage3)] + fn transmute<T,U>(e: T) -> U; } } /// Casts the value at `src` to U. The two types must have the same length. #[inline(always)] +#[cfg(stage0)] pub unsafe fn reinterpret_cast<T, U>(src: &T) -> U { rusti::reinterpret_cast(*src) } +#[inline(always)] +#[cfg(stage1)] +#[cfg(stage2)] +#[cfg(stage3)] +pub unsafe fn reinterpret_cast<T, U>(src: &T) -> U { + let mut dest: U = unstable::intrinsics::init(); + { + let dest_ptr: *mut u8 = rusti::transmute(&mut dest); + let src_ptr: *u8 = rusti::transmute(src); + unstable::intrinsics::memmove64(dest_ptr, + src_ptr, + sys::size_of::<U>() as u64); + } + dest +} + /** * Move a thing into the void * @@ -53,12 +80,21 @@ pub unsafe fn bump_box_refcount<T>(t: @T) { forget(t); } * assert!(transmute("L") == ~[76u8, 0u8]); */ #[inline(always)] +#[cfg(stage0)] pub unsafe fn transmute<L, G>(thing: L) -> G { let newthing: G = reinterpret_cast(&thing); forget(thing); newthing } +#[inline(always)] +#[cfg(stage1)] +#[cfg(stage2)] +#[cfg(stage3)] +pub unsafe fn transmute<L, G>(thing: L) -> G { + rusti::transmute(thing) +} + /// Coerce an immutable reference to be mutable. #[inline(always)] pub unsafe fn transmute_mut<'a,T>(ptr: &'a T) -> &'a mut T { transmute(ptr) } |
