mirror of
https://github.com/mii443/wasmer.git
synced 2025-12-07 13:18:20 +00:00
rustfmt
This commit is contained in:
@@ -80,9 +80,7 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||||||
// We will get bytes out of the memory so we need to
|
// We will get bytes out of the memory so we need to
|
||||||
// decode them into a string.
|
// decode them into a string.
|
||||||
let memory_view = memory.view(&store);
|
let memory_view = memory.view(&store);
|
||||||
let str = ptr
|
let str = ptr.read_utf8_string(&memory_view, length as u32).unwrap();
|
||||||
.read_utf8_string(&memory_view, length as u32)
|
|
||||||
.unwrap();
|
|
||||||
println!("Memory contents: {:?}", str);
|
println!("Memory contents: {:?}", str);
|
||||||
|
|
||||||
// What about changing the contents of the memory with a more
|
// What about changing the contents of the memory with a more
|
||||||
|
|||||||
21
lib/api/src/js/externals/memory.rs
vendored
21
lib/api/src/js/externals/memory.rs
vendored
@@ -240,7 +240,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
let view = unsafe { &*(self.base) };
|
let view = unsafe { &*(self.base) };
|
||||||
if end > view.length().into() {
|
if end > view.length().into() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", buf.len(), end, view.length());
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
buf.len(),
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
view.subarray(offset as _, end as _)
|
view.subarray(offset as _, end as _)
|
||||||
@@ -259,7 +264,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
let view = unsafe { &*(self.base) };
|
let view = unsafe { &*(self.base) };
|
||||||
if end > view.length().into() {
|
if end > view.length().into() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", buf.len(), end, view.length());
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
buf.len(),
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
let buf_ptr = buf.as_mut_ptr() as *mut u8;
|
let buf_ptr = buf.as_mut_ptr() as *mut u8;
|
||||||
@@ -276,7 +286,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
let view = unsafe { &mut *(self.base) };
|
let view = unsafe { &mut *(self.base) };
|
||||||
if end > view.length().into() {
|
if end > view.length().into() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})", data.len(), end, view.length());
|
warn!(
|
||||||
|
"attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
data.len(),
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
view.subarray(offset as _, end as _).copy_from(data);
|
view.subarray(offset as _, end as _).copy_from(data);
|
||||||
|
|||||||
70
lib/api/src/js/externals/memory_view.rs
vendored
70
lib/api/src/js/externals/memory_view.rs
vendored
@@ -9,8 +9,8 @@ use tracing::warn;
|
|||||||
|
|
||||||
use wasmer_types::{Bytes, Pages};
|
use wasmer_types::{Bytes, Pages};
|
||||||
|
|
||||||
use super::Memory;
|
|
||||||
use super::memory::MemoryBuffer;
|
use super::memory::MemoryBuffer;
|
||||||
|
use super::Memory;
|
||||||
|
|
||||||
/// A WebAssembly `memory` view.
|
/// A WebAssembly `memory` view.
|
||||||
///
|
///
|
||||||
@@ -25,8 +25,7 @@ pub struct MemoryView<'a> {
|
|||||||
marker: PhantomData<&'a Memory>,
|
marker: PhantomData<&'a Memory>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> MemoryView<'a>
|
impl<'a> MemoryView<'a> {
|
||||||
{
|
|
||||||
pub(crate) fn new(memory: &Memory, store: &impl AsStoreRef) -> Self {
|
pub(crate) fn new(memory: &Memory, store: &impl AsStoreRef) -> Self {
|
||||||
let buffer = memory
|
let buffer = memory
|
||||||
.handle
|
.handle
|
||||||
@@ -34,17 +33,12 @@ impl<'a> MemoryView<'a>
|
|||||||
.memory
|
.memory
|
||||||
.buffer();
|
.buffer();
|
||||||
|
|
||||||
let size = js_sys::Reflect::get(
|
let size = js_sys::Reflect::get(&buffer, &"byteLength".into())
|
||||||
&buffer,
|
|
||||||
&"byteLength".into(),
|
|
||||||
)
|
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.as_f64()
|
.as_f64()
|
||||||
.unwrap() as u64;
|
.unwrap() as u64;
|
||||||
|
|
||||||
let view = js_sys::Uint8Array::new(
|
let view = js_sys::Uint8Array::new(&buffer);
|
||||||
&buffer,
|
|
||||||
);
|
|
||||||
|
|
||||||
Self {
|
Self {
|
||||||
view,
|
view,
|
||||||
@@ -94,11 +88,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn read(
|
pub fn read(&self, offset: u64, data: &mut [u8]) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
data: &mut [u8],
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
let view = &self.view;
|
let view = &self.view;
|
||||||
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
||||||
let len: u32 = data
|
let len: u32 = data
|
||||||
@@ -108,7 +98,12 @@ impl<'a> MemoryView<'a>
|
|||||||
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > view.length() {
|
if end > view.length() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", len, end, view.length());
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
len,
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
Err(MemoryAccessError::HeapOutOfBounds)?;
|
Err(MemoryAccessError::HeapOutOfBounds)?;
|
||||||
}
|
}
|
||||||
view.subarray(offset, end).copy_to(data);
|
view.subarray(offset, end).copy_to(data);
|
||||||
@@ -119,15 +114,16 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn read_u8(
|
pub fn read_u8(&self, offset: u64) -> Result<u8, MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64
|
|
||||||
) -> Result<u8, MemoryAccessError> {
|
|
||||||
let view = &self.view;
|
let view = &self.view;
|
||||||
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
||||||
if offset >= view.length() {
|
if offset >= view.length() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read beyond the bounds of the memory view ({} >= {})", offset, view.length());
|
warn!(
|
||||||
|
"attempted to read beyond the bounds of the memory view ({} >= {})",
|
||||||
|
offset,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
Err(MemoryAccessError::HeapOutOfBounds)?;
|
Err(MemoryAccessError::HeapOutOfBounds)?;
|
||||||
}
|
}
|
||||||
Ok(view.get_index(offset))
|
Ok(view.get_index(offset))
|
||||||
@@ -157,7 +153,12 @@ impl<'a> MemoryView<'a>
|
|||||||
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > view.length() {
|
if end > view.length() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", len, end, view.length());
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
len,
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
Err(MemoryAccessError::HeapOutOfBounds)?;
|
Err(MemoryAccessError::HeapOutOfBounds)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -179,11 +180,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent reads/writes.
|
/// concurrent reads/writes.
|
||||||
pub fn write(
|
pub fn write(&self, offset: u64, data: &[u8]) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
data: &[u8],
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
||||||
let len: u32 = data
|
let len: u32 = data
|
||||||
.len()
|
.len()
|
||||||
@@ -193,7 +190,12 @@ impl<'a> MemoryView<'a>
|
|||||||
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
let end = offset.checked_add(len).ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > view.length() {
|
if end > view.length() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})", len, end, view.length());
|
warn!(
|
||||||
|
"attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
len,
|
||||||
|
end,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
Err(MemoryAccessError::HeapOutOfBounds)?;
|
Err(MemoryAccessError::HeapOutOfBounds)?;
|
||||||
}
|
}
|
||||||
view.subarray(offset, end).copy_from(data);
|
view.subarray(offset, end).copy_from(data);
|
||||||
@@ -204,16 +206,16 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn write_u8(
|
pub fn write_u8(&self, offset: u64, val: u8) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
val: u8
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
let view = &self.view;
|
let view = &self.view;
|
||||||
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
let offset: u32 = offset.try_into().map_err(|_| MemoryAccessError::Overflow)?;
|
||||||
if offset >= view.length() {
|
if offset >= view.length() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to write beyond the bounds of the memory view ({} >= {})", offset, view.length());
|
warn!(
|
||||||
|
"attempted to write beyond the bounds of the memory view ({} >= {})",
|
||||||
|
offset,
|
||||||
|
view.length()
|
||||||
|
);
|
||||||
Err(MemoryAccessError::HeapOutOfBounds)?;
|
Err(MemoryAccessError::HeapOutOfBounds)?;
|
||||||
}
|
}
|
||||||
view.set_index(offset, val);
|
view.set_index(offset, val);
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use crate::js::externals::memory::MemoryBuffer;
|
use crate::js::externals::memory::MemoryBuffer;
|
||||||
use crate::js::RuntimeError;
|
use crate::js::RuntimeError;
|
||||||
use crate::js::{MemoryView, Memory32, Memory64, WasmPtr};
|
use crate::js::{Memory32, Memory64, MemoryView, WasmPtr};
|
||||||
use std::{
|
use std::{
|
||||||
convert::TryInto,
|
convert::TryInto,
|
||||||
fmt,
|
fmt,
|
||||||
@@ -158,11 +158,7 @@ impl<'a, T: ValueType> WasmSlice<'a, T> {
|
|||||||
///
|
///
|
||||||
/// Returns a `MemoryAccessError` if the slice length overflows.
|
/// Returns a `MemoryAccessError` if the slice length overflows.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn new(
|
pub fn new(memory: &'a MemoryView, offset: u64, len: u64) -> Result<Self, MemoryAccessError> {
|
||||||
memory: &'a MemoryView,
|
|
||||||
offset: u64,
|
|
||||||
len: u64,
|
|
||||||
) -> Result<Self, MemoryAccessError> {
|
|
||||||
let total_len = len
|
let total_len = len
|
||||||
.checked_mul(mem::size_of::<T>() as u64)
|
.checked_mul(mem::size_of::<T>() as u64)
|
||||||
.ok_or(MemoryAccessError::Overflow)?;
|
.ok_or(MemoryAccessError::Overflow)?;
|
||||||
|
|||||||
@@ -48,8 +48,8 @@ pub use crate::js::error::{DeserializeError, InstantiationError, SerializeError}
|
|||||||
pub use crate::js::export::Export;
|
pub use crate::js::export::Export;
|
||||||
pub use crate::js::exports::{ExportError, Exportable, Exports, ExportsIterator};
|
pub use crate::js::exports::{ExportError, Exportable, Exports, ExportsIterator};
|
||||||
pub use crate::js::externals::{
|
pub use crate::js::externals::{
|
||||||
Extern, FromToNativeWasmType, Function, Global, HostFunction, Memory, MemoryView, MemoryError, Table,
|
Extern, FromToNativeWasmType, Function, Global, HostFunction, Memory, MemoryError, MemoryView,
|
||||||
WasmTypeList,
|
Table, WasmTypeList,
|
||||||
};
|
};
|
||||||
pub use crate::js::function_env::{FunctionEnv, FunctionEnvMut};
|
pub use crate::js::function_env::{FunctionEnv, FunctionEnvMut};
|
||||||
pub use crate::js::imports::Imports;
|
pub use crate::js::imports::Imports;
|
||||||
|
|||||||
@@ -149,11 +149,7 @@ impl<T: ValueType, M: MemorySize> WasmPtr<T, M> {
|
|||||||
|
|
||||||
/// Writes to the address pointed to by this `WasmPtr` in a memory.
|
/// Writes to the address pointed to by this `WasmPtr` in a memory.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn write(
|
pub fn write(self, view: &MemoryView, val: T) -> Result<(), MemoryAccessError> {
|
||||||
self,
|
|
||||||
view: &MemoryView,
|
|
||||||
val: T,
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
self.deref(view).write(val)
|
self.deref(view).write(val)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
21
lib/api/src/sys/externals/memory.rs
vendored
21
lib/api/src/sys/externals/memory.rs
vendored
@@ -179,7 +179,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
.ok_or(MemoryAccessError::Overflow)?;
|
.ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > self.len.try_into().unwrap() {
|
if end > self.len.try_into().unwrap() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", buf.len(), end, self.len);
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
buf.len(),
|
||||||
|
end,
|
||||||
|
self.len
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
unsafe {
|
unsafe {
|
||||||
@@ -198,7 +203,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
.ok_or(MemoryAccessError::Overflow)?;
|
.ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > self.len.try_into().unwrap() {
|
if end > self.len.try_into().unwrap() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})", buf.len(), end, self.len);
|
warn!(
|
||||||
|
"attempted to read ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
buf.len(),
|
||||||
|
end,
|
||||||
|
self.len
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
let buf_ptr = buf.as_mut_ptr() as *mut u8;
|
let buf_ptr = buf.as_mut_ptr() as *mut u8;
|
||||||
@@ -215,7 +225,12 @@ impl<'a> MemoryBuffer<'a> {
|
|||||||
.ok_or(MemoryAccessError::Overflow)?;
|
.ok_or(MemoryAccessError::Overflow)?;
|
||||||
if end > self.len.try_into().unwrap() {
|
if end > self.len.try_into().unwrap() {
|
||||||
#[cfg(feature = "tracing")]
|
#[cfg(feature = "tracing")]
|
||||||
warn!("attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})", data.len(), end, self.len);
|
warn!(
|
||||||
|
"attempted to write ({} bytes) beyond the bounds of the memory view ({} > {})",
|
||||||
|
data.len(),
|
||||||
|
end,
|
||||||
|
self.len
|
||||||
|
);
|
||||||
return Err(MemoryAccessError::HeapOutOfBounds);
|
return Err(MemoryAccessError::HeapOutOfBounds);
|
||||||
}
|
}
|
||||||
unsafe {
|
unsafe {
|
||||||
|
|||||||
28
lib/api/src/sys/externals/memory_view.rs
vendored
28
lib/api/src/sys/externals/memory_view.rs
vendored
@@ -6,8 +6,8 @@ use std::mem::MaybeUninit;
|
|||||||
use std::slice;
|
use std::slice;
|
||||||
use wasmer_types::Pages;
|
use wasmer_types::Pages;
|
||||||
|
|
||||||
use super::Memory;
|
|
||||||
use super::memory::MemoryBuffer;
|
use super::memory::MemoryBuffer;
|
||||||
|
use super::Memory;
|
||||||
|
|
||||||
/// A WebAssembly `memory` view.
|
/// A WebAssembly `memory` view.
|
||||||
///
|
///
|
||||||
@@ -21,8 +21,7 @@ pub struct MemoryView<'a> {
|
|||||||
pub(crate) size: Pages,
|
pub(crate) size: Pages,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> MemoryView<'a>
|
impl<'a> MemoryView<'a> {
|
||||||
{
|
|
||||||
pub(crate) fn new(memory: &Memory, store: &'a impl AsStoreRef) -> Self {
|
pub(crate) fn new(memory: &Memory, store: &'a impl AsStoreRef) -> Self {
|
||||||
let size = memory.handle.get(store.as_store_ref().objects()).size();
|
let size = memory.handle.get(store.as_store_ref().objects()).size();
|
||||||
|
|
||||||
@@ -107,11 +106,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn read(
|
pub fn read(&self, offset: u64, buf: &mut [u8]) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
buf: &mut [u8],
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
self.buffer.read(offset, buf)
|
self.buffer.read(offset, buf)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -119,10 +114,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn read_u8(
|
pub fn read_u8(&self, offset: u64) -> Result<u8, MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64
|
|
||||||
) -> Result<u8, MemoryAccessError> {
|
|
||||||
let mut buf = [0u8; 1];
|
let mut buf = [0u8; 1];
|
||||||
self.read(offset, &mut buf)?;
|
self.read(offset, &mut buf)?;
|
||||||
Ok(buf[0])
|
Ok(buf[0])
|
||||||
@@ -153,11 +145,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent reads/writes.
|
/// concurrent reads/writes.
|
||||||
pub fn write(
|
pub fn write(&self, offset: u64, data: &[u8]) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
data: &[u8],
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
self.buffer.write(offset, data)
|
self.buffer.write(offset, data)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -165,11 +153,7 @@ impl<'a> MemoryView<'a>
|
|||||||
///
|
///
|
||||||
/// This method is guaranteed to be safe (from the host side) in the face of
|
/// This method is guaranteed to be safe (from the host side) in the face of
|
||||||
/// concurrent writes.
|
/// concurrent writes.
|
||||||
pub fn write_u8(
|
pub fn write_u8(&self, offset: u64, val: u8) -> Result<(), MemoryAccessError> {
|
||||||
&self,
|
|
||||||
offset: u64,
|
|
||||||
val: u8
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
let buf = [val];
|
let buf = [val];
|
||||||
self.write(offset, &buf)?;
|
self.write(offset, &buf)?;
|
||||||
Ok(())
|
Ok(())
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use crate::RuntimeError;
|
use crate::RuntimeError;
|
||||||
#[allow(unused_imports)]
|
#[allow(unused_imports)]
|
||||||
use crate::{Memory, MemoryView, Memory32, Memory64, MemorySize, WasmPtr};
|
use crate::{Memory, Memory32, Memory64, MemorySize, MemoryView, WasmPtr};
|
||||||
use std::{
|
use std::{
|
||||||
convert::TryInto,
|
convert::TryInto,
|
||||||
fmt,
|
fmt,
|
||||||
@@ -160,11 +160,7 @@ impl<'a, T: ValueType> WasmSlice<'a, T> {
|
|||||||
///
|
///
|
||||||
/// Returns a `MemoryAccessError` if the slice length overflows.
|
/// Returns a `MemoryAccessError` if the slice length overflows.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn new(
|
pub fn new(view: &'a MemoryView, offset: u64, len: u64) -> Result<Self, MemoryAccessError> {
|
||||||
view: &'a MemoryView,
|
|
||||||
offset: u64,
|
|
||||||
len: u64,
|
|
||||||
) -> Result<Self, MemoryAccessError> {
|
|
||||||
let total_len = len
|
let total_len = len
|
||||||
.checked_mul(mem::size_of::<T>() as u64)
|
.checked_mul(mem::size_of::<T>() as u64)
|
||||||
.ok_or(MemoryAccessError::Overflow)?;
|
.ok_or(MemoryAccessError::Overflow)?;
|
||||||
|
|||||||
@@ -16,7 +16,8 @@ mod value;
|
|||||||
pub use crate::sys::exports::{ExportError, Exportable, Exports, ExportsIterator};
|
pub use crate::sys::exports::{ExportError, Exportable, Exports, ExportsIterator};
|
||||||
pub use crate::sys::extern_ref::ExternRef;
|
pub use crate::sys::extern_ref::ExternRef;
|
||||||
pub use crate::sys::externals::{
|
pub use crate::sys::externals::{
|
||||||
Extern, FromToNativeWasmType, Function, Global, HostFunction, Memory, MemoryView, Table, WasmTypeList,
|
Extern, FromToNativeWasmType, Function, Global, HostFunction, Memory, MemoryView, Table,
|
||||||
|
WasmTypeList,
|
||||||
};
|
};
|
||||||
pub use crate::sys::function_env::{FunctionEnv, FunctionEnvMut};
|
pub use crate::sys::function_env::{FunctionEnv, FunctionEnvMut};
|
||||||
pub use crate::sys::imports::Imports;
|
pub use crate::sys::imports::Imports;
|
||||||
|
|||||||
@@ -154,11 +154,7 @@ impl<T: ValueType, M: MemorySize> WasmPtr<T, M> {
|
|||||||
|
|
||||||
/// Writes to the address pointed to by this `WasmPtr` in a memory.
|
/// Writes to the address pointed to by this `WasmPtr` in a memory.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn write(
|
pub fn write(self, view: &MemoryView, val: T) -> Result<(), MemoryAccessError> {
|
||||||
self,
|
|
||||||
view: &MemoryView,
|
|
||||||
val: T,
|
|
||||||
) -> Result<(), MemoryAccessError> {
|
|
||||||
self.deref(view).write(val)
|
self.deref(view).write(val)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -219,10 +215,7 @@ impl<M: MemorySize> WasmPtr<u8, M> {
|
|||||||
/// This method is safe to call even if the memory is being concurrently
|
/// This method is safe to call even if the memory is being concurrently
|
||||||
/// modified.
|
/// modified.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn read_utf8_string_with_nul(
|
pub fn read_utf8_string_with_nul(self, view: &MemoryView) -> Result<String, MemoryAccessError> {
|
||||||
self,
|
|
||||||
view: &MemoryView,
|
|
||||||
) -> Result<String, MemoryAccessError> {
|
|
||||||
let vec = self.read_until(view, |&byte| byte == 0)?;
|
let vec = self.read_until(view, |&byte| byte == 0)?;
|
||||||
Ok(String::from_utf8(vec)?)
|
Ok(String::from_utf8(vec)?)
|
||||||
}
|
}
|
||||||
|
|||||||
6
lib/emscripten/src/env/mod.rs
vendored
6
lib/emscripten/src/env/mod.rs
vendored
@@ -75,7 +75,8 @@ pub fn ___build_environment(mut ctx: FunctionEnvMut<EmEnv>, environ: c_int) {
|
|||||||
debug!("emscripten::___build_environment {}", environ);
|
debug!("emscripten::___build_environment {}", environ);
|
||||||
const MAX_ENV_VALUES: u32 = 64;
|
const MAX_ENV_VALUES: u32 = 64;
|
||||||
const TOTAL_ENV_SIZE: u32 = 1024;
|
const TOTAL_ENV_SIZE: u32 = 1024;
|
||||||
let environment = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), environ) as *mut c_int;
|
let environment =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), environ) as *mut c_int;
|
||||||
let (mut pool_offset, env_ptr, mut pool_ptr) = unsafe {
|
let (mut pool_offset, env_ptr, mut pool_ptr) = unsafe {
|
||||||
let (pool_offset, _pool_slice): (u32, &mut [u8]) =
|
let (pool_offset, _pool_slice): (u32, &mut [u8]) =
|
||||||
allocate_on_stack(&mut ctx, TOTAL_ENV_SIZE as u32);
|
allocate_on_stack(&mut ctx, TOTAL_ENV_SIZE as u32);
|
||||||
@@ -136,7 +137,8 @@ pub fn _pathconf(ctx: FunctionEnvMut<EmEnv>, path_addr: c_int, name: c_int) -> c
|
|||||||
"emscripten::_pathconf {} {} - UNIMPLEMENTED",
|
"emscripten::_pathconf {} {} - UNIMPLEMENTED",
|
||||||
path_addr, name
|
path_addr, name
|
||||||
);
|
);
|
||||||
let _path = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), path_addr) as *const c_char;
|
let _path =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), path_addr) as *const c_char;
|
||||||
match name {
|
match name {
|
||||||
0 => 32000,
|
0 => 32000,
|
||||||
1 | 2 | 3 => 255,
|
1 | 2 | 3 => 255,
|
||||||
|
|||||||
24
lib/emscripten/src/env/unix/mod.rs
vendored
24
lib/emscripten/src/env/unix/mod.rs
vendored
@@ -17,7 +17,8 @@ use wasmer::{FunctionEnvMut, WasmPtr};
|
|||||||
pub fn _getenv(mut ctx: FunctionEnvMut<EmEnv>, name: i32) -> u32 {
|
pub fn _getenv(mut ctx: FunctionEnvMut<EmEnv>, name: i32) -> u32 {
|
||||||
debug!("emscripten::_getenv");
|
debug!("emscripten::_getenv");
|
||||||
|
|
||||||
let name_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
let name_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
||||||
|
|
||||||
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
||||||
|
|
||||||
@@ -33,8 +34,10 @@ pub fn _getenv(mut ctx: FunctionEnvMut<EmEnv>, name: i32) -> u32 {
|
|||||||
pub fn _setenv(ctx: FunctionEnvMut<EmEnv>, name: c_int, value: c_int, overwrite: c_int) -> c_int {
|
pub fn _setenv(ctx: FunctionEnvMut<EmEnv>, name: c_int, value: c_int, overwrite: c_int) -> c_int {
|
||||||
debug!("emscripten::_setenv");
|
debug!("emscripten::_setenv");
|
||||||
|
|
||||||
let name_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
let name_addr =
|
||||||
let value_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), value) as *const c_char;
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
||||||
|
let value_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), value) as *const c_char;
|
||||||
|
|
||||||
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
||||||
debug!("=> value({:?})", unsafe { CStr::from_ptr(value_addr) });
|
debug!("=> value({:?})", unsafe { CStr::from_ptr(value_addr) });
|
||||||
@@ -46,7 +49,8 @@ pub fn _setenv(ctx: FunctionEnvMut<EmEnv>, name: c_int, value: c_int, overwrite:
|
|||||||
pub fn _putenv(ctx: FunctionEnvMut<EmEnv>, name: c_int) -> c_int {
|
pub fn _putenv(ctx: FunctionEnvMut<EmEnv>, name: c_int) -> c_int {
|
||||||
debug!("emscripten::_putenv");
|
debug!("emscripten::_putenv");
|
||||||
|
|
||||||
let name_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
let name_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
||||||
|
|
||||||
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
||||||
|
|
||||||
@@ -57,7 +61,8 @@ pub fn _putenv(ctx: FunctionEnvMut<EmEnv>, name: c_int) -> c_int {
|
|||||||
pub fn _unsetenv(ctx: FunctionEnvMut<EmEnv>, name: c_int) -> c_int {
|
pub fn _unsetenv(ctx: FunctionEnvMut<EmEnv>, name: c_int) -> c_int {
|
||||||
debug!("emscripten::_unsetenv");
|
debug!("emscripten::_unsetenv");
|
||||||
|
|
||||||
let name_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
let name_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), name) as *const c_char;
|
||||||
|
|
||||||
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
debug!("=> name({:?})", unsafe { CStr::from_ptr(name_addr) });
|
||||||
|
|
||||||
@@ -155,9 +160,7 @@ pub fn _gai_strerror(mut ctx: FunctionEnvMut<EmEnv>, ecode: i32) -> i32 {
|
|||||||
let string_on_guest: WasmPtr<c_char> = call_malloc_with_cast(&mut ctx, bytes.len() as _);
|
let string_on_guest: WasmPtr<c_char> = call_malloc_with_cast(&mut ctx, bytes.len() as _);
|
||||||
let memory = ctx.data().memory_view(0, &ctx);
|
let memory = ctx.data().memory_view(0, &ctx);
|
||||||
|
|
||||||
let writer = string_on_guest
|
let writer = string_on_guest.slice(&memory, bytes.len() as _).unwrap();
|
||||||
.slice(&memory, bytes.len() as _)
|
|
||||||
.unwrap();
|
|
||||||
for (i, byte) in bytes.iter().enumerate() {
|
for (i, byte) in bytes.iter().enumerate() {
|
||||||
writer.index(i as u64).write(*byte as _).unwrap();
|
writer.index(i as u64).write(*byte as _).unwrap();
|
||||||
}
|
}
|
||||||
@@ -192,7 +195,10 @@ pub fn _getaddrinfo(
|
|||||||
let hints = if hints_ptr.is_null() {
|
let hints = if hints_ptr.is_null() {
|
||||||
None
|
None
|
||||||
} else {
|
} else {
|
||||||
let hints_guest = hints_ptr.deref(&ctx.data().memory_view(0, &ctx)).read().unwrap();
|
let hints_guest = hints_ptr
|
||||||
|
.deref(&ctx.data().memory_view(0, &ctx))
|
||||||
|
.read()
|
||||||
|
.unwrap();
|
||||||
Some(addrinfo {
|
Some(addrinfo {
|
||||||
ai_flags: hints_guest.ai_flags,
|
ai_flags: hints_guest.ai_flags,
|
||||||
ai_family: hints_guest.ai_family,
|
ai_family: hints_guest.ai_family,
|
||||||
|
|||||||
@@ -11,7 +11,8 @@ pub fn _emscripten_memcpy_big(ctx: FunctionEnvMut<EmEnv>, dest: u32, src: u32, l
|
|||||||
"emscripten::_emscripten_memcpy_big {}, {}, {}",
|
"emscripten::_emscripten_memcpy_big {}, {}, {}",
|
||||||
dest, src, len
|
dest, src, len
|
||||||
);
|
);
|
||||||
let dest_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), dest) as *mut c_void;
|
let dest_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), dest) as *mut c_void;
|
||||||
let src_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), src) as *mut c_void;
|
let src_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), src) as *mut c_void;
|
||||||
unsafe {
|
unsafe {
|
||||||
memcpy(dest_addr, src_addr, len as size_t);
|
memcpy(dest_addr, src_addr, len as size_t);
|
||||||
|
|||||||
@@ -80,7 +80,8 @@ pub fn ___syscall4(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: VarAr
|
|||||||
let buf: i32 = varargs.get(&ctx);
|
let buf: i32 = varargs.get(&ctx);
|
||||||
let count: i32 = varargs.get(&ctx);
|
let count: i32 = varargs.get(&ctx);
|
||||||
debug!("=> fd: {}, buf: {}, count: {}", fd, buf, count);
|
debug!("=> fd: {}, buf: {}, count: {}", fd, buf, count);
|
||||||
let buf_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), buf) as *const c_void;
|
let buf_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), buf) as *const c_void;
|
||||||
unsafe { write(fd, buf_addr, count as _) as i32 }
|
unsafe { write(fd, buf_addr, count as _) as i32 }
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -384,7 +385,8 @@ pub fn ___syscall192(mut ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs:
|
|||||||
// ENOMEM
|
// ENOMEM
|
||||||
return -12;
|
return -12;
|
||||||
}
|
}
|
||||||
let real_ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), ptr) as *const u8;
|
let real_ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), ptr) as *const u8;
|
||||||
env::call_memset(&mut ctx, ptr, 0, len);
|
env::call_memset(&mut ctx, ptr, 0, len);
|
||||||
for i in 0..(len as usize) {
|
for i in 0..(len as usize) {
|
||||||
unsafe {
|
unsafe {
|
||||||
@@ -450,9 +452,10 @@ pub fn ___syscall145(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: Var
|
|||||||
let guest_iov_addr =
|
let guest_iov_addr =
|
||||||
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (iov + i * 8))
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (iov + i * 8))
|
||||||
as *mut GuestIovec;
|
as *mut GuestIovec;
|
||||||
let iov_base =
|
let iov_base = emscripten_memory_pointer!(
|
||||||
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (*guest_iov_addr).iov_base)
|
ctx.data().memory_view(0, &ctx),
|
||||||
as *mut c_void;
|
(*guest_iov_addr).iov_base
|
||||||
|
) as *mut c_void;
|
||||||
let iov_len = (*guest_iov_addr).iov_len as _;
|
let iov_len = (*guest_iov_addr).iov_len as _;
|
||||||
// debug!("=> iov_addr: {:?}, {:?}", iov_base, iov_len);
|
// debug!("=> iov_addr: {:?}, {:?}", iov_base, iov_len);
|
||||||
let curr = read(fd, iov_base, iov_len);
|
let curr = read(fd, iov_base, iov_len);
|
||||||
@@ -488,9 +491,10 @@ pub fn ___syscall146(ctx: FunctionEnvMut<EmEnv>, _which: i32, mut varargs: VarAr
|
|||||||
let guest_iov_addr =
|
let guest_iov_addr =
|
||||||
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (iov + i * 8))
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (iov + i * 8))
|
||||||
as *mut GuestIovec;
|
as *mut GuestIovec;
|
||||||
let iov_base =
|
let iov_base = emscripten_memory_pointer!(
|
||||||
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), (*guest_iov_addr).iov_base)
|
ctx.data().memory_view(0, &ctx),
|
||||||
as *const c_void;
|
(*guest_iov_addr).iov_base
|
||||||
|
) as *const c_void;
|
||||||
let iov_len = (*guest_iov_addr).iov_len as _;
|
let iov_len = (*guest_iov_addr).iov_len as _;
|
||||||
// debug!("=> iov_addr: {:?}, {:?}", iov_base, iov_len);
|
// debug!("=> iov_addr: {:?}, {:?}", iov_base, iov_len);
|
||||||
let curr = write(fd, iov_base, iov_len);
|
let curr = write(fd, iov_base, iov_len);
|
||||||
@@ -518,7 +522,8 @@ pub fn ___syscall191(ctx: FunctionEnvMut<EmEnv>, _which: i32, mut varargs: VarAr
|
|||||||
_resource
|
_resource
|
||||||
);
|
);
|
||||||
let rlim_emptr: i32 = varargs.get(&ctx);
|
let rlim_emptr: i32 = varargs.get(&ctx);
|
||||||
let rlim_ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rlim_emptr) as *mut u8;
|
let rlim_ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rlim_emptr) as *mut u8;
|
||||||
let rlim = unsafe { slice::from_raw_parts_mut(rlim_ptr, 16) };
|
let rlim = unsafe { slice::from_raw_parts_mut(rlim_ptr, 16) };
|
||||||
|
|
||||||
// set all to RLIM_INIFINTY
|
// set all to RLIM_INIFINTY
|
||||||
@@ -722,7 +727,8 @@ pub fn ___syscall340(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: Var
|
|||||||
|
|
||||||
if old_limit != 0 {
|
if old_limit != 0 {
|
||||||
// just report no limits
|
// just report no limits
|
||||||
let buf_ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), old_limit) as *mut u8;
|
let buf_ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), old_limit) as *mut u8;
|
||||||
let buf = unsafe { slice::from_raw_parts_mut(buf_ptr, 16) };
|
let buf = unsafe { slice::from_raw_parts_mut(buf_ptr, 16) };
|
||||||
|
|
||||||
LittleEndian::write_i64(&mut *buf, val);
|
LittleEndian::write_i64(&mut *buf, val);
|
||||||
|
|||||||
@@ -203,7 +203,8 @@ pub fn ___syscall77(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: VarA
|
|||||||
let resource: c_int = varargs.get(&ctx);
|
let resource: c_int = varargs.get(&ctx);
|
||||||
let rusage_ptr: c_int = varargs.get(&ctx);
|
let rusage_ptr: c_int = varargs.get(&ctx);
|
||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
let rusage = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rusage_ptr) as *mut rusage;
|
let rusage =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rusage_ptr) as *mut rusage;
|
||||||
assert_eq!(8, mem::align_of_val(&rusage));
|
assert_eq!(8, mem::align_of_val(&rusage));
|
||||||
unsafe { getrusage(resource, rusage) }
|
unsafe { getrusage(resource, rusage) }
|
||||||
}
|
}
|
||||||
@@ -779,8 +780,7 @@ pub fn ___syscall102(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: Var
|
|||||||
let value: u32 = socket_varargs.get(&ctx);
|
let value: u32 = socket_varargs.get(&ctx);
|
||||||
let option_len: u32 = socket_varargs.get(&ctx);
|
let option_len: u32 = socket_varargs.get(&ctx);
|
||||||
let value_addr = emscripten_memory_pointer!(memory, value) as _;
|
let value_addr = emscripten_memory_pointer!(memory, value) as _;
|
||||||
let option_len_addr =
|
let option_len_addr = emscripten_memory_pointer!(memory, option_len) as *mut socklen_t;
|
||||||
emscripten_memory_pointer!(memory, option_len) as *mut socklen_t;
|
|
||||||
unsafe { getsockopt(socket, level, name, value_addr, option_len_addr) }
|
unsafe { getsockopt(socket, level, name, value_addr, option_len_addr) }
|
||||||
}
|
}
|
||||||
16 => {
|
16 => {
|
||||||
@@ -927,9 +927,11 @@ pub fn ___syscall114(ctx: FunctionEnvMut<EmEnv>, _which: c_int, mut varargs: Var
|
|||||||
let status: u32 = varargs.get(&ctx);
|
let status: u32 = varargs.get(&ctx);
|
||||||
let options: c_int = varargs.get(&ctx);
|
let options: c_int = varargs.get(&ctx);
|
||||||
let rusage: u32 = varargs.get(&ctx);
|
let rusage: u32 = varargs.get(&ctx);
|
||||||
let status_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), status) as *mut c_int;
|
let status_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), status) as *mut c_int;
|
||||||
|
|
||||||
let rusage_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rusage) as *mut rusage;
|
let rusage_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), rusage) as *mut rusage;
|
||||||
let res = unsafe { wait4(pid, status_addr, options, rusage_addr) };
|
let res = unsafe { wait4(pid, status_addr, options, rusage_addr) };
|
||||||
debug!(
|
debug!(
|
||||||
"=> pid: {}, status: {:?}, options: {}, rusage: {:?} = pid: {}",
|
"=> pid: {}, status: {:?}, options: {}, rusage: {:?} = pid: {}",
|
||||||
|
|||||||
@@ -178,7 +178,8 @@ pub fn _tvset(mut _ctx: FunctionEnvMut<EmEnv>) {
|
|||||||
/// formats time as a C string
|
/// formats time as a C string
|
||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
unsafe fn fmt_time(ctx: FunctionEnvMut<EmEnv>, time: u32) -> *const c_char {
|
unsafe fn fmt_time(ctx: FunctionEnvMut<EmEnv>, time: u32) -> *const c_char {
|
||||||
let date = &*(emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time) as *mut guest_tm);
|
let date =
|
||||||
|
&*(emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time) as *mut guest_tm);
|
||||||
|
|
||||||
let days = vec!["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
let days = vec!["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
|
||||||
let months = vec![
|
let months = vec![
|
||||||
@@ -241,14 +242,16 @@ pub fn _localtime(mut ctx: FunctionEnvMut<EmEnv>, time_p: u32) -> c_int {
|
|||||||
// https://stackoverflow.com/questions/19170721/real-time-awareness-of-timezone-change-in-localtime-vs-localtime-r
|
// https://stackoverflow.com/questions/19170721/real-time-awareness-of-timezone-change-in-localtime-vs-localtime-r
|
||||||
|
|
||||||
let timespec = unsafe {
|
let timespec = unsafe {
|
||||||
let time_p_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *mut i64;
|
let time_p_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *mut i64;
|
||||||
let seconds = *time_p_addr;
|
let seconds = *time_p_addr;
|
||||||
time::OffsetDateTime::from_unix_timestamp(seconds)
|
time::OffsetDateTime::from_unix_timestamp(seconds)
|
||||||
};
|
};
|
||||||
|
|
||||||
unsafe {
|
unsafe {
|
||||||
let tm_struct_offset = env::call_malloc(&mut ctx, mem::size_of::<guest_tm>() as _);
|
let tm_struct_offset = env::call_malloc(&mut ctx, mem::size_of::<guest_tm>() as _);
|
||||||
let tm_struct_ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), tm_struct_offset)
|
let tm_struct_ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), tm_struct_offset)
|
||||||
as *mut guest_tm;
|
as *mut guest_tm;
|
||||||
// debug!(
|
// debug!(
|
||||||
// ">>>>>>> time = {}, {}, {}, {}, {}, {}, {}, {}",
|
// ">>>>>>> time = {}, {}, {}, {}, {}, {}, {}, {}",
|
||||||
@@ -279,7 +282,8 @@ pub fn _localtime_r(ctx: FunctionEnvMut<EmEnv>, time_p: u32, result: u32) -> c_i
|
|||||||
// https://stackoverflow.com/questions/19170721/real-time-awareness-of-timezone-change-in-localtime-vs-localtime-r
|
// https://stackoverflow.com/questions/19170721/real-time-awareness-of-timezone-change-in-localtime-vs-localtime-r
|
||||||
|
|
||||||
unsafe {
|
unsafe {
|
||||||
let seconds = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *const i32;
|
let seconds =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *const i32;
|
||||||
let timespec = time::OffsetDateTime::from_unix_timestamp_nanos(*seconds as _);
|
let timespec = time::OffsetDateTime::from_unix_timestamp_nanos(*seconds as _);
|
||||||
|
|
||||||
// debug!(
|
// debug!(
|
||||||
@@ -313,7 +317,8 @@ pub fn _time(ctx: FunctionEnvMut<EmEnv>, time_p: u32) -> i32 {
|
|||||||
debug!("emscripten::_time {}", time_p);
|
debug!("emscripten::_time {}", time_p);
|
||||||
|
|
||||||
unsafe {
|
unsafe {
|
||||||
let time_p_addr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *mut i64;
|
let time_p_addr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), time_p) as *mut i64;
|
||||||
libc_time(time_p_addr) as i32 // TODO review i64
|
libc_time(time_p_addr) as i32 // TODO review i64
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -403,7 +408,8 @@ pub fn _strftime(
|
|||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
let s = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), s_ptr) as *mut c_char;
|
let s = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), s_ptr) as *mut c_char;
|
||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
let format = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), format_ptr) as *const c_char;
|
let format =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), format_ptr) as *const c_char;
|
||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
let tm = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), tm_ptr) as *const guest_tm;
|
let tm = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), tm_ptr) as *const guest_tm;
|
||||||
|
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ use std::mem::size_of;
|
|||||||
use std::os::raw::c_char;
|
use std::os::raw::c_char;
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
use std::slice;
|
use std::slice;
|
||||||
use wasmer::{FunctionEnvMut, GlobalInit, Module, Pages, WasmPtr, MemoryView};
|
use wasmer::{FunctionEnvMut, GlobalInit, MemoryView, Module, Pages, WasmPtr};
|
||||||
|
|
||||||
/// We check if a provided module is an Emscripten generated one
|
/// We check if a provided module is an Emscripten generated one
|
||||||
pub fn is_emscripten_module(module: &Module) -> bool {
|
pub fn is_emscripten_module(module: &Module) -> bool {
|
||||||
@@ -204,7 +204,8 @@ pub struct GuestStat {
|
|||||||
|
|
||||||
#[allow(clippy::cast_ptr_alignment)]
|
#[allow(clippy::cast_ptr_alignment)]
|
||||||
pub unsafe fn copy_stat_into_wasm(ctx: FunctionEnvMut<EmEnv>, buf: u32, stat: &stat) {
|
pub unsafe fn copy_stat_into_wasm(ctx: FunctionEnvMut<EmEnv>, buf: u32, stat: &stat) {
|
||||||
let stat_ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), buf) as *mut GuestStat;
|
let stat_ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), buf) as *mut GuestStat;
|
||||||
(*stat_ptr).st_dev = stat.st_dev as _;
|
(*stat_ptr).st_dev = stat.st_dev as _;
|
||||||
(*stat_ptr).__st_dev_padding = 0;
|
(*stat_ptr).__st_dev_padding = 0;
|
||||||
(*stat_ptr).__st_ino_truncated = stat.st_ino as _;
|
(*stat_ptr).__st_ino_truncated = stat.st_ino as _;
|
||||||
|
|||||||
@@ -21,7 +21,8 @@ impl VarArgs {
|
|||||||
// pub fn getStr<'a>(&mut self, ctx: &mut Ctx) -> &'a CStr {
|
// pub fn getStr<'a>(&mut self, ctx: &mut Ctx) -> &'a CStr {
|
||||||
pub fn get_str(&mut self, ctx: &FunctionEnvMut<EmEnv>) -> *const c_char {
|
pub fn get_str(&mut self, ctx: &FunctionEnvMut<EmEnv>) -> *const c_char {
|
||||||
let ptr_addr: u32 = self.get(ctx);
|
let ptr_addr: u32 = self.get(ctx);
|
||||||
let ptr = emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), ptr_addr) as *const c_char;
|
let ptr =
|
||||||
|
emscripten_memory_pointer!(ctx.data().memory_view(0, &ctx), ptr_addr) as *const c_char;
|
||||||
ptr
|
ptr
|
||||||
// unsafe { CStr::from_ptr(ptr) }
|
// unsafe { CStr::from_ptr(ptr) }
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -63,8 +63,8 @@ use derivative::*;
|
|||||||
use std::ops::Deref;
|
use std::ops::Deref;
|
||||||
use thiserror::Error;
|
use thiserror::Error;
|
||||||
use wasmer::{
|
use wasmer::{
|
||||||
imports, namespace, AsStoreMut, Exports, Function, FunctionEnv, Imports, Memory, Memory32,
|
imports, namespace, AsStoreMut, AsStoreRef, Exports, Function, FunctionEnv, Imports, Memory,
|
||||||
MemoryAccessError, MemorySize, Module, TypedFunction, MemoryView, AsStoreRef
|
Memory32, MemoryAccessError, MemorySize, MemoryView, Module, TypedFunction,
|
||||||
};
|
};
|
||||||
|
|
||||||
pub use runtime::{
|
pub use runtime::{
|
||||||
@@ -349,7 +349,11 @@ impl WasiEnv {
|
|||||||
&self.state
|
&self.state
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn get_memory_and_wasi_state<'a>(&'a self, store: &'a impl AsStoreRef, _mem_index: u32) -> (MemoryView<'a>, &WasiState) {
|
pub(crate) fn get_memory_and_wasi_state<'a>(
|
||||||
|
&'a self,
|
||||||
|
store: &'a impl AsStoreRef,
|
||||||
|
_mem_index: u32,
|
||||||
|
) -> (MemoryView<'a>, &WasiState) {
|
||||||
let memory = self.memory_view(store);
|
let memory = self.memory_view(store);
|
||||||
let state = self.state.deref();
|
let state = self.state.deref();
|
||||||
(memory, state)
|
(memory, state)
|
||||||
|
|||||||
@@ -6,8 +6,8 @@ use std::io::{self, Read};
|
|||||||
use std::ops::DerefMut;
|
use std::ops::DerefMut;
|
||||||
use std::sync::mpsc;
|
use std::sync::mpsc;
|
||||||
use std::sync::Mutex;
|
use std::sync::Mutex;
|
||||||
use wasmer::{MemorySize, MemoryView};
|
|
||||||
use wasmer::WasmSlice;
|
use wasmer::WasmSlice;
|
||||||
|
use wasmer::{MemorySize, MemoryView};
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct WasiPipe {
|
pub struct WasiPipe {
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ use std::sync::Mutex;
|
|||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
#[allow(unused_imports)]
|
#[allow(unused_imports)]
|
||||||
use tracing::{debug, error, info, warn};
|
use tracing::{debug, error, info, warn};
|
||||||
use wasmer::{MemorySize, WasmPtr, WasmSlice, MemoryView};
|
use wasmer::{MemorySize, MemoryView, WasmPtr, WasmSlice};
|
||||||
use wasmer_vnet::{net_error_into_io_err, TimeType};
|
use wasmer_vnet::{net_error_into_io_err, TimeType};
|
||||||
use wasmer_vnet::{
|
use wasmer_vnet::{
|
||||||
IpCidr, IpRoute, SocketHttpRequest, VirtualIcmpSocket, VirtualNetworking, VirtualRawSocket,
|
IpCidr, IpRoute, SocketHttpRequest, VirtualIcmpSocket, VirtualNetworking, VirtualRawSocket,
|
||||||
|
|||||||
@@ -47,8 +47,8 @@ use std::sync::{mpsc, Arc};
|
|||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
use tracing::{debug, error, trace, warn};
|
use tracing::{debug, error, trace, warn};
|
||||||
use wasmer::{
|
use wasmer::{
|
||||||
AsStoreMut, FunctionEnvMut, Memory, Memory32, Memory64, MemorySize, RuntimeError, Value,
|
AsStoreMut, Extern, FunctionEnv, FunctionEnvMut, Instance, Memory, Memory32, Memory64,
|
||||||
WasmPtr, WasmSlice, FunctionEnv, Instance, Module, Extern, MemoryView,
|
MemorySize, MemoryView, Module, RuntimeError, Value, WasmPtr, WasmSlice,
|
||||||
};
|
};
|
||||||
use wasmer_vbus::{FileDescriptor, StdioMode};
|
use wasmer_vbus::{FileDescriptor, StdioMode};
|
||||||
use wasmer_vfs::{FsError, VirtualFile};
|
use wasmer_vfs::{FsError, VirtualFile};
|
||||||
@@ -891,10 +891,7 @@ pub fn fd_pread<M: MemorySize>(
|
|||||||
Kind::Dir { .. } | Kind::Root { .. } => return Ok(__WASI_EISDIR),
|
Kind::Dir { .. } | Kind::Root { .. } => return Ok(__WASI_EISDIR),
|
||||||
Kind::Symlink { .. } => unimplemented!("Symlinks in wasi::fd_pread"),
|
Kind::Symlink { .. } => unimplemented!("Symlinks in wasi::fd_pread"),
|
||||||
Kind::Buffer { buffer } => {
|
Kind::Buffer { buffer } => {
|
||||||
wasi_try_ok!(
|
wasi_try_ok!(read_bytes(&buffer[(offset as usize)..], &memory, iovs), env)
|
||||||
read_bytes(&buffer[(offset as usize)..], &memory, iovs),
|
|
||||||
env
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -924,13 +921,14 @@ pub fn fd_prestat_get<M: MemorySize>(
|
|||||||
let (memory, mut state, inodes) = env.get_memory_and_wasi_state_and_inodes(&ctx, 0);
|
let (memory, mut state, inodes) = env.get_memory_and_wasi_state_and_inodes(&ctx, 0);
|
||||||
|
|
||||||
let prestat_ptr = buf.deref(&memory);
|
let prestat_ptr = buf.deref(&memory);
|
||||||
wasi_try_mem!(prestat_ptr.write(wasi_try!(
|
wasi_try_mem!(
|
||||||
state.fs.prestat_fd(inodes.deref(), fd)
|
prestat_ptr.write(wasi_try!(state.fs.prestat_fd(inodes.deref(), fd).map_err(
|
||||||
.map_err(|code| {
|
|code| {
|
||||||
debug!("fd_prestat_get failed (fd={}) - errno={}", fd, code);
|
debug!("fd_prestat_get failed (fd={}) - errno={}", fd, code);
|
||||||
code
|
code
|
||||||
})
|
}
|
||||||
)));
|
)))
|
||||||
|
);
|
||||||
|
|
||||||
__WASI_ESUCCESS
|
__WASI_ESUCCESS
|
||||||
}
|
}
|
||||||
@@ -1733,8 +1731,7 @@ pub fn fd_write<M: MemorySize>(
|
|||||||
counter, wakers, ..
|
counter, wakers, ..
|
||||||
} => {
|
} => {
|
||||||
let mut val = 0u64.to_ne_bytes();
|
let mut val = 0u64.to_ne_bytes();
|
||||||
let written =
|
let written = wasi_try_ok!(write_bytes(&mut val[..], &memory, iovs_arr));
|
||||||
wasi_try_ok!(write_bytes(&mut val[..], &memory, iovs_arr));
|
|
||||||
if written != val.len() {
|
if written != val.len() {
|
||||||
return Ok(__WASI_EINVAL);
|
return Ok(__WASI_EINVAL);
|
||||||
}
|
}
|
||||||
@@ -1754,10 +1751,7 @@ pub fn fd_write<M: MemorySize>(
|
|||||||
}
|
}
|
||||||
Kind::Symlink { .. } => unimplemented!("Symlinks in wasi::fd_write"),
|
Kind::Symlink { .. } => unimplemented!("Symlinks in wasi::fd_write"),
|
||||||
Kind::Buffer { buffer } => {
|
Kind::Buffer { buffer } => {
|
||||||
wasi_try_ok!(
|
wasi_try_ok!(write_bytes(&mut buffer[offset..], &memory, iovs_arr), env)
|
||||||
write_bytes(&mut buffer[offset..], &memory, iovs_arr),
|
|
||||||
env
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -2503,8 +2497,7 @@ pub fn path_readlink<M: MemorySize>(
|
|||||||
}
|
}
|
||||||
let bytes: Vec<_> = bytes.collect();
|
let bytes: Vec<_> = bytes.collect();
|
||||||
|
|
||||||
let out =
|
let out = wasi_try_mem!(buf.slice(&memory, wasi_try!(to_offset::<M>(bytes.len()))));
|
||||||
wasi_try_mem!(buf.slice(&memory, wasi_try!(to_offset::<M>(bytes.len()))));
|
|
||||||
wasi_try_mem!(out.write_slice(&bytes));
|
wasi_try_mem!(out.write_slice(&bytes));
|
||||||
// should we null terminate this?
|
// should we null terminate this?
|
||||||
|
|
||||||
@@ -4533,8 +4526,7 @@ pub fn port_route_list<M: MemorySize>(
|
|||||||
let max_routes: usize = wasi_try!(wasi_try_mem!(nroutes.read())
|
let max_routes: usize = wasi_try!(wasi_try_mem!(nroutes.read())
|
||||||
.try_into()
|
.try_into()
|
||||||
.map_err(|_| __WASI_EINVAL));
|
.map_err(|_| __WASI_EINVAL));
|
||||||
let ref_routes =
|
let ref_routes = wasi_try_mem!(routes.slice(&memory, wasi_try!(to_offset::<M>(max_routes))));
|
||||||
wasi_try_mem!(routes.slice(&memory, wasi_try!(to_offset::<M>(max_routes))));
|
|
||||||
|
|
||||||
let routes = wasi_try!(env.net().route_list().map_err(net_error_into_wasi_err));
|
let routes = wasi_try!(env.net().route_list().map_err(net_error_into_wasi_err));
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user