use alloc::{sync::Arc, vec::Vec};
use core::future::Future;
use miden_core::{
AdviceMap, DebugOptions, EventId, EventName, Felt, Word, crypto::merkle::InnerNodeInfo,
mast::MastForest, precompile::PrecompileRequest,
};
use miden_debug_types::{Location, SourceFile, SourceSpan};
use crate::{EventError, ExecutionError, ProcessState};
pub(super) mod advice;
pub mod debug;
pub mod default;
pub mod handlers;
use handlers::DebugHandler;
mod mast_forest_store;
pub use mast_forest_store::{MastForestStore, MemMastForestStore};
#[derive(Debug, PartialEq, Eq)]
pub enum AdviceMutation {
ExtendStack { values: Vec<Felt> },
ExtendMap { other: AdviceMap },
ExtendMerkleStore { infos: Vec<InnerNodeInfo> },
ExtendPrecompileRequests { data: Vec<PrecompileRequest> },
}
impl AdviceMutation {
pub fn extend_stack(iter: impl IntoIterator<Item = Felt>) -> Self {
Self::ExtendStack { values: Vec::from_iter(iter) }
}
pub fn extend_map(other: AdviceMap) -> Self {
Self::ExtendMap { other }
}
pub fn extend_merkle_store(infos: impl IntoIterator<Item = InnerNodeInfo>) -> Self {
Self::ExtendMerkleStore { infos: Vec::from_iter(infos) }
}
pub fn extend_precompile_requests(data: impl IntoIterator<Item = PrecompileRequest>) -> Self {
Self::ExtendPrecompileRequests { data: Vec::from_iter(data) }
}
}
pub trait BaseHost {
fn get_label_and_source_file(
&self,
location: &Location,
) -> (SourceSpan, Option<Arc<SourceFile>>);
fn on_debug(
&mut self,
process: &mut ProcessState,
options: &DebugOptions,
) -> Result<(), ExecutionError> {
let mut handler = debug::DefaultDebugHandler::default();
handler.on_debug(process, options)
}
fn on_trace(
&mut self,
process: &mut ProcessState,
trace_id: u32,
) -> Result<(), ExecutionError> {
let mut handler = debug::DefaultDebugHandler::default();
handler.on_trace(process, trace_id)
}
fn on_assert_failed(&mut self, _process: &ProcessState, _err_code: Felt) {}
fn resolve_event(&self, _event_id: EventId) -> Option<&EventName> {
None
}
}
pub trait SyncHost: BaseHost {
fn get_mast_forest(&self, node_digest: &Word) -> Option<Arc<MastForest>>;
fn on_event(&mut self, process: &ProcessState) -> Result<Vec<AdviceMutation>, EventError>;
}
pub trait AsyncHost: BaseHost {
fn get_mast_forest(&self, node_digest: &Word) -> impl FutureMaybeSend<Option<Arc<MastForest>>>;
fn on_event(
&mut self,
process: &ProcessState<'_>,
) -> impl FutureMaybeSend<Result<Vec<AdviceMutation>, EventError>>;
}
#[cfg(target_family = "wasm")]
pub trait FutureMaybeSend<O>: Future<Output = O> {}
#[cfg(target_family = "wasm")]
impl<T, O> FutureMaybeSend<O> for T where T: Future<Output = O> {}
#[cfg(not(target_family = "wasm"))]
pub trait FutureMaybeSend<O>: Future<Output = O> + Send {}
#[cfg(not(target_family = "wasm"))]
impl<T, O> FutureMaybeSend<O> for T where T: Future<Output = O> + Send {}