]> git.lizzy.rs Git - rust.git/blob - src/libcore/raw.rs
Rollup merge of #43846 - frewsxcv:frewsxcv-mailmap, r=Mark-Simulacrum
[rust.git] / src / libcore / raw.rs
1 // Copyright 2013 The Rust Project Developers. See the COPYRIGHT
2 // file at the top-level directory of this distribution and at
3 // http://rust-lang.org/COPYRIGHT.
4 //
5 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8 // option. This file may not be copied, modified, or distributed
9 // except according to those terms.
10
11 #![allow(missing_docs)]
12 #![unstable(feature = "raw", issue = "27751")]
13
14 //! Contains struct definitions for the layout of compiler built-in types.
15 //!
16 //! They can be used as targets of transmutes in unsafe code for manipulating
17 //! the raw representations directly.
18 //!
19 //! Their definition should always match the ABI defined in `rustc::back::abi`.
20
21 /// The representation of a trait object like `&SomeTrait`.
22 ///
23 /// This struct has the same layout as types like `&SomeTrait` and
24 /// `Box<AnotherTrait>`. The [Trait Objects chapter of the
25 /// Book][moreinfo] contains more details about the precise nature of
26 /// these internals.
27 ///
28 /// [moreinfo]: ../../book/first-edition/trait-objects.html#representation
29 ///
30 /// `TraitObject` is guaranteed to match layouts, but it is not the
31 /// type of trait objects (e.g. the fields are not directly accessible
32 /// on a `&SomeTrait`) nor does it control that layout (changing the
33 /// definition will not change the layout of a `&SomeTrait`). It is
34 /// only designed to be used by unsafe code that needs to manipulate
35 /// the low-level details.
36 ///
37 /// There is no way to refer to all trait objects generically, so the only
38 /// way to create values of this type is with functions like
39 /// [`std::mem::transmute`][transmute]. Similarly, the only way to create a true
40 /// trait object from a `TraitObject` value is with `transmute`.
41 ///
42 /// [transmute]: ../intrinsics/fn.transmute.html
43 ///
44 /// Synthesizing a trait object with mismatched types—one where the
45 /// vtable does not correspond to the type of the value to which the
46 /// data pointer points—is highly likely to lead to undefined
47 /// behavior.
48 ///
49 /// # Examples
50 ///
51 /// ```
52 /// #![feature(raw)]
53 ///
54 /// use std::{mem, raw};
55 ///
56 /// // an example trait
57 /// trait Foo {
58 ///     fn bar(&self) -> i32;
59 /// }
60 ///
61 /// impl Foo for i32 {
62 ///     fn bar(&self) -> i32 {
63 ///          *self + 1
64 ///     }
65 /// }
66 ///
67 /// let value: i32 = 123;
68 ///
69 /// // let the compiler make a trait object
70 /// let object: &Foo = &value;
71 ///
72 /// // look at the raw representation
73 /// let raw_object: raw::TraitObject = unsafe { mem::transmute(object) };
74 ///
75 /// // the data pointer is the address of `value`
76 /// assert_eq!(raw_object.data as *const i32, &value as *const _);
77 ///
78 /// let other_value: i32 = 456;
79 ///
80 /// // construct a new object, pointing to a different `i32`, being
81 /// // careful to use the `i32` vtable from `object`
82 /// let synthesized: &Foo = unsafe {
83 ///      mem::transmute(raw::TraitObject {
84 ///          data: &other_value as *const _ as *mut (),
85 ///          vtable: raw_object.vtable,
86 ///      })
87 /// };
88 ///
89 /// // it should work just as if we had constructed a trait object out of
90 /// // `other_value` directly
91 /// assert_eq!(synthesized.bar(), 457);
92 /// ```
93 #[repr(C)]
94 #[derive(Copy, Clone)]
95 #[allow(missing_debug_implementations)]
96 pub struct TraitObject {
97     pub data: *mut (),
98     pub vtable: *mut (),
99 }