1 | //! `core_arch` |
2 | |
3 | #[macro_use ] |
4 | mod macros; |
5 | |
6 | #[cfg (any(target_arch = "riscv32" , target_arch = "riscv64" , doc))] |
7 | mod riscv_shared; |
8 | |
9 | #[cfg (any( |
10 | target_arch = "arm" , |
11 | target_arch = "aarch64" , |
12 | target_arch = "arm64ec" , |
13 | doc |
14 | ))] |
15 | mod arm_shared; |
16 | |
17 | mod simd; |
18 | |
19 | #[doc = include_str!("core_arch_docs.md" )] |
20 | #[stable (feature = "simd_arch" , since = "1.27.0" )] |
21 | pub mod arch { |
22 | /// Platform-specific intrinsics for the `x86` platform. |
23 | /// |
24 | /// See the [module documentation](../index.html) for more details. |
25 | #[cfg (any(target_arch = "x86" , doc))] |
26 | #[doc (cfg(target_arch = "x86" ))] |
27 | #[stable (feature = "simd_x86" , since = "1.27.0" )] |
28 | pub mod x86 { |
29 | #[stable (feature = "simd_x86" , since = "1.27.0" )] |
30 | pub use crate::core_arch::x86::*; |
31 | } |
32 | |
33 | /// Platform-specific intrinsics for the `x86_64` platform. |
34 | /// |
35 | /// See the [module documentation](../index.html) for more details. |
36 | #[cfg (any(target_arch = "x86_64" , doc))] |
37 | #[doc (cfg(target_arch = "x86_64" ))] |
38 | #[stable (feature = "simd_x86" , since = "1.27.0" )] |
39 | pub mod x86_64 { |
40 | #[stable (feature = "simd_x86" , since = "1.27.0" )] |
41 | pub use crate::core_arch::x86::*; |
42 | #[stable (feature = "simd_x86" , since = "1.27.0" )] |
43 | pub use crate::core_arch::x86_64::*; |
44 | } |
45 | |
46 | /// Platform-specific intrinsics for the `arm` platform. |
47 | /// |
48 | /// See the [module documentation](../index.html) for more details. |
49 | #[cfg (any(target_arch = "arm" , doc))] |
50 | #[doc (cfg(target_arch = "arm" ))] |
51 | #[unstable (feature = "stdarch_arm_neon_intrinsics" , issue = "111800" )] |
52 | pub mod arm { |
53 | #[unstable (feature = "stdarch_arm_neon_intrinsics" , issue = "111800" )] |
54 | pub use crate::core_arch::arm::*; |
55 | } |
56 | |
57 | /// Platform-specific intrinsics for the `aarch64` platform. |
58 | /// |
59 | /// See the [module documentation](../index.html) for more details. |
60 | #[cfg (any(target_arch = "aarch64" , target_arch = "arm64ec" , doc))] |
61 | #[doc (cfg(any(target_arch = "aarch64" , target_arch = "arm64ec" )))] |
62 | #[stable (feature = "neon_intrinsics" , since = "1.59.0" )] |
63 | pub mod aarch64 { |
64 | #[stable (feature = "neon_intrinsics" , since = "1.59.0" )] |
65 | pub use crate::core_arch::aarch64::*; |
66 | } |
67 | |
68 | /// Platform-specific intrinsics for the `riscv32` platform. |
69 | /// |
70 | /// See the [module documentation](../index.html) for more details. |
71 | #[cfg (any(target_arch = "riscv32" , doc))] |
72 | #[doc (cfg(any(target_arch = "riscv32" )))] |
73 | #[unstable (feature = "riscv_ext_intrinsics" , issue = "114544" )] |
74 | pub mod riscv32 { |
75 | pub use crate::core_arch::riscv32::*; |
76 | pub use crate::core_arch::riscv_shared::*; |
77 | } |
78 | |
79 | /// Platform-specific intrinsics for the `riscv64` platform. |
80 | /// |
81 | /// See the [module documentation](../index.html) for more details. |
82 | #[cfg (any(target_arch = "riscv64" , doc))] |
83 | #[doc (cfg(any(target_arch = "riscv64" )))] |
84 | #[unstable (feature = "riscv_ext_intrinsics" , issue = "114544" )] |
85 | pub mod riscv64 { |
86 | pub use crate::core_arch::riscv64::*; |
87 | // RISC-V RV64 supports all RV32 instructions as well in current specifications (2022-01-05). |
88 | // Module `riscv_shared` includes instructions available under all RISC-V platforms, |
89 | // i.e. RISC-V RV32 instructions. |
90 | pub use crate::core_arch::riscv_shared::*; |
91 | } |
92 | |
93 | /// Platform-specific intrinsics for the `wasm32` platform. |
94 | /// |
95 | /// This module provides intrinsics specific to the WebAssembly |
96 | /// architecture. Here you'll find intrinsics specific to WebAssembly that |
97 | /// aren't otherwise surfaced somewhere in a cross-platform abstraction of |
98 | /// `std`, and you'll also find functions for leveraging WebAssembly |
99 | /// proposals such as [atomics] and [simd]. |
100 | /// |
101 | /// Intrinsics in the `wasm32` module are modeled after the WebAssembly |
102 | /// instructions that they represent. Most functions are named after the |
103 | /// instruction they intend to correspond to, and the arguments/results |
104 | /// correspond to the type signature of the instruction itself. Stable |
105 | /// WebAssembly instructions are [documented online][instrdoc]. |
106 | /// |
107 | /// [instrdoc]: https://webassembly.github.io/spec/core/valid/instructions.html |
108 | /// |
109 | /// If a proposal is not yet stable in WebAssembly itself then the functions |
110 | /// within this function may be unstable and require the nightly channel of |
111 | /// Rust to use. As the proposal itself stabilizes the intrinsics in this |
112 | /// module should stabilize as well. |
113 | /// |
114 | /// [atomics]: https://github.com/webassembly/threads |
115 | /// [simd]: https://github.com/webassembly/simd |
116 | /// |
117 | /// See the [module documentation](../index.html) for general information |
118 | /// about the `arch` module and platform intrinsics. |
119 | /// |
120 | /// ## Atomics |
121 | /// |
122 | /// The [threads proposal][atomics] for WebAssembly adds a number of |
123 | /// instructions for dealing with multithreaded programs. Most instructions |
124 | /// added in the [atomics] proposal are exposed in Rust through the |
125 | /// `std::sync::atomic` module. Some instructions, however, don't have |
126 | /// direct equivalents in Rust so they're exposed here instead. |
127 | /// |
128 | /// Note that the instructions added in the [atomics] proposal can work in |
129 | /// either a context with a shared wasm memory and without. These intrinsics |
130 | /// are always available in the standard library, but you likely won't be |
131 | /// able to use them too productively unless you recompile the standard |
132 | /// library (and all your code) with `-Ctarget-feature=+atomics`. |
133 | /// |
134 | /// It's also worth pointing out that multi-threaded WebAssembly and its |
135 | /// story in Rust is still in a somewhat "early days" phase as of the time |
136 | /// of this writing. Pieces should mostly work but it generally requires a |
137 | /// good deal of manual setup. At this time it's not as simple as "just call |
138 | /// `std::thread::spawn`", but it will hopefully get there one day! |
139 | /// |
140 | /// ## SIMD |
141 | /// |
142 | /// The [simd proposal][simd] for WebAssembly added a new `v128` type for a |
143 | /// 128-bit SIMD register. It also added a large array of instructions to |
144 | /// operate on the `v128` type to perform data processing. Using SIMD on |
145 | /// wasm is intended to be similar to as you would on `x86_64`, for example. |
146 | /// You'd write a function such as: |
147 | /// |
148 | /// ```rust,ignore |
149 | /// #[cfg(target_arch = "wasm32")] |
150 | /// #[target_feature(enable = "simd128")] |
151 | /// unsafe fn uses_simd() { |
152 | /// use std::arch::wasm32::*; |
153 | /// // ... |
154 | /// } |
155 | /// ``` |
156 | /// |
157 | /// Unlike `x86_64`, however, WebAssembly does not currently have dynamic |
158 | /// detection at runtime as to whether SIMD is supported (this is one of the |
159 | /// motivators for the [conditional sections][condsections] and [feature |
160 | /// detection] proposals, but that is still pretty early days). This means |
161 | /// that your binary will either have SIMD and can only run on engines |
162 | /// which support SIMD, or it will not have SIMD at all. For compatibility |
163 | /// the standard library itself does not use any SIMD internally. |
164 | /// Determining how best to ship your WebAssembly binary with SIMD is |
165 | /// largely left up to you as it can be pretty nuanced depending on |
166 | /// your situation. |
167 | /// |
168 | /// [condsections]: https://github.com/webassembly/conditional-sections |
169 | /// [feature detection]: https://github.com/WebAssembly/feature-detection |
170 | /// |
171 | /// To enable SIMD support at compile time you need to do one of two things: |
172 | /// |
173 | /// * First you can annotate functions with `#[target_feature(enable = |
174 | /// "simd128")]`. This causes just that one function to have SIMD support |
175 | /// available to it, and intrinsics will get inlined as usual in this |
176 | /// situation. |
177 | /// |
178 | /// * Second you can compile your program with `-Ctarget-feature=+simd128`. |
179 | /// This compilation flag blanket enables SIMD support for your entire |
180 | /// compilation. Note that this does not include the standard library |
181 | /// unless you [recompile the standard library][buildstd]. |
182 | /// |
183 | /// [buildstd]: https://doc.rust-lang.org/nightly/cargo/reference/unstable.html#build-std |
184 | /// |
185 | /// If you enable SIMD via either of these routes then you'll have a |
186 | /// WebAssembly binary that uses SIMD instructions, and you'll need to ship |
187 | /// that accordingly. Also note that if you call SIMD intrinsics but don't |
188 | /// enable SIMD via either of these mechanisms, you'll still have SIMD |
189 | /// generated in your program. This means to generate a binary without SIMD |
190 | /// you'll need to avoid both options above plus calling into any intrinsics |
191 | /// in this module. |
192 | #[cfg (any(target_arch = "wasm32" , doc))] |
193 | #[doc (cfg(target_arch = "wasm32" ))] |
194 | #[stable (feature = "simd_wasm32" , since = "1.33.0" )] |
195 | pub mod wasm32 { |
196 | #[stable (feature = "simd_wasm32" , since = "1.33.0" )] |
197 | pub use crate::core_arch::wasm32::*; |
198 | } |
199 | |
200 | /// Platform-specific intrinsics for the `wasm64` platform. |
201 | /// |
202 | /// See the [module documentation](../index.html) for more details. |
203 | #[cfg (any(target_arch = "wasm64" , doc))] |
204 | #[doc (cfg(target_arch = "wasm64" ))] |
205 | #[unstable (feature = "simd_wasm64" , issue = "90599" )] |
206 | pub mod wasm64 { |
207 | #[unstable (feature = "simd_wasm64" , issue = "90599" )] |
208 | pub use crate::core_arch::wasm32::*; |
209 | } |
210 | |
211 | /// Platform-specific intrinsics for the `wasm` target family. |
212 | /// |
213 | /// See the [module documentation](../index.html) for more details. |
214 | #[cfg (any(target_family = "wasm" , doc))] |
215 | #[doc (cfg(target_family = "wasm" ))] |
216 | #[unstable (feature = "simd_wasm64" , issue = "90599" )] |
217 | pub mod wasm { |
218 | #[unstable (feature = "simd_wasm64" , issue = "90599" )] |
219 | pub use crate::core_arch::wasm32::*; |
220 | } |
221 | |
222 | /// Platform-specific intrinsics for the `mips` platform. |
223 | /// |
224 | /// See the [module documentation](../index.html) for more details. |
225 | #[cfg (any(target_arch = "mips" , doc))] |
226 | #[doc (cfg(target_arch = "mips" ))] |
227 | #[unstable (feature = "stdarch_mips" , issue = "111198" )] |
228 | pub mod mips { |
229 | pub use crate::core_arch::mips::*; |
230 | } |
231 | |
232 | /// Platform-specific intrinsics for the `mips64` platform. |
233 | /// |
234 | /// See the [module documentation](../index.html) for more details. |
235 | #[cfg (any(target_arch = "mips64" , doc))] |
236 | #[doc (cfg(target_arch = "mips64" ))] |
237 | #[unstable (feature = "stdarch_mips" , issue = "111198" )] |
238 | pub mod mips64 { |
239 | pub use crate::core_arch::mips::*; |
240 | } |
241 | |
242 | /// Platform-specific intrinsics for the `PowerPC` platform. |
243 | /// |
244 | /// See the [module documentation](../index.html) for more details. |
245 | #[cfg (any(target_arch = "powerpc" , doc))] |
246 | #[doc (cfg(target_arch = "powerpc" ))] |
247 | #[unstable (feature = "stdarch_powerpc" , issue = "111145" )] |
248 | pub mod powerpc { |
249 | pub use crate::core_arch::powerpc::*; |
250 | } |
251 | |
252 | /// Platform-specific intrinsics for the `PowerPC64` platform. |
253 | /// |
254 | /// See the [module documentation](../index.html) for more details. |
255 | #[cfg (any(target_arch = "powerpc64" , doc))] |
256 | #[doc (cfg(target_arch = "powerpc64" ))] |
257 | #[unstable (feature = "stdarch_powerpc" , issue = "111145" )] |
258 | pub mod powerpc64 { |
259 | pub use crate::core_arch::powerpc64::*; |
260 | } |
261 | |
262 | /// Platform-specific intrinsics for the `NVPTX` platform. |
263 | /// |
264 | /// See the [module documentation](../index.html) for more details. |
265 | #[cfg (any(target_arch = "nvptx64" , doc))] |
266 | #[doc (cfg(target_arch = "nvptx64" ))] |
267 | #[unstable (feature = "stdarch_nvptx" , issue = "111199" )] |
268 | pub mod nvptx { |
269 | pub use crate::core_arch::nvptx::*; |
270 | } |
271 | |
272 | /// Platform-specific intrinsics for the `loongarch` platform. |
273 | /// |
274 | /// See the [module documentation](../index.html) for more details. |
275 | #[cfg (any(target_arch = "loongarch64" , doc))] |
276 | #[doc (cfg(target_arch = "loongarch64" ))] |
277 | #[unstable (feature = "stdarch_loongarch" , issue = "117427" )] |
278 | pub mod loongarch64 { |
279 | pub use crate::core_arch::loongarch64::*; |
280 | } |
281 | } |
282 | |
283 | #[cfg (any(target_arch = "x86" , target_arch = "x86_64" , doc))] |
284 | #[doc (cfg(any(target_arch = "x86" , target_arch = "x86_64" )))] |
285 | mod x86; |
286 | #[cfg (any(target_arch = "x86_64" , doc))] |
287 | #[doc (cfg(target_arch = "x86_64" ))] |
288 | mod x86_64; |
289 | |
290 | #[cfg (any(target_arch = "aarch64" , target_arch = "arm64ec" , doc))] |
291 | #[doc (cfg(any(target_arch = "aarch64" , target_arch = "arm64ec" )))] |
292 | mod aarch64; |
293 | #[cfg (any(target_arch = "arm" , doc))] |
294 | #[doc (cfg(any(target_arch = "arm" )))] |
295 | mod arm; |
296 | |
297 | #[cfg (any(target_arch = "riscv32" , doc))] |
298 | #[doc (cfg(any(target_arch = "riscv32" )))] |
299 | mod riscv32; |
300 | |
301 | #[cfg (any(target_arch = "riscv64" , doc))] |
302 | #[doc (cfg(any(target_arch = "riscv64" )))] |
303 | mod riscv64; |
304 | |
305 | #[cfg (any(target_family = "wasm" , doc))] |
306 | #[doc (cfg(target_family = "wasm" ))] |
307 | mod wasm32; |
308 | |
309 | #[cfg (any(target_arch = "mips" , target_arch = "mips64" , doc))] |
310 | #[doc (cfg(any(target_arch = "mips" , target_arch = "mips64" )))] |
311 | mod mips; |
312 | |
313 | #[cfg (any(target_arch = "powerpc" , target_arch = "powerpc64" , doc))] |
314 | #[doc (cfg(any(target_arch = "powerpc" , target_arch = "powerpc64" )))] |
315 | mod powerpc; |
316 | |
317 | #[cfg (any(target_arch = "powerpc64" , doc))] |
318 | #[doc (cfg(target_arch = "powerpc64" ))] |
319 | mod powerpc64; |
320 | |
321 | #[cfg (any(target_arch = "nvptx64" , doc))] |
322 | #[doc (cfg(target_arch = "nvptx64" ))] |
323 | mod nvptx; |
324 | |
325 | #[cfg (any(target_arch = "loongarch64" , doc))] |
326 | #[doc (cfg(target_arch = "loongarch64" ))] |
327 | mod loongarch64; |
328 | |