|
8 | 8 | // option. This file may not be copied, modified, or distributed |
9 | 9 | // except according to those terms. |
10 | 10 | #![no_std] |
11 | | -#![allow(unused_attributes)] |
12 | | -#![unstable(feature = "alloc_system", |
13 | | - reason = "this library is unlikely to be stabilized in its current \ |
14 | | - form or name", |
15 | | - issue = "32838")] |
16 | 11 | #![feature(allocator_api)] |
17 | | -#![feature(core_intrinsics)] |
18 | | -#![feature(nll)] |
19 | | -#![feature(staged_api)] |
20 | | -#![feature(rustc_attrs)] |
21 | | -#![feature(alloc_layout_extra)] |
22 | | -#![cfg_attr( |
23 | | - all(target_arch = "wasm32", not(target_os = "emscripten")), |
24 | | - feature(integer_atomics, stdsimd) |
25 | | -)] |
26 | 12 | #![cfg_attr(any(unix, target_os = "redox"), feature(libc))] |
| 13 | + |
27 | 14 | // The minimum alignment guaranteed by the architecture. This value is used to |
28 | 15 | // add fast paths for low alignment values. |
29 | 16 | #[cfg(all(any(target_arch = "x86", |
30 | 17 | target_arch = "arm", |
31 | 18 | target_arch = "mips", |
32 | 19 | target_arch = "powerpc", |
33 | | - target_arch = "powerpc64", |
34 | | - target_arch = "asmjs", |
35 | | - target_arch = "wasm32")))] |
36 | | -#[allow(dead_code)] |
| 20 | + target_arch = "powerpc64")))] |
37 | 21 | const MIN_ALIGN: usize = 8; |
38 | 22 | #[cfg(all(any(target_arch = "x86_64", |
39 | 23 | target_arch = "aarch64", |
40 | 24 | target_arch = "mips64", |
41 | 25 | target_arch = "s390x", |
42 | 26 | target_arch = "sparc64")))] |
43 | | -#[allow(dead_code)] |
44 | 27 | const MIN_ALIGN: usize = 16; |
45 | 28 |
|
46 | | -/// The default memory allocator provided by the operating system. |
47 | | -/// |
48 | | -/// This is based on `malloc` on Unix platforms and `HeapAlloc` on Windows, |
49 | | -/// plus related functions. |
50 | | -/// |
51 | | -/// This type can be used in a `static` item |
52 | | -/// with the `#[global_allocator]` attribute |
53 | | -/// to force the global allocator to be the system’s one. |
54 | | -/// (The default is jemalloc for executables, on some platforms.) |
55 | | -/// |
56 | | -/// ```rust |
57 | | -/// use std::alloc::System; |
58 | | -/// |
59 | | -/// #[global_allocator] |
60 | | -/// static A: System = System; |
61 | | -/// |
62 | | -/// fn main() { |
63 | | -/// let a = Box::new(4); // Allocates from the system allocator. |
64 | | -/// println!("{}", a); |
65 | | -/// } |
66 | | -/// ``` |
67 | | -/// |
68 | | -/// It can also be used directly to allocate memory |
69 | | -/// independently of the standard library’s global allocator. |
70 | | -#[stable(feature = "alloc_system_type", since = "1.28.0")] |
71 | 29 | pub struct System; |
72 | 30 | #[cfg(any(windows, unix, target_os = "redox"))] |
73 | 31 | mod realloc_fallback { |
@@ -96,7 +54,6 @@ mod platform { |
96 | 54 | use MIN_ALIGN; |
97 | 55 | use System; |
98 | 56 | use core::alloc::{GlobalAlloc, Layout}; |
99 | | - #[stable(feature = "alloc_system_type", since = "1.28.0")] |
100 | 57 | unsafe impl GlobalAlloc for System { |
101 | 58 | #[inline] |
102 | 59 | unsafe fn alloc(&self, layout: Layout) -> *mut u8 { |
@@ -221,7 +178,6 @@ mod platform { |
221 | 178 | }; |
222 | 179 | ptr as *mut u8 |
223 | 180 | } |
224 | | - #[stable(feature = "alloc_system_type", since = "1.28.0")] |
225 | 181 | unsafe impl GlobalAlloc for System { |
226 | 182 | #[inline] |
227 | 183 | unsafe fn alloc(&self, layout: Layout) -> *mut u8 { |
@@ -254,89 +210,3 @@ mod platform { |
254 | 210 | } |
255 | 211 | } |
256 | 212 | } |
257 | | -// This is an implementation of a global allocator on the wasm32 platform when |
258 | | -// emscripten is not in use. In that situation there's no actual runtime for us |
259 | | -// to lean on for allocation, so instead we provide our own! |
260 | | -// |
261 | | -// The wasm32 instruction set has two instructions for getting the current |
262 | | -// amount of memory and growing the amount of memory. These instructions are the |
263 | | -// foundation on which we're able to build an allocator, so we do so! Note that |
264 | | -// the instructions are also pretty "global" and this is the "global" allocator |
265 | | -// after all! |
266 | | -// |
267 | | -// The current allocator here is the `dlmalloc` crate which we've got included |
268 | | -// in the rust-lang/rust repository as a submodule. The crate is a port of |
269 | | -// dlmalloc.c from C to Rust and is basically just so we can have "pure Rust" |
270 | | -// for now which is currently technically required (can't link with C yet). |
271 | | -// |
272 | | -// The crate itself provides a global allocator which on wasm has no |
273 | | -// synchronization as there are no threads! |
274 | | -#[cfg(all(target_arch = "wasm32", not(target_os = "emscripten")))] |
275 | | -mod platform { |
276 | | - extern crate dlmalloc; |
277 | | - use core::alloc::{GlobalAlloc, Layout}; |
278 | | - use System; |
279 | | - static mut DLMALLOC: dlmalloc::Dlmalloc = dlmalloc::DLMALLOC_INIT; |
280 | | - #[stable(feature = "alloc_system_type", since = "1.28.0")] |
281 | | - unsafe impl GlobalAlloc for System { |
282 | | - #[inline] |
283 | | - unsafe fn alloc(&self, layout: Layout) -> *mut u8 { |
284 | | - let _lock = lock::lock(); |
285 | | - DLMALLOC.malloc(layout.size(), layout.align()) |
286 | | - } |
287 | | - #[inline] |
288 | | - unsafe fn alloc_zeroed(&self, layout: Layout) -> *mut u8 { |
289 | | - let _lock = lock::lock(); |
290 | | - DLMALLOC.calloc(layout.size(), layout.align()) |
291 | | - } |
292 | | - #[inline] |
293 | | - unsafe fn dealloc(&self, ptr: *mut u8, layout: Layout) { |
294 | | - let _lock = lock::lock(); |
295 | | - DLMALLOC.free(ptr, layout.size(), layout.align()) |
296 | | - } |
297 | | - #[inline] |
298 | | - unsafe fn realloc(&self, ptr: *mut u8, layout: Layout, new_size: usize) -> *mut u8 { |
299 | | - let _lock = lock::lock(); |
300 | | - DLMALLOC.realloc(ptr, layout.size(), layout.align(), new_size) |
301 | | - } |
302 | | - } |
303 | | - #[cfg(target_feature = "atomics")] |
304 | | - mod lock { |
305 | | - use core::arch::wasm32; |
306 | | - use core::sync::atomic::{AtomicI32, Ordering::SeqCst}; |
307 | | - static LOCKED: AtomicI32 = AtomicI32::new(0); |
308 | | - pub struct DropLock; |
309 | | - pub fn lock() -> DropLock { |
310 | | - loop { |
311 | | - if LOCKED.swap(1, SeqCst) == 0 { |
312 | | - return DropLock |
313 | | - } |
314 | | - unsafe { |
315 | | - let r = wasm32::atomic::wait_i32( |
316 | | - &LOCKED as *const AtomicI32 as *mut i32, |
317 | | - 1, // expected value |
318 | | - -1, // timeout |
319 | | - ); |
320 | | - debug_assert!(r == 0 || r == 1); |
321 | | - } |
322 | | - } |
323 | | - } |
324 | | - impl Drop for DropLock { |
325 | | - fn drop(&mut self) { |
326 | | - let r = LOCKED.swap(0, SeqCst); |
327 | | - debug_assert_eq!(r, 1); |
328 | | - unsafe { |
329 | | - wasm32::atomic::wake( |
330 | | - &LOCKED as *const AtomicI32 as *mut i32, |
331 | | - 1, // only one thread |
332 | | - ); |
333 | | - } |
334 | | - } |
335 | | - } |
336 | | - } |
337 | | - #[cfg(not(target_feature = "atomics"))] |
338 | | - mod lock { |
339 | | - #[inline] |
340 | | - pub fn lock() {} // no atomics, no threads, that's easy! |
341 | | - } |
342 | | -} |
0 commit comments