1 use super::cvt;
2 use crate::prelude::*;
3 use crate::runtime::vm::SendSyncPtr;
4 use crate::runtime::vm::sys::capi;
5 use crate::vm::sys::DecommitBehavior;
6 use core::ptr::{self, NonNull};
7 #[cfg(feature = "std")]
8 use std::{fs::File, sync::Arc};
9
10 pub use crate::runtime::vm::pagemap_disabled::{PageMap, reset_with_pagemap};
11
expose_existing_mapping(ptr: *mut u8, len: usize) -> Result<()>12 pub unsafe fn expose_existing_mapping(ptr: *mut u8, len: usize) -> Result<()> {
13 unsafe {
14 cvt(capi::wasmtime_mprotect(
15 ptr.cast(),
16 len,
17 capi::PROT_READ | capi::PROT_WRITE,
18 ))
19 }
20 }
21
hide_existing_mapping(ptr: *mut u8, len: usize) -> Result<()>22 pub unsafe fn hide_existing_mapping(ptr: *mut u8, len: usize) -> Result<()> {
23 unsafe { cvt(capi::wasmtime_mprotect(ptr.cast(), len, 0)) }
24 }
25
erase_existing_mapping(ptr: *mut u8, len: usize) -> Result<()>26 pub unsafe fn erase_existing_mapping(ptr: *mut u8, len: usize) -> Result<()> {
27 unsafe { cvt(capi::wasmtime_mmap_remap(ptr.cast(), len, 0)) }
28 }
29
30 #[cfg(feature = "pooling-allocator")]
commit_pages(_addr: *mut u8, _len: usize) -> Result<()>31 pub unsafe fn commit_pages(_addr: *mut u8, _len: usize) -> Result<()> {
32 // Pages are always READ | WRITE so there's nothing that needs to be
33 // done here.
34 Ok(())
35 }
36
37 #[cfg(feature = "pooling-allocator")]
decommit_pages(addr: *mut u8, len: usize) -> Result<()>38 pub unsafe fn decommit_pages(addr: *mut u8, len: usize) -> Result<()> {
39 if len == 0 {
40 return Ok(());
41 }
42
43 unsafe {
44 cvt(capi::wasmtime_mmap_remap(
45 addr,
46 len,
47 capi::PROT_READ | capi::PROT_WRITE,
48 ))
49 }
50 }
51
get_page_size() -> usize52 pub fn get_page_size() -> usize {
53 unsafe { capi::wasmtime_page_size() }
54 }
55
decommit_behavior() -> DecommitBehavior56 pub fn decommit_behavior() -> DecommitBehavior {
57 DecommitBehavior::Zero
58 }
59
60 #[derive(PartialEq, Debug)]
61 pub struct MemoryImageSource {
62 data: SendSyncPtr<capi::wasmtime_memory_image>,
63 }
64
65 impl MemoryImageSource {
66 #[cfg(feature = "std")]
from_file(_file: &Arc<File>) -> Option<MemoryImageSource>67 pub fn from_file(_file: &Arc<File>) -> Option<MemoryImageSource> {
68 None
69 }
70
from_data(data: &[u8]) -> Result<Option<MemoryImageSource>>71 pub fn from_data(data: &[u8]) -> Result<Option<MemoryImageSource>> {
72 unsafe {
73 let mut ptr = ptr::null_mut();
74 cvt(capi::wasmtime_memory_image_new(
75 data.as_ptr(),
76 data.len(),
77 &mut ptr,
78 ))?;
79 match NonNull::new(ptr) {
80 Some(ptr) => Ok(Some(MemoryImageSource {
81 data: SendSyncPtr::new(ptr),
82 })),
83 None => Ok(None),
84 }
85 }
86 }
87
88 #[inline]
image_ptr(&self) -> SendSyncPtr<capi::wasmtime_memory_image>89 pub(super) fn image_ptr(&self) -> SendSyncPtr<capi::wasmtime_memory_image> {
90 self.data
91 }
92
remap_as_zeros_at(&self, base: *mut u8, len: usize) -> Result<()>93 pub unsafe fn remap_as_zeros_at(&self, base: *mut u8, len: usize) -> Result<()> {
94 unsafe {
95 cvt(capi::wasmtime_mmap_remap(
96 base.cast(),
97 len,
98 capi::PROT_READ | capi::PROT_WRITE,
99 ))
100 }
101 }
102 }
103
104 impl Drop for MemoryImageSource {
drop(&mut self)105 fn drop(&mut self) {
106 unsafe {
107 capi::wasmtime_memory_image_free(self.data.as_ptr());
108 }
109 }
110 }
111