rename PrimOpPhase

This commit is contained in:
2026-07-12 21:11:38 +08:00
parent dde3052e2d
commit 7220b42024
14 changed files with 349 additions and 345 deletions
+3 -3
View File
@@ -2,7 +2,7 @@ use std::fmt::Write;
use colored::Colorize as _;
use crate::{InstructionPtr, Op, OperandType, PrimOpPhase};
use crate::{InstructionPtr, Op, OperandType, Continuation};
pub trait DisassemblerContext {
fn resolve_string(&self, id: u32) -> &str;
@@ -294,8 +294,8 @@ impl<'a, Ctx: DisassemblerContext> Disassembler<'a, Ctx> {
self.read_operand_data();
("Call", "arg=?".into())
}
Op::DispatchPrimOp => {
let phase = PrimOpPhase::try_from(self.read_u8()).expect("invalid primop phase");
Op::DispatchCont => {
let phase = Continuation::try_from(self.read_u8()).expect("invalid primop phase");
("DispatchPrimOp", format!("phase={phase:?}"))
}
+233 -232
View File
@@ -31,7 +31,7 @@ pub enum Op {
MakePatternClosure,
Call,
DispatchPrimOp,
DispatchCont,
MakeAttrs,
MakeEmptyAttrs,
@@ -133,128 +133,140 @@ pub enum OperandData {
#[repr(u8)]
#[derive(Debug, Clone, Copy, Hash, PartialEq, Eq)]
pub enum PrimOpPhase {
Abort,
Add,
AddErrorContext,
pub enum Continuation {
// primops
PAbort,
PAdd,
PAddErrorContext,
All,
AllCallPred,
AllCheck,
PAll,
PAllCallPred,
PAllCheck,
Any,
AnyCallPred,
AnyCheck,
PAny,
PAnyCallPred,
PAnyCheck,
AppendContext,
AttrNames,
AttrValues,
BaseNameOf,
BitAnd,
BitOr,
BitXor,
Break,
CatAttrs,
Ceil,
CompareVersions,
ConcatLists,
ConcatMap,
ConcatStringsSep,
ConvertHash,
PAppendContext,
PAppendContextLoop,
PAppendContextEntryForced,
PAppendContextOutputsForced,
PAppendContextOutputElementLoop,
PAppendContextOutputElementForced,
DeepSeq,
DeepSeqPush,
DeepSeqLoop,
PAttrNames,
PAttrValues,
PBaseNameOf,
PBitAnd,
PBitOr,
PBitXor,
PBreak,
PCatAttrs,
PCeil,
PCompareVersions,
PConcatLists,
PConcatMap,
PConcatStringsSep,
PConvertHash,
Derivation,
DerivationStrict,
DirOf,
Div,
Elem,
ElemAt,
FetchGit,
FetchMercurial,
FetchTarball,
FetchTree,
FetchUrl,
PDeepSeq,
PDeepSeqPush,
PDeepSeqLoop,
FilterForceList,
FilterCallPred,
FilterCheck,
PDerivation,
PDerivationStrict,
PDirOf,
PDiv,
PElem,
PElemAt,
PFetchGit,
PFetchMercurial,
PFetchTarball,
PFetchTree,
PFetchUrl,
FilterSource,
FindFile,
Floor,
FoldlStrict,
FoldlStrictEmpty,
FoldlStrictCall1,
FoldlStrictCall2,
FoldlStrictUpdate,
FromJSON,
FromTOML,
FunctionArgs,
GenList,
GenericClosure,
GetAttr,
GetContext,
GetEnv,
GroupBy,
HasAttr,
HasContext,
HashFile,
HashString,
Head,
Import,
IntersectAttrs,
IsAttrs,
IsBool,
IsFloat,
IsFunction,
IsInt,
IsList,
IsNull,
IsPath,
IsString,
Length,
LessThan,
ListToAttrs,
Map,
MapAttrs,
Match,
Mul,
ParseDrvName,
Partition,
Path,
PathExists,
Placeholder,
ReadDir,
ReadFile,
ReadFileType,
RemoveAttrs,
ReplaceStrings,
ScopedImport,
Seq,
Sort,
Split,
SplitVersion,
StorePath,
StringLength,
Sub,
Substring,
Tail,
Throw,
ToFile,
ToJSON,
ToPath,
ToString,
ToXML,
Trace,
TryEval,
TypeOf,
UnsafeDiscardStringContext,
UnsafeGetAttrPos,
Warn,
ZipAttrsWith,
PFilterForceList,
PFilterCallPred,
PFilterCheck,
PFilterSource,
PFindFile,
PFloor,
PFoldlStrict,
PFoldlStrictEmpty,
PFoldlStrictCall1,
PFoldlStrictCall2,
PFoldlStrictUpdate,
PFromJSON,
PFromTOML,
PFunctionArgs,
PGenList,
PGenericClosure,
PGetAttr,
PGetContext,
PGetEnv,
PGroupBy,
PHasAttr,
PHasContext,
PHashFile,
PHashString,
PHead,
PImport,
PImportFinalize,
PScopedImport,
PScopedImportFinalize,
PIntersectAttrs,
PIsAttrs,
PIsBool,
PIsFloat,
PIsFunction,
PIsInt,
PIsList,
PIsNull,
PIsPath,
PIsString,
PLength,
PLessThan,
PListToAttrs,
PMap,
PMapAttrs,
PMatch,
PMul,
PParseDrvName,
PPartition,
PPath,
PPathExists,
PPlaceholder,
PReadDir,
PReadFile,
PReadFileType,
PRemoveAttrs,
PReplaceStrings,
PSeq,
PSort,
PSplit,
PSplitVersion,
PStorePath,
PStringLength,
PSub,
PSubstring,
PTail,
PThrow,
PToFile,
PToJSON,
PToPath,
PToString,
PToXML,
PTrace,
PTryEval,
PTypeOf,
PUnsafeDiscardStringContext,
PUnsafeGetAttrPos,
PWarn,
PZipAttrsWith,
PUnsafeDiscardOutputDependency,
ForceResultShallow,
ForceResultShallowPush,
@@ -268,21 +280,10 @@ pub enum PrimOpPhase {
CallFunctor1,
CallFunctor2,
ImportFinalize,
ScopedImportFinalize,
AppendContextLoop,
AppendContextEntryForced,
AppendContextOutputsForced,
AppendContextOutputElementLoop,
AppendContextOutputElementForced,
UnsafeDiscardOutputDependency,
Illegal,
}
impl TryFrom<u8> for PrimOpPhase {
impl TryFrom<u8> for Continuation {
type Error = u8;
fn try_from(value: u8) -> Result<Self, Self::Error> {
@@ -294,113 +295,113 @@ impl TryFrom<u8> for PrimOpPhase {
}
}
impl PrimOpPhase {
impl Continuation {
pub fn entry_for_builtin(id: BuiltinId) -> Self {
use BuiltinId::*;
match id {
Abort => Self::Abort,
Add => Self::Add,
AddErrorContext => Self::AddErrorContext,
All => Self::All,
Any => Self::Any,
AppendContext => Self::AppendContext,
AttrNames => Self::AttrNames,
AttrValues => Self::AttrValues,
BaseNameOf => Self::BaseNameOf,
BitAnd => Self::BitAnd,
BitOr => Self::BitOr,
BitXor => Self::BitXor,
Break => Self::Break,
CatAttrs => Self::CatAttrs,
Ceil => Self::Ceil,
CompareVersions => Self::CompareVersions,
ConcatLists => Self::ConcatLists,
ConcatMap => Self::ConcatMap,
ConcatStringsSep => Self::ConcatStringsSep,
ConvertHash => Self::ConvertHash,
DeepSeq => Self::DeepSeq,
Derivation => Self::Derivation,
DerivationStrict => Self::DerivationStrict,
DirOf => Self::DirOf,
Div => Self::Div,
Elem => Self::Elem,
ElemAt => Self::ElemAt,
FetchGit => Self::FetchGit,
FetchMercurial => Self::FetchMercurial,
FetchTarball => Self::FetchTarball,
FetchTree => Self::FetchTree,
FetchUrl => Self::FetchUrl,
Filter => Self::FilterForceList,
FilterSource => Self::FilterSource,
FindFile => Self::FindFile,
Floor => Self::Floor,
FoldlStrict => Self::FoldlStrict,
FromJSON => Self::FromJSON,
FromTOML => Self::FromTOML,
FunctionArgs => Self::FunctionArgs,
GenList => Self::GenList,
GenericClosure => Self::GenericClosure,
GetAttr => Self::GetAttr,
GetContext => Self::GetContext,
GetEnv => Self::GetEnv,
GroupBy => Self::GroupBy,
HasAttr => Self::HasAttr,
HasContext => Self::HasContext,
HashFile => Self::HashFile,
HashString => Self::HashString,
Head => Self::Head,
Import => Self::Import,
IntersectAttrs => Self::IntersectAttrs,
IsAttrs => Self::IsAttrs,
IsBool => Self::IsBool,
IsFloat => Self::IsFloat,
IsFunction => Self::IsFunction,
IsInt => Self::IsInt,
IsList => Self::IsList,
IsNull => Self::IsNull,
IsPath => Self::IsPath,
IsString => Self::IsString,
Length => Self::Length,
LessThan => Self::LessThan,
ListToAttrs => Self::ListToAttrs,
Map => Self::Map,
MapAttrs => Self::MapAttrs,
Match => Self::Match,
Mul => Self::Mul,
ParseDrvName => Self::ParseDrvName,
Partition => Self::Partition,
Path => Self::Path,
PathExists => Self::PathExists,
Placeholder => Self::Placeholder,
ReadDir => Self::ReadDir,
ReadFile => Self::ReadFile,
ReadFileType => Self::ReadFileType,
RemoveAttrs => Self::RemoveAttrs,
ReplaceStrings => Self::ReplaceStrings,
ScopedImport => Self::ScopedImport,
Seq => Self::Seq,
Sort => Self::Sort,
Split => Self::Split,
SplitVersion => Self::SplitVersion,
StorePath => Self::StorePath,
StringLength => Self::StringLength,
Sub => Self::Sub,
Substring => Self::Substring,
Tail => Self::Tail,
Throw => Self::Throw,
ToFile => Self::ToFile,
ToJSON => Self::ToJSON,
ToPath => Self::ToPath,
ToString => Self::ToString,
ToXML => Self::ToXML,
Trace => Self::Trace,
TryEval => Self::TryEval,
TypeOf => Self::TypeOf,
UnsafeDiscardStringContext => Self::UnsafeDiscardStringContext,
UnsafeDiscardOutputDependency => Self::UnsafeDiscardOutputDependency,
UnsafeGetAttrPos => Self::UnsafeGetAttrPos,
Warn => Self::Warn,
ZipAttrsWith => Self::ZipAttrsWith,
Abort => Self::PAbort,
Add => Self::PAdd,
AddErrorContext => Self::PAddErrorContext,
All => Self::PAll,
Any => Self::PAny,
AppendContext => Self::PAppendContext,
AttrNames => Self::PAttrNames,
AttrValues => Self::PAttrValues,
BaseNameOf => Self::PBaseNameOf,
BitAnd => Self::PBitAnd,
BitOr => Self::PBitOr,
BitXor => Self::PBitXor,
Break => Self::PBreak,
CatAttrs => Self::PCatAttrs,
Ceil => Self::PCeil,
CompareVersions => Self::PCompareVersions,
ConcatLists => Self::PConcatLists,
ConcatMap => Self::PConcatMap,
ConcatStringsSep => Self::PConcatStringsSep,
ConvertHash => Self::PConvertHash,
DeepSeq => Self::PDeepSeq,
Derivation => Self::PDerivation,
DerivationStrict => Self::PDerivationStrict,
DirOf => Self::PDirOf,
Div => Self::PDiv,
Elem => Self::PElem,
ElemAt => Self::PElemAt,
FetchGit => Self::PFetchGit,
FetchMercurial => Self::PFetchMercurial,
FetchTarball => Self::PFetchTarball,
FetchTree => Self::PFetchTree,
FetchUrl => Self::PFetchUrl,
Filter => Self::PFilterForceList,
FilterSource => Self::PFilterSource,
FindFile => Self::PFindFile,
Floor => Self::PFloor,
FoldlStrict => Self::PFoldlStrict,
FromJSON => Self::PFromJSON,
FromTOML => Self::PFromTOML,
FunctionArgs => Self::PFunctionArgs,
GenList => Self::PGenList,
GenericClosure => Self::PGenericClosure,
GetAttr => Self::PGetAttr,
GetContext => Self::PGetContext,
GetEnv => Self::PGetEnv,
GroupBy => Self::PGroupBy,
HasAttr => Self::PHasAttr,
HasContext => Self::PHasContext,
HashFile => Self::PHashFile,
HashString => Self::PHashString,
Head => Self::PHead,
Import => Self::PImport,
IntersectAttrs => Self::PIntersectAttrs,
IsAttrs => Self::PIsAttrs,
IsBool => Self::PIsBool,
IsFloat => Self::PIsFloat,
IsFunction => Self::PIsFunction,
IsInt => Self::PIsInt,
IsList => Self::PIsList,
IsNull => Self::PIsNull,
IsPath => Self::PIsPath,
IsString => Self::PIsString,
Length => Self::PLength,
LessThan => Self::PLessThan,
ListToAttrs => Self::PListToAttrs,
Map => Self::PMap,
MapAttrs => Self::PMapAttrs,
Match => Self::PMatch,
Mul => Self::PMul,
ParseDrvName => Self::PParseDrvName,
Partition => Self::PPartition,
Path => Self::PPath,
PathExists => Self::PPathExists,
Placeholder => Self::PPlaceholder,
ReadDir => Self::PReadDir,
ReadFile => Self::PReadFile,
ReadFileType => Self::PReadFileType,
RemoveAttrs => Self::PRemoveAttrs,
ReplaceStrings => Self::PReplaceStrings,
ScopedImport => Self::PScopedImport,
Seq => Self::PSeq,
Sort => Self::PSort,
Split => Self::PSplit,
SplitVersion => Self::PSplitVersion,
StorePath => Self::PStorePath,
StringLength => Self::PStringLength,
Sub => Self::PSub,
Substring => Self::PSubstring,
Tail => Self::PTail,
Throw => Self::PThrow,
ToFile => Self::PToFile,
ToJSON => Self::PToJSON,
ToPath => Self::PToPath,
ToString => Self::PToString,
ToXML => Self::PToXML,
Trace => Self::PTrace,
TryEval => Self::PTryEval,
TypeOf => Self::PTypeOf,
UnsafeDiscardStringContext => Self::PUnsafeDiscardStringContext,
UnsafeDiscardOutputDependency => Self::PUnsafeDiscardOutputDependency,
UnsafeGetAttrPos => Self::PUnsafeGetAttrPos,
Warn => Self::PWarn,
ZipAttrsWith => Self::PZipAttrsWith,
}
}
+4 -4
View File
@@ -1,5 +1,5 @@
use bumpalo::Bump;
use fix_bytecode::{Const, InstructionPtr, Op, PrimOpPhase};
use fix_bytecode::{Const, InstructionPtr, Op, Continuation};
use fix_error::{Error, Result, Source};
use fix_lang::{StringId, Symbol};
use fix_runtime::{StaticValue, VmCode, VmRuntimeCtx};
@@ -25,9 +25,9 @@ pub struct CodeState {
impl CodeState {
pub fn new(strings: &mut DefaultStringInterner) -> Self {
let global_env = crate::ir::new_global_env(strings);
let mut bytecode = Vec::with_capacity(PrimOpPhase::Illegal as usize * 2);
for phase in 0..=PrimOpPhase::Illegal as u8 {
bytecode.push(Op::DispatchPrimOp as u8);
let mut bytecode = Vec::with_capacity(Continuation::Illegal as usize * 2);
for phase in 0..=Continuation::Illegal as u8 {
bytecode.push(Op::DispatchCont as u8);
bytecode.push(phase);
}
Self {
+2 -2
View File
@@ -1,4 +1,4 @@
use fix_bytecode::{Const, InstructionPtr, Op, OperandType, PrimOpPhase};
use fix_bytecode::{Const, InstructionPtr, Op, OperandType, Continuation};
use fix_lang::{BUILTINS, StringId};
use hashbrown::HashMap;
use rnix::TextRange;
@@ -80,7 +80,7 @@ impl<'a, Ctx: BytecodeContext> BytecodeEmitter<'a, Ctx> {
InlineOperand::Const(Const::PrimOp {
id,
arity,
dispatch_ip: PrimOpPhase::entry_for_builtin(id).ip(),
dispatch_ip: Continuation::entry_for_builtin(id).ip(),
})
}
BuiltinConst(id) => InlineOperand::BuiltinConst(id),
+2 -2
View File
@@ -144,7 +144,7 @@ tail_fn!(op_make_closure, (reader, mc));
tail_fn!(op_make_pattern_closure, (reader, mc));
tail_fn!(op_call, (ctx, reader, mc));
tail_fn!(op_dispatch_primop, (ctx, reader, mc));
tail_fn!(op_dispatch_cont, (ctx, reader, mc));
tail_fn!(op_return, (ctx, reader, mc));
tail_fn!(op_make_attrs, (ctx, reader, mc));
@@ -235,7 +235,7 @@ table! {
MakePatternClosure => op_make_pattern_closure,
Call => op_call,
DispatchPrimOp => op_dispatch_primop,
DispatchCont => op_dispatch_cont,
Return => op_return,
MakeAttrs => op_make_attrs,
+8 -8
View File
@@ -1,4 +1,4 @@
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_runtime::{resolve_operand, *};
use gc_arena::{Gc, Mutation, RefLock};
@@ -31,7 +31,7 @@ pub(crate) fn call<'gc, M: Machine<'gc>>(
thunk: None,
env: m.env(),
});
reader.set_pc(PrimOpPhase::CallPattern.ip() as usize);
reader.set_pc(Continuation::CallPattern.ip() as usize);
return Step::Continue(());
}
@@ -101,7 +101,7 @@ pub(crate) fn call<'gc, M: Machine<'gc>>(
m.push(arg);
m.push(func.relax());
m.push(functor);
reader.set_pc(PrimOpPhase::CallFunctor1.ip() as usize);
reader.set_pc(Continuation::CallFunctor1.ip() as usize);
return Step::Continue(());
} else {
return m.finish_err(Error::eval_error(format!(
@@ -142,19 +142,19 @@ pub(crate) fn op_return<'gc, M: Machine<'gc>>(
ForceMode::AsIs => return m.finish_ok(ctx.convert_value(val.relax())),
ForceMode::Shallow => {
m.push(val.relax());
reader.set_pc(PrimOpPhase::ForceResultShallow.ip() as usize);
reader.set_pc(Continuation::ForceResultShallow.ip() as usize);
return Step::Continue(());
}
ForceMode::Deep => {
m.push(val.relax());
m.push(val.relax());
m.push_call_frame(CallFrame {
pc: PrimOpPhase::ForceResultDeepFinish.ip() as usize,
pc: Continuation::ForceResultDeepFinish.ip() as usize,
thunk: None,
env: m.env(),
});
m.inc_call_depth();
reader.set_pc(PrimOpPhase::DeepSeq.ip() as usize);
reader.set_pc(Continuation::PDeepSeq.ip() as usize);
return Step::Continue(());
}
}
@@ -171,11 +171,11 @@ pub(crate) fn op_return<'gc, M: Machine<'gc>>(
}
#[inline(always)]
pub(crate) fn op_dispatch_primop<'gc, M: Machine<'gc>>(
pub(crate) fn op_dispatch_cont<'gc, M: Machine<'gc>>(
m: &mut M,
ctx: &mut impl VmRuntimeCtx,
reader: &mut BytecodeReader<'_>,
mc: &Mutation<'gc>,
) -> Step {
crate::primops::dispatch_primop(m, ctx, reader, mc)
crate::primops::dispatch_cont(m, ctx, reader, mc)
}
+2 -2
View File
@@ -1,6 +1,6 @@
use std::path::PathBuf;
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_lang::{BUILTINS, BuiltinId, StringId};
use fix_runtime::{
@@ -25,7 +25,7 @@ pub(crate) fn op_load_builtin<'gc, M: Machine<'gc>>(
m.push(Value::new_inline(PrimOp {
id,
arity: BUILTINS[id as usize].1,
dispatch_ip: PrimOpPhase::entry_for_builtin(id).ip(),
dispatch_ip: Continuation::entry_for_builtin(id).ip(),
}));
Step::Continue(())
}
+5 -3
View File
@@ -7,7 +7,7 @@
use std::path::PathBuf;
use fix_bytecode::{InstructionPtr, PrimOpPhase};
use fix_bytecode::{InstructionPtr, Continuation};
use fix_error::{Error, Result, Source};
use fix_lang::{BUILTINS, BuiltinId, StringId};
use gc_arena::metrics::Pacing;
@@ -60,7 +60,7 @@ fn init_builtins<'gc>(mc: &Mutation<'gc>, ctx: &mut impl VmRuntimeCtx) -> Value<
let id = BuiltinId::try_from(idx as u8).expect("infallible");
let name = name.strip_prefix("__").unwrap_or(name);
let name = ctx.intern_string(name);
let dispatch_ip = PrimOpPhase::entry_for_builtin(id).ip();
let dispatch_ip = Continuation::entry_for_builtin(id).ip();
entries.push((
name,
Value::new_inline(PrimOp {
@@ -476,6 +476,8 @@ impl<'gc> Vm<'gc> {
let mut fuel = Self::DEFAULT_FUEL_AMOUNT;
loop {
use crate::instructions::op_dispatch_cont;
if fuel == 0 {
return Action::Continue { pc: reader.pc() };
}
@@ -502,7 +504,7 @@ impl<'gc> Vm<'gc> {
MakePatternClosure => op_make_pattern_closure(self, &mut reader, mc),
Call => op_call(self, ctx, &mut reader, mc),
DispatchPrimOp => op_dispatch_primop(self, ctx, &mut reader, mc),
DispatchCont => op_dispatch_cont(self, ctx, &mut reader, mc),
Return => op_return(self, ctx, &mut reader, mc),
MakeAttrs => op_make_attrs(self, ctx, &mut reader, mc),
+13 -13
View File
@@ -5,7 +5,7 @@
//! See `fix-runtime/src/string_context.rs` for the
//! `StringContextElem` type.
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_lang::StringId;
use fix_runtime::{
@@ -196,7 +196,7 @@ pub fn append_context<'gc, M: Machine<'gc>>(
m.push(Value::new_inline(0i32));
m.push(Value::new_gc(acc));
reader.set_pc(PrimOpPhase::AppendContextLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextLoop.ip() as usize);
Step::Continue(())
}
@@ -221,9 +221,9 @@ pub fn append_context_loop<'gc, M: Machine<'gc>>(
0,
reader,
mc,
PrimOpPhase::AppendContextEntryForced.ip() as usize,
Continuation::PAppendContextEntryForced.ip() as usize,
)?;
reader.set_pc(PrimOpPhase::AppendContextEntryForced.ip() as usize);
reader.set_pc(Continuation::PAppendContextEntryForced.ip() as usize);
Step::Continue(())
}
@@ -296,9 +296,9 @@ pub fn append_context_entry_forced<'gc, M: Machine<'gc>>(
0,
reader,
mc,
PrimOpPhase::AppendContextOutputsForced.ip() as usize,
Continuation::PAppendContextOutputsForced.ip() as usize,
)?;
reader.set_pc(PrimOpPhase::AppendContextOutputsForced.ip() as usize);
reader.set_pc(Continuation::PAppendContextOutputsForced.ip() as usize);
return Step::Continue(());
}
@@ -306,7 +306,7 @@ pub fn append_context_entry_forced<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let idx_back = m.peek(1).as_inline::<i32>().unwrap();
m.replace(1, Value::new_inline(idx_back + 1));
reader.set_pc(PrimOpPhase::AppendContextLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextLoop.ip() as usize);
Step::Continue(())
}
@@ -327,12 +327,12 @@ pub fn append_context_outputs_forced<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let idx_back = m.peek(1).as_inline::<i32>().unwrap();
m.replace(1, Value::new_inline(idx_back + 1));
reader.set_pc(PrimOpPhase::AppendContextLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextLoop.ip() as usize);
return Step::Continue(());
}
m.push(Value::new_inline(0i32));
reader.set_pc(PrimOpPhase::AppendContextOutputElementLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextOutputElementLoop.ip() as usize);
Step::Continue(())
}
@@ -355,7 +355,7 @@ pub fn append_context_output_element_loop<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let idx_back = m.peek(1).as_inline::<i32>().unwrap();
m.replace(1, Value::new_inline(idx_back + 1));
reader.set_pc(PrimOpPhase::AppendContextLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextLoop.ip() as usize);
return Step::Continue(());
}
@@ -365,9 +365,9 @@ pub fn append_context_output_element_loop<'gc, M: Machine<'gc>>(
0,
reader,
mc,
PrimOpPhase::AppendContextOutputElementForced.ip() as usize,
Continuation::PAppendContextOutputElementForced.ip() as usize,
)?;
reader.set_pc(PrimOpPhase::AppendContextOutputElementForced.ip() as usize);
reader.set_pc(Continuation::PAppendContextOutputElementForced.ip() as usize);
Step::Continue(())
}
@@ -412,7 +412,7 @@ pub fn append_context_output_element_forced<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let oidx = m.peek(0).as_inline::<i32>().unwrap();
m.replace(0, Value::new_inline(oidx + 1));
reader.set_pc(PrimOpPhase::AppendContextOutputElementLoop.ip() as usize);
reader.set_pc(Continuation::PAppendContextOutputElementLoop.ip() as usize);
Step::Continue(())
}
+10 -10
View File
@@ -1,4 +1,4 @@
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_runtime::{
AttrSet, BytecodeReader, Closure, Env, List, Machine, MachineExt, Step, StrictValue, Value,
@@ -78,7 +78,7 @@ pub fn deep_seq_force_top<'gc, M: Machine<'gc>>(
m.push(Value::new_gc(seen));
m.push(Value::new_gc(worklist));
m.push(Value::new_inline(count));
reader.set_pc(PrimOpPhase::DeepSeqPush.ip() as usize);
reader.set_pc(Continuation::PDeepSeqPush.ip() as usize);
Step::Continue(())
}
@@ -106,8 +106,8 @@ pub fn deep_seq_push<'gc, M: Machine<'gc>>(
m.push(item);
// force item at TOS, resume at DeepSeqLoop after force
m.force_slot_to_pc(0, reader, mc, PrimOpPhase::DeepSeqLoop.ip() as usize)?;
reader.set_pc(PrimOpPhase::DeepSeqLoop.ip() as usize);
m.force_slot_to_pc(0, reader, mc, Continuation::PDeepSeqLoop.ip() as usize)?;
reader.set_pc(Continuation::PDeepSeqLoop.ip() as usize);
Step::Continue(())
}
@@ -157,7 +157,7 @@ pub fn deep_seq_loop<'gc, M: Machine<'gc>>(
}
m.replace(0, Value::new_inline(counter + added as i32));
reader.set_pc(PrimOpPhase::DeepSeqPush.ip() as usize);
reader.set_pc(Continuation::PDeepSeqPush.ip() as usize);
Step::Continue(())
}
@@ -187,7 +187,7 @@ pub fn force_result_shallow<'gc, M: Machine<'gc>>(
m.push(Value::new_inline(0i32));
m.push(Value::new_inline(count as i32));
reader.set_pc(PrimOpPhase::ForceResultShallowPush.ip() as usize);
reader.set_pc(Continuation::ForceResultShallowPush.ip() as usize);
Step::Continue(())
}
@@ -225,9 +225,9 @@ pub fn force_result_shallow_push<'gc, M: Machine<'gc>>(
0,
reader,
mc,
PrimOpPhase::ForceResultShallowLoop.ip() as usize,
Continuation::ForceResultShallowLoop.ip() as usize,
)?;
reader.set_pc(PrimOpPhase::ForceResultShallowLoop.ip() as usize);
reader.set_pc(Continuation::ForceResultShallowLoop.ip() as usize);
}
Step::Continue(())
}
@@ -238,7 +238,7 @@ pub fn force_result_shallow_loop<'gc, M: Machine<'gc>>(
_mc: &Mutation<'gc>,
) -> Step {
let _ = m.pop(); // forced child
reader.set_pc(PrimOpPhase::ForceResultShallowPush.ip() as usize);
reader.set_pc(Continuation::ForceResultShallowPush.ip() as usize);
Step::Continue(())
}
@@ -288,7 +288,7 @@ pub fn call_functor_1<'gc, M: Machine<'gc>>(
reader,
mc,
self_val,
PrimOpPhase::CallFunctor2.ip() as usize,
Continuation::CallFunctor2.ip() as usize,
)
}
+4 -4
View File
@@ -1,4 +1,4 @@
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_runtime::{
AttrSet, BytecodeReader, CallFrame, List, Machine, MachineExt, NixNum, Null, Path, Step,
StrictValue, Value, VmRuntimeCtx, VmRuntimeCtxExt,
@@ -71,7 +71,7 @@ pub fn eq_step<'gc, M: Machine<'gc>>(
.expect("non-empty rhs queue");
m.push(lhs);
m.push(rhs);
reader.set_pc(PrimOpPhase::EqForce.ip() as usize);
reader.set_pc(Continuation::EqForce.ip() as usize);
Step::Continue(())
}
@@ -83,7 +83,7 @@ pub fn eq_force<'gc, M: Machine<'gc>>(
) -> Step {
let (lhs, rhs) = m.force_and_retry::<(StrictValue, StrictValue)>(reader, mc)?;
apply_pair(m, ctx, mc, lhs, rhs);
reader.set_pc(PrimOpPhase::EqStep.ip() as usize);
reader.set_pc(Continuation::EqStep.ip() as usize);
Step::Continue(())
}
@@ -173,7 +173,7 @@ fn enter_eq_machine<'gc, M: Machine<'gc>>(
m.push(Value::new_inline(true));
m.push(Value::new_gc(List::new(mc, lhs_init)));
m.push(Value::new_gc(List::new(mc, rhs_init)));
reader.set_pc(PrimOpPhase::EqStep.ip() as usize);
reader.set_pc(Continuation::EqStep.ip() as usize);
Step::Continue(())
}
+3 -3
View File
@@ -1,6 +1,6 @@
use std::path::PathBuf;
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_lang::StringId;
use fix_runtime::{
@@ -43,7 +43,7 @@ pub fn import<'gc, M: Machine<'gc>>(
m.push(Value::new_inline(path_sid));
let env = m.env();
m.push_call_frame(CallFrame {
pc: PrimOpPhase::ImportFinalize.ip() as usize,
pc: Continuation::PImportFinalize.ip() as usize,
thunk: None,
env,
});
@@ -111,7 +111,7 @@ pub fn scoped_import<'gc, M: Machine<'gc>>(
let env = m.env();
m.push_call_frame(CallFrame {
pc: PrimOpPhase::ScopedImportFinalize.ip() as usize,
pc: Continuation::PScopedImportFinalize.ip() as usize,
thunk: None,
env,
});
+15 -15
View File
@@ -1,4 +1,4 @@
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_runtime::{BytecodeReader, List, Machine, MachineExt, NixType, Step, StrictValue, Value};
use gc_arena::Mutation;
@@ -20,7 +20,7 @@ pub fn filter_force_list<'gc, M: Machine<'gc>>(
// prepare stack layout: [ pred list idx acc ]
m.push(Value::new_inline(0));
m.push(Value::new_gc(List::new_gc(mc)));
reader.set_pc(PrimOpPhase::FilterCallPred.ip() as usize);
reader.set_pc(Continuation::PFilterCallPred.ip() as usize);
Step::Continue(())
}
@@ -36,7 +36,7 @@ pub fn filter_call_pred<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let elem = m.peek_forced(2).as_gc::<List>().unwrap().inner.borrow()[idx as usize];
m.push(pred.relax());
m.call(reader, mc, elem, PrimOpPhase::FilterCheck.ip() as usize)
m.call(reader, mc, elem, Continuation::PFilterCheck.ip() as usize)
}
pub fn filter_check<'gc, M: Machine<'gc>>(
@@ -64,7 +64,7 @@ pub fn filter_check<'gc, M: Machine<'gc>>(
return m.return_from_primop(acc, reader);
}
m.replace(1, Value::new_inline(idx + 1));
reader.set_pc(PrimOpPhase::FilterCallPred.ip() as usize);
reader.set_pc(Continuation::PFilterCallPred.ip() as usize);
Step::Continue(())
}
@@ -88,7 +88,7 @@ pub fn foldl_strict_entry<'gc, M: Machine<'gc>>(
};
if list.inner.borrow().is_empty() {
let _ = m.pop(); // list
reader.set_pc(PrimOpPhase::FoldlStrictEmpty.ip() as usize);
reader.set_pc(Continuation::PFoldlStrictEmpty.ip() as usize);
return Step::Continue(());
}
let list_val = m.pop();
@@ -96,7 +96,7 @@ pub fn foldl_strict_entry<'gc, M: Machine<'gc>>(
m.push(list_val);
m.push(Value::new_inline(0i32));
m.push(nul_val);
reader.set_pc(PrimOpPhase::FoldlStrictCall1.ip() as usize);
reader.set_pc(Continuation::PFoldlStrictCall1.ip() as usize);
Step::Continue(())
}
@@ -119,7 +119,7 @@ pub fn foldl_strict_call1<'gc, M: Machine<'gc>>(
let op = m.peek_forced(3);
let acc = m.peek(0);
m.push(op.relax());
m.call(reader, mc, acc, PrimOpPhase::FoldlStrictCall2.ip() as usize)
m.call(reader, mc, acc, Continuation::PFoldlStrictCall2.ip() as usize)
}
pub fn foldl_strict_call2<'gc, M: Machine<'gc>>(
@@ -136,7 +136,7 @@ pub fn foldl_strict_call2<'gc, M: Machine<'gc>>(
reader,
mc,
elem,
PrimOpPhase::FoldlStrictUpdate.ip() as usize,
Continuation::PFoldlStrictUpdate.ip() as usize,
)
}
@@ -160,7 +160,7 @@ pub fn foldl_strict_update<'gc, M: Machine<'gc>>(
return m.return_from_primop(acc, reader);
}
m.replace(1, Value::new_inline(idx + 1));
reader.set_pc(PrimOpPhase::FoldlStrictCall1.ip() as usize);
reader.set_pc(Continuation::PFoldlStrictCall1.ip() as usize);
Step::Continue(())
}
@@ -183,7 +183,7 @@ pub fn all_entry<'gc, M: Machine<'gc>>(
}
// prepare stack layout: [ pred list idx ]
m.push(Value::new_inline(0));
reader.set_pc(PrimOpPhase::AllCallPred.ip() as usize);
reader.set_pc(Continuation::PAllCallPred.ip() as usize);
Step::Continue(())
}
@@ -198,7 +198,7 @@ pub fn all_call_pred<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let elem = m.peek_forced(1).as_gc::<List>().unwrap().inner.borrow()[idx as usize];
m.push(pred.relax());
m.call(reader, mc, elem, PrimOpPhase::AllCheck.ip() as usize)
m.call(reader, mc, elem, Continuation::PAllCheck.ip() as usize)
}
pub fn all_check<'gc, M: Machine<'gc>>(
@@ -219,7 +219,7 @@ pub fn all_check<'gc, M: Machine<'gc>>(
return m.return_from_primop(Value::new_inline(ret), reader);
}
m.replace(0, Value::new_inline(idx + 1));
reader.set_pc(PrimOpPhase::AllCallPred.ip() as usize);
reader.set_pc(Continuation::PAllCallPred.ip() as usize);
Step::Continue(())
}
@@ -242,7 +242,7 @@ pub fn any_entry<'gc, M: Machine<'gc>>(
}
// prepare stack layout: [ pred list idx ]
m.push(Value::new_inline(0));
reader.set_pc(PrimOpPhase::AnyCallPred.ip() as usize);
reader.set_pc(Continuation::PAnyCallPred.ip() as usize);
Step::Continue(())
}
@@ -257,7 +257,7 @@ pub fn any_call_pred<'gc, M: Machine<'gc>>(
#[allow(clippy::unwrap_used)]
let elem = m.peek_forced(1).as_gc::<List>().unwrap().inner.borrow()[idx as usize];
m.push(pred.relax());
m.call(reader, mc, elem, PrimOpPhase::AnyCheck.ip() as usize)
m.call(reader, mc, elem, Continuation::PAnyCheck.ip() as usize)
}
pub fn any_check<'gc, M: Machine<'gc>>(
@@ -278,6 +278,6 @@ pub fn any_check<'gc, M: Machine<'gc>>(
return m.return_from_primop(Value::new_inline(ret), reader);
}
m.replace(0, Value::new_inline(idx + 1));
reader.set_pc(PrimOpPhase::AnyCallPred.ip() as usize);
reader.set_pc(Continuation::PAnyCallPred.ip() as usize);
Step::Continue(())
}
+45 -44
View File
@@ -10,7 +10,7 @@ pub use context::*;
pub use control::*;
pub use conv::*;
pub use eq::*;
use fix_bytecode::PrimOpPhase;
use fix_bytecode::Continuation;
use fix_error::Error;
use fix_runtime::{BytecodeReader, Machine, Step, VmRuntimeCtx};
use gc_arena::Mutation;
@@ -19,42 +19,42 @@ pub use list::*;
pub use path::*;
#[allow(clippy::too_many_lines)]
pub fn dispatch_primop<'gc, M: Machine<'gc>>(
pub fn dispatch_cont<'gc, M: Machine<'gc>>(
m: &mut M,
ctx: &mut impl VmRuntimeCtx,
reader: &mut BytecodeReader<'_>,
mc: &Mutation<'gc>,
) -> Step {
use PrimOpPhase::*;
let phase_disc = reader.read_u8();
let Ok(phase) = PrimOpPhase::try_from(phase_disc) else {
use Continuation::*;
let cont = reader.read_u8();
let Ok(cont) = Continuation::try_from(cont) else {
return m.finish_err(Error::eval_error("invalid primop phase"));
};
match phase {
Abort => abort(m, ctx, reader, mc),
match cont {
PAbort => abort(m, ctx, reader, mc),
All => all_entry(m, reader, mc),
AllCallPred => all_call_pred(m, reader, mc),
AllCheck => all_check(m, reader, mc),
PAll => all_entry(m, reader, mc),
PAllCallPred => all_call_pred(m, reader, mc),
PAllCheck => all_check(m, reader, mc),
Any => any_entry(m, reader, mc),
AnyCallPred => any_call_pred(m, reader, mc),
AnyCheck => any_check(m, reader, mc),
PAny => any_entry(m, reader, mc),
PAnyCallPred => any_call_pred(m, reader, mc),
PAnyCheck => any_check(m, reader, mc),
DeepSeq => deep_seq_force_top(m, reader, mc),
DeepSeqPush => deep_seq_push(m, reader, mc),
DeepSeqLoop => deep_seq_loop(m, reader, mc),
Seq => seq(m, reader, mc),
PDeepSeq => deep_seq_force_top(m, reader, mc),
PDeepSeqPush => deep_seq_push(m, reader, mc),
PDeepSeqLoop => deep_seq_loop(m, reader, mc),
PSeq => seq(m, reader, mc),
FilterForceList => filter_force_list(m, reader, mc),
FilterCallPred => filter_call_pred(m, reader, mc),
FilterCheck => filter_check(m, reader, mc),
PFilterForceList => filter_force_list(m, reader, mc),
PFilterCallPred => filter_call_pred(m, reader, mc),
PFilterCheck => filter_check(m, reader, mc),
FoldlStrict => foldl_strict_entry(m, reader, mc),
FoldlStrictEmpty => foldl_strict_empty(m, reader, mc),
FoldlStrictCall1 => foldl_strict_call1(m, reader, mc),
FoldlStrictCall2 => foldl_strict_call2(m, reader, mc),
FoldlStrictUpdate => foldl_strict_update(m, reader, mc),
PFoldlStrict => foldl_strict_entry(m, reader, mc),
PFoldlStrictEmpty => foldl_strict_empty(m, reader, mc),
PFoldlStrictCall1 => foldl_strict_call1(m, reader, mc),
PFoldlStrictCall2 => foldl_strict_call2(m, reader, mc),
PFoldlStrictUpdate => foldl_strict_update(m, reader, mc),
ForceResultShallow => force_result_shallow(m, ctx, reader, mc),
ForceResultShallowPush => force_result_shallow_push(m, ctx, reader, mc),
@@ -68,29 +68,30 @@ pub fn dispatch_primop<'gc, M: Machine<'gc>>(
CallFunctor1 => call_functor_1(m, reader, mc),
CallFunctor2 => call_functor_2(m, reader, mc),
Import => import(m, ctx, reader, mc),
ImportFinalize => import_finalize(m, ctx, reader),
ScopedImport => scoped_import(m, ctx, reader, mc),
ScopedImportFinalize => scoped_import_finalize(m, ctx, reader, mc),
PImport => import(m, ctx, reader, mc),
PImportFinalize => import_finalize(m, ctx, reader),
PScopedImport => scoped_import(m, ctx, reader, mc),
PScopedImportFinalize => scoped_import_finalize(m, ctx, reader, mc),
PathExists => path_exists(m, ctx, reader, mc),
ToPath => to_path(m, ctx, reader, mc),
IsPath => is_path(m, reader, mc),
ToString => to_string(m, ctx, reader, mc),
TypeOf => type_of(m, ctx, reader, mc),
PPathExists => path_exists(m, ctx, reader, mc),
PToPath => to_path(m, ctx, reader, mc),
PIsPath => is_path(m, reader, mc),
PToString => to_string(m, ctx, reader, mc),
PTypeOf => type_of(m, ctx, reader, mc),
HasContext => has_context(m, ctx, reader, mc),
GetContext => get_context(m, ctx, reader, mc),
AppendContext => append_context(m, ctx, reader, mc),
AppendContextLoop => append_context_loop(m, ctx, reader, mc),
AppendContextEntryForced => append_context_entry_forced(m, ctx, reader, mc),
AppendContextOutputsForced => append_context_outputs_forced(m, ctx, reader, mc),
AppendContextOutputElementLoop => append_context_output_element_loop(m, ctx, reader, mc),
AppendContextOutputElementForced => {
PHasContext => has_context(m, ctx, reader, mc),
PGetContext => get_context(m, ctx, reader, mc),
PAppendContext => append_context(m, ctx, reader, mc),
PAppendContextLoop => append_context_loop(m, ctx, reader, mc),
PAppendContextEntryForced => append_context_entry_forced(m, ctx, reader, mc),
PAppendContextOutputsForced => append_context_outputs_forced(m, ctx, reader, mc),
PAppendContextOutputElementLoop => append_context_output_element_loop(m, ctx, reader, mc),
PAppendContextOutputElementForced => {
append_context_output_element_forced(m, ctx, reader, mc)
}
UnsafeDiscardStringContext => unsafe_discard_string_context(m, ctx, reader, mc),
UnsafeDiscardOutputDependency => unsafe_discard_output_dependency(m, ctx, reader, mc),
PUnsafeDiscardStringContext => unsafe_discard_string_context(m, ctx, reader, mc),
PUnsafeDiscardOutputDependency => unsafe_discard_output_dependency(m, ctx, reader, mc),
phase => todo!("primop phase {phase:?}"),
}