use crate::global::Global;
use crate::instance::WeakOrStrongInstanceRef;
use crate::memory::{Memory, MemoryStyle};
use crate::table::{Table, TableStyle};
use crate::vmcontext::{VMFunctionBody, VMFunctionEnvironment, VMFunctionKind, VMTrampoline};
use crate::VMSharedSignatureIndex;
use std::sync::Arc;
use unc_vm_types::{MemoryType, TableType};
#[derive(Debug)]
pub enum VMExtern {
Function(VMFunction),
Table(VMTable),
Memory(VMMemory),
Global(VMGlobal),
}
#[derive(Clone, Debug, PartialEq)]
pub struct VMFunction {
pub address: *const VMFunctionBody,
pub vmctx: VMFunctionEnvironment,
pub signature: VMSharedSignatureIndex,
pub kind: VMFunctionKind,
pub call_trampoline: Option<VMTrampoline>,
pub instance_ref: Option<WeakOrStrongInstanceRef>,
}
impl VMFunction {
pub fn upgrade_instance_ref(&mut self) -> Option<()> {
if let Some(ref mut ir) = self.instance_ref {
*ir = ir.upgrade()?;
}
Some(())
}
}
unsafe impl Send for VMFunction {}
unsafe impl Sync for VMFunction {}
impl From<VMFunction> for VMExtern {
fn from(func: VMFunction) -> Self {
Self::Function(func)
}
}
#[derive(Clone, Debug)]
pub struct VMTable {
pub from: Arc<dyn Table>,
pub instance_ref: Option<WeakOrStrongInstanceRef>,
}
unsafe impl Send for VMTable {}
unsafe impl Sync for VMTable {}
impl VMTable {
pub fn ty(&self) -> &TableType {
self.from.ty()
}
pub fn style(&self) -> &TableStyle {
self.from.style()
}
pub fn same(&self, other: &Self) -> bool {
Arc::ptr_eq(&self.from, &other.from)
}
pub fn upgrade_instance_ref(&mut self) -> Option<()> {
if let Some(ref mut ir) = self.instance_ref {
*ir = ir.upgrade()?;
}
Some(())
}
}
impl From<VMTable> for VMExtern {
fn from(table: VMTable) -> Self {
Self::Table(table)
}
}
#[derive(Debug, Clone)]
pub struct VMMemory {
pub from: Arc<dyn Memory>,
pub instance_ref: Option<WeakOrStrongInstanceRef>,
}
unsafe impl Send for VMMemory {}
unsafe impl Sync for VMMemory {}
impl VMMemory {
pub fn ty(&self) -> MemoryType {
self.from.ty()
}
pub fn style(&self) -> &MemoryStyle {
self.from.style()
}
pub fn same(&self, other: &Self) -> bool {
Arc::ptr_eq(&self.from, &other.from)
}
pub fn upgrade_instance_ref(&mut self) -> Option<()> {
if let Some(ref mut ir) = self.instance_ref {
*ir = ir.upgrade()?;
}
Some(())
}
}
impl From<VMMemory> for VMExtern {
fn from(memory: VMMemory) -> Self {
Self::Memory(memory)
}
}
#[derive(Debug, Clone)]
pub struct VMGlobal {
pub from: Arc<Global>,
pub instance_ref: Option<WeakOrStrongInstanceRef>,
}
unsafe impl Send for VMGlobal {}
unsafe impl Sync for VMGlobal {}
impl VMGlobal {
pub fn same(&self, other: &Self) -> bool {
Arc::ptr_eq(&self.from, &other.from)
}
pub fn upgrade_instance_ref(&mut self) -> Option<()> {
if let Some(ref mut ir) = self.instance_ref {
*ir = ir.upgrade()?;
}
Some(())
}
}
impl From<VMGlobal> for VMExtern {
fn from(global: VMGlobal) -> Self {
Self::Global(global)
}
}