pub enum Op {
Show 336 variants
Nop,
LoadInt(i64),
LoadFloat(f64),
LoadConst(u16),
LoadUndef,
Pop,
Dup,
Dup2,
Swap,
Rot,
ValueScalarContext,
GetScalar(u16),
GetScalarPlain(u16),
SetScalar(u16),
SetScalarPlain(u16),
DeclareScalar(u16),
DeclareScalarFrozen(u16),
DeclareScalarTyped(u16, u8),
DeclareScalarTypedFrozen(u16, u8),
DeclareStateScalar(u16),
DeclareStateArray(u16),
DeclareStateHash(u16),
GetArray(u16),
SetArray(u16),
DeclareArray(u16),
DeclareArrayFrozen(u16),
GetArrayElem(u16),
SetArrayElem(u16),
SetArrayElemKeep(u16),
PushArray(u16),
PopArray(u16),
ShiftArray(u16),
ArrayLen(u16),
ArraySlicePart(u16),
ArrayConcatTwo,
ExistsArrayElem(u16),
DeleteArrayElem(u16),
GetHash(u16),
SetHash(u16),
DeclareHash(u16),
DeclareHashFrozen(u16),
LocalDeclareScalar(u16),
LocalDeclareArray(u16),
LocalDeclareHash(u16),
LocalDeclareHashElement(u16),
LocalDeclareArrayElement(u16),
LocalDeclareTypeglob(u16, Option<u16>),
LocalDeclareTypeglobDynamic(Option<u16>),
GetHashElem(u16),
SetHashElem(u16),
SetHashElemKeep(u16),
DeleteHashElem(u16),
ExistsHashElem(u16),
DeleteArrowHashElem,
ExistsArrowHashElem,
ExistsArrowArrayElem,
DeleteArrowArrayElem,
HashKeys(u16),
HashValues(u16),
HashKeysScalar(u16),
HashValuesScalar(u16),
KeysFromValue,
KeysFromValueScalar,
ValuesFromValue,
ValuesFromValueScalar,
PushArrayDeref,
ArrayDerefLen,
PopArrayDeref,
ShiftArrayDeref,
UnshiftArrayDeref(u8),
SpliceArrayDeref(u8),
Add,
Sub,
Mul,
Div,
Mod,
Pow,
Negate,
Inc,
Dec,
Concat,
ArrayStringifyListSep,
StringRepeat,
ProcessCaseEscapes,
NumEq,
NumNe,
NumLt,
NumGt,
NumLe,
NumGe,
Spaceship,
StrEq,
StrNe,
StrLt,
StrGt,
StrLe,
StrGe,
StrCmp,
LogNot,
BitAnd,
BitOr,
BitXor,
BitNot,
Shl,
Shr,
Jump(usize),
JumpIfTrue(usize),
JumpIfFalse(usize),
JumpIfFalseKeep(usize),
JumpIfTrueKeep(usize),
JumpIfDefinedKeep(usize),
PreInc(u16),
PreDec(u16),
PostInc(u16),
PostDec(u16),
PreIncSlot(u8),
PreDecSlot(u8),
PostIncSlot(u8),
PostDecSlot(u8),
Call(u16, u8, u8),
CallStaticSubId(u16, u16, u8, u8),
Return,
ReturnValue,
BlockReturnValue,
BindSubClosure(u16),
PushFrame,
PopFrame,
Print(Option<u16>, u8),
Say(Option<u16>, u8),
CallBuiltin(u16, u8),
WantarrayPush(u8),
WantarrayPop,
MakeArray(u16),
HashSliceDeref(u16),
ArrowArraySlice(u16),
SetHashSliceDeref(u16),
SetHashSlice(u16, u16),
GetHashSlice(u16, u16),
HashSliceDerefCompound(u8, u16),
HashSliceDerefIncDec(u8, u16),
NamedHashSliceCompound(u8, u16, u16),
NamedHashSliceIncDec(u8, u16, u16),
NamedHashSlicePeekLast(u16, u16),
NamedHashSliceDropKeysKeepCur(u16),
SetNamedHashSliceLastKeep(u16, u16),
HashSliceDerefPeekLast(u16),
HashSliceDerefRollValUnderKeys(u16),
HashSliceDerefSetLastKeep(u16),
HashSliceDerefDropKeysKeepCur(u16),
SetArrowArraySlice(u16),
ArrowArraySliceCompound(u8, u16),
ArrowArraySliceIncDec(u8, u16),
ArrowArraySlicePeekLast(u16),
ArrowArraySliceDropKeysKeepCur(u16),
ArrowArraySliceRollValUnderSpecs(u16),
SetArrowArraySliceLastKeep(u16),
NamedArraySliceIncDec(u8, u16, u16),
NamedArraySliceCompound(u8, u16, u16),
NamedArraySlicePeekLast(u16, u16),
NamedArraySliceDropKeysKeepCur(u16),
NamedArraySliceRollValUnderSpecs(u16),
SetNamedArraySliceLastKeep(u16, u16),
SetNamedArraySlice(u16, u16),
BarewordRvalue(u16),
RuntimeErrorConst(u16),
MakeHash(u16),
Range,
RangeStep,
ScalarFlipFlop(u16, u8),
RegexFlipFlop(u16, u8, u16, u16, u16, u16),
RegexEofFlipFlop(u16, u8, u16, u16),
RegexFlipFlopExprRhs(u16, u8, u16, u16, u16),
RegexFlipFlopDotLineRhs(u16, u8, u16, u16, u16),
RegexMatch(u16, u16, bool, u16),
RegexSubst(u16, u16, u16, u16),
RegexTransliterate(u16, u16, u16, u16),
RegexMatchDyn(bool),
LoadRegex(u16, u16),
RegexBoolToScalar,
SetRegexPos,
SetScalarKeep(u16),
SetScalarKeepPlain(u16),
MapWithBlock(u16),
FlatMapWithBlock(u16),
GrepWithBlock(u16),
ForEachWithBlock(u16),
MapWithExpr(u16),
FlatMapWithExpr(u16),
GrepWithExpr(u16),
ChunkByWithBlock(u16),
ChunkByWithExpr(u16),
SortWithBlock(u16),
SortNoBlock,
SortWithCodeComparator(u8),
SortWithBlockFast(u8),
MapIntMul(i64),
GrepIntModEq(i64, i64),
PSortWithBlockFast(u8),
ReadIntoVar(u16),
ChompInPlace(u16),
ChopInPlace(u16),
SubstrFourArg(u16),
KeysExpr(u16),
ValuesExpr(u16),
KeysExprScalar(u16),
ValuesExprScalar(u16),
DeleteExpr(u16),
ExistsExpr(u16),
PushExpr(u16),
PopExpr(u16),
ShiftExpr(u16),
UnshiftExpr(u16),
SpliceExpr(u16),
ConcatAppend(u16),
ConcatAppendSlot(u8),
AddAssignSlotSlot(u8, u8),
SubAssignSlotSlot(u8, u8),
MulAssignSlotSlot(u8, u8),
SlotLtIntJumpIfFalse(u8, i32, usize),
AddAssignSlotSlotVoid(u8, u8),
PreIncSlotVoid(u8),
ConcatAppendSlotVoid(u8),
SlotIncLtIntJumpBack(u8, i32, usize),
AccumSumLoop(u8, u8, i32),
ConcatConstSlotLoop(u16, u8, u8, i32),
PushIntRangeToArrayLoop(u16, u8, i32),
SetHashIntTimesLoop(u16, u8, i32, i32),
AddHashElemPlainKeyToSlot(u8, u16, u16),
AddHashElemSlotKeyToSlot(u8, u8, u16),
SumHashValuesToSlot(u8, u16),
GetScalarSlot(u8),
SetScalarSlot(u8),
SetScalarSlotKeep(u8),
DeclareScalarSlot(u8, u16),
GetArg(u8),
ReverseListOp,
ReverseScalarOp,
RevListOp,
RevScalarOp,
StackArrayLen,
ListSliceToScalar,
PMapWithBlock(u16),
PFlatMapWithBlock(u16),
PMapsWithBlock(u16),
PFlatMapsWithBlock(u16),
PMapRemote {
block_idx: u16,
flat: u8,
},
Puniq,
PFirstWithBlock(u16),
PAnyWithBlock(u16),
PMapChunkedWithBlock(u16),
PGrepWithBlock(u16),
PGrepsWithBlock(u16),
PForWithBlock(u16),
PSortWithBlock(u16),
PSortNoBlockParallel,
ReduceWithBlock(u16),
PReduceWithBlock(u16),
PReduceInitWithBlock(u16),
PMapReduceWithBlocks(u16, u16),
PcacheWithBlock(u16),
Pselect {
n_rx: u8,
has_timeout: bool,
},
ParLines(u16),
ParWalk(u16),
Pwatch(u16),
FanWithBlock(u16),
FanWithBlockAuto(u16),
FanCapWithBlock(u16),
FanCapWithBlockAuto(u16),
EvalBlock(u16, u8),
TraceBlock(u16),
TimerBlock(u16),
BenchBlock(u16),
Given(u16),
EvalTimeout(u16),
AlgebraicMatch(u16),
AsyncBlock(u16),
Await,
LoadCurrentSub,
DeferBlock,
MakeScalarRef,
MakeScalarBindingRef(u16),
MakeArrayBindingRef(u16),
MakeHashBindingRef(u16),
MakeArrayRefAlias,
MakeHashRefAlias,
MakeArrayRef,
MakeHashRef,
MakeCodeRef(u16, u16),
LoadNamedSubRef(u16),
LoadDynamicSubRef,
LoadDynamicTypeglob,
CopyTypeglobSlots(u16, u16),
TypeglobAssignFromValue(u16),
TypeglobAssignFromValueDynamic,
CopyTypeglobSlotsDynamicLhs(u16),
SymbolicDeref(u8),
ArrowArray,
ArrowHash,
SetArrowHash,
SetArrowArray,
SetArrowArrayKeep,
SetArrowHashKeep,
ArrowArrayPostfix(u8),
ArrowHashPostfix(u8),
SetSymbolicScalarRef,
SetSymbolicScalarRefKeep,
SetSymbolicArrayRef,
SetSymbolicHashRef,
SetSymbolicTypeglobRef,
SymbolicScalarRefPostfix(u8),
ArrowCall(u8),
IndirectCall(u8, u8, u8),
MethodCall(u16, u8, u8),
MethodCallSuper(u16, u8, u8),
FileTestOp(u8),
TryPush {
catch_ip: usize,
finally_ip: Option<usize>,
after_ip: usize,
catch_var_idx: u16,
},
TryContinueNormal,
TryFinallyEnd,
CatchReceive(u16),
DeclareMySyncScalar(u16),
DeclareMySyncArray(u16),
DeclareMySyncHash(u16),
RuntimeSubDecl(u16),
Tie {
target_kind: u8,
name_idx: u16,
argc: u8,
},
FormatDecl(u16),
UseOverload(u16),
ScalarCompoundAssign {
name_idx: u16,
op: u8,
},
SetGlobalPhase(u8),
Halt,
EvalAstExpr(u16),
MapsWithBlock(u16),
MapsFlatMapWithBlock(u16),
MapsWithExpr(u16),
MapsFlatMapWithExpr(u16),
FilterWithBlock(u16),
FilterWithExpr(u16),
}Expand description
Stack-based bytecode instruction set for the stryke VM. Operands use u16 for pool indices (64k names/constants) and i32 for jumps.
Variants§
Nop
LoadInt(i64)
LoadFloat(f64)
LoadConst(u16)
LoadUndef
Pop
Dup
Dup2
Duplicate the top two stack values: [a, b] (b on top) → [a, b, a, b].
Swap
Swap the top two stack values (PerlValue).
Rot
Rotate the top three values upward (FORTH rot): [a, b, c] (c on top) → [b, c, a].
ValueScalarContext
Pop one value; push PerlValue::scalar_context of that value (Perl aggregate rules).
GetScalar(u16)
GetScalarPlain(u16)
Like GetScalar but reads scope.get_scalar only (no Perl special-variable dispatch).
SetScalar(u16)
SetScalarPlain(u16)
Like SetScalar but calls scope.set_scalar only (no special-variable dispatch).
DeclareScalar(u16)
DeclareScalarFrozen(u16)
Like DeclareScalar but the binding is immutable after initialization.
DeclareScalarTyped(u16, u8)
typed my $x : Type — u8 encodes crate::ast::PerlTypeName (0=Int,1=Str,2=Float).
DeclareScalarTypedFrozen(u16, u8)
frozen typed my $x : Type — immutable after initialization + type-checked.
DeclareStateScalar(u16)
state $x = EXPR — pop TOS as initializer on first call only.
On subsequent calls the persisted value is used as the local binding.
Key: (sub entry IP, name_idx) in VM’s state_vars table.
DeclareStateArray(u16)
state @arr = (...) — array variant.
DeclareStateHash(u16)
state %hash = (...) — hash variant.
GetArray(u16)
SetArray(u16)
DeclareArray(u16)
DeclareArrayFrozen(u16)
GetArrayElem(u16)
SetArrayElem(u16)
SetArrayElemKeep(u16)
Like Op::SetArrayElem but leaves the assigned value on the stack (e.g. $a[$i] //=).
PushArray(u16)
PopArray(u16)
ShiftArray(u16)
ArrayLen(u16)
ArraySlicePart(u16)
Pop index spec (scalar or array from Op::Range); push one PerlValue::array of elements
read from the named array. Used for @name[...] slice rvalues.
ArrayConcatTwo
Pop b, pop a (arrays); push concatenation a followed by b (Perl slice / list glue).
ExistsArrayElem(u16)
exists $a[$i] — stack: [index] → 0/1 (stash-qualified array name pool index).
DeleteArrayElem(u16)
delete $a[$i] — stack: [index] → deleted value (or undef).
GetHash(u16)
SetHash(u16)
DeclareHash(u16)
DeclareHashFrozen(u16)
LocalDeclareScalar(u16)
Dynamic local $x — save previous binding, assign TOS (same stack shape as DeclareScalar).
LocalDeclareArray(u16)
LocalDeclareHash(u16)
LocalDeclareHashElement(u16)
local $h{key} = val — stack: [value, key] (key on top), same as Op::SetHashElem.
LocalDeclareArrayElement(u16)
local $a[i] = val — stack: [value, index] (index on top), same as Op::SetArrayElem.
LocalDeclareTypeglob(u16, Option<u16>)
local *name or local *name = *other — second pool index is Some(rhs) when aliasing.
LocalDeclareTypeglobDynamic(Option<u16>)
local *{EXPR} / local *$x — LHS glob name string on stack (TOS); optional static *rhs pool index.
GetHashElem(u16)
SetHashElem(u16)
SetHashElemKeep(u16)
Like Op::SetHashElem but leaves the assigned value on the stack (e.g. $h{k} //=).
DeleteHashElem(u16)
ExistsHashElem(u16)
DeleteArrowHashElem
delete $href->{key} — stack: [container, key] (key on top) → deleted value.
ExistsArrowHashElem
exists $href->{key} — stack: [container, key] → 0/1.
ExistsArrowArrayElem
exists $aref->[$i] — stack: [container, index] (index on top, int-coerced).
DeleteArrowArrayElem
delete $aref->[$i] — stack: [container, index] → deleted value (or undef).
HashKeys(u16)
HashValues(u16)
HashKeysScalar(u16)
Scalar keys %h — push integer key count.
HashValuesScalar(u16)
Scalar values %h — push integer value count.
KeysFromValue
keys EXPR after operand evaluated in list context — stack: [value] → key list array.
KeysFromValueScalar
Scalar keys EXPR after operand — stack: [value] → key count.
ValuesFromValue
values EXPR after operand evaluated in list context — stack: [value] → values array.
ValuesFromValueScalar
Scalar values EXPR after operand — stack: [value] → value count.
PushArrayDeref
push @$aref, ITEM — stack: [aref, item] (item on top); mutates; pushes aref back.
ArrayDerefLen
After push @$aref, … — stack: [aref] → [len] (consumes aref).
PopArrayDeref
pop @$aref — stack: [aref] → popped value.
ShiftArrayDeref
shift @$aref — stack: [aref] → shifted value.
UnshiftArrayDeref(u8)
unshift @$aref, LIST — stack [aref, v1, …, vn] (vn on top); n extra values.
SpliceArrayDeref(u8)
splice @$aref, off, len, LIST — stack top: replacements, then len, off, aref (len may be undef).
Add
Sub
Mul
Div
Mod
Pow
Negate
Inc
inc EXPR — pop value, push value + 1 (integer if input is integer, else float).
Dec
dec EXPR — pop value, push value - 1.
Concat
ArrayStringifyListSep
Pop array (or value coerced with PerlValue::to_list), join element strings with
[Interpreter::list_separator] ($"), push one string. Used for @a in " / qq.
StringRepeat
ProcessCaseEscapes
Pop string, apply \U / \L / \u / \l / \Q / \E case escapes, push result.
NumEq
NumNe
NumLt
NumGt
NumLe
NumGe
Spaceship
StrEq
StrNe
StrLt
StrGt
StrLe
StrGe
StrCmp
LogNot
BitAnd
BitOr
BitXor
BitNot
Shl
Shr
Jump(usize)
JumpIfTrue(usize)
JumpIfFalse(usize)
JumpIfFalseKeep(usize)
Jump if TOS is falsy WITHOUT popping (for short-circuit &&)
JumpIfTrueKeep(usize)
Jump if TOS is truthy WITHOUT popping (for short-circuit ||)
JumpIfDefinedKeep(usize)
Jump if TOS is defined WITHOUT popping (for //)
PreInc(u16)
PreDec(u16)
PostInc(u16)
PostDec(u16)
PreIncSlot(u8)
Pre-increment on a frame slot entry (compiled my $x fast path).
PreDecSlot(u8)
PostIncSlot(u8)
PostDecSlot(u8)
Call(u16, u8, u8)
Call subroutine: name index, arg count, WantarrayCtx discriminant as u8
CallStaticSubId(u16, u16, u8, u8)
Like Op::Call but with a compile-time-resolved entry: sid indexes Chunk::static_sub_calls
(entry IP + stack-args); name_idx duplicates the stash pool index for closure restore / JIT
(same as in the table; kept in the opcode so JIT does not need the side table).
Return
ReturnValue
BlockReturnValue
End of a compiled map / grep / sort block body (empty block or last statement an expression).
Pops the synthetic call frame from crate::vm::VM::run_block_region and unwinds the
block-local scope (scope_push_hook per iteration, like crate::interpreter::Interpreter::exec_block);
not subroutine return and not a closure capture.
BindSubClosure(u16)
At runtime statement position: capture current lexicals into crate::value::PerlSub::closure_env
for a sub already registered in [Interpreter::subs] (see prepare_program_top_level).
PushFrame
PopFrame
Print(Option<u16>, u8)
print [HANDLE] LIST — None uses crate::interpreter::Interpreter::default_print_handle.
Say(Option<u16>, u8)
CallBuiltin(u16, u8)
Calls a registered built-in: (builtin_id, arg_count)
WantarrayPush(u8)
Save crate::interpreter::Interpreter::wantarray_kind and set from u8
([crate::interpreter::WantarrayCtx::as_byte]). Used for splice / similar where the
dynamic context must match the expression’s compile-time [WantarrayCtx] (e.g. print splice…).
WantarrayPop
Restore after Op::WantarrayPush.
MakeArray(u16)
HashSliceDeref(u16)
@$href{k1,k2} — stack: [container, key1, …, keyN] (TOS = last key); pops N+1 values; pushes array of slot values.
ArrowArraySlice(u16)
@$aref[i1,i2,...] — stack: [array_ref, spec1, …, specN] (TOS = last spec); each spec is a
scalar index or array of indices (list-context .. / qw/list). Pops N+1; pushes elements.
SetHashSliceDeref(u16)
@$href{k1,k2} = VALUE — stack: [value, container, key1, …, keyN] (TOS = last key); pops N+2 values.
SetHashSlice(u16, u16)
%name{k1,k2} = VALUE — stack: [value, key1, …, keyN] (TOS = last key); pops N+1. Pool: hash name, key count.
GetHashSlice(u16, u16)
@h{k1,k2} read — stack: [key1, …, keyN] (TOS = last key); pops N values; pushes array of slot values.
Each key value may be a scalar or array (from list-context range); arrays are flattened into individual keys.
Pool: hash name index, key-expression count.
HashSliceDerefCompound(u8, u16)
@$href{k1,k2} OP= VALUE — stack: [rhs, container, key1, …, keyN] (TOS = last key); pops N+2, pushes the new value.
u8 = [crate::compiler::scalar_compound_op_to_byte] encoding of the binop.
Perl 5 applies the op only to the last key’s element.
HashSliceDerefIncDec(u8, u16)
++@$href{k1,k2} / --... / @$href{k1,k2}++ / ...-- — stack: [container, key1, …, keyN];
pops N+1. Pre-forms push the new last-element value; post-forms push the old last value.
u8 encodes kind: 0=PreInc, 1=PreDec, 2=PostInc, 3=PostDec. Only the last key is updated.
NamedHashSliceCompound(u8, u16, u16)
@name{k1,k2} OP= rhs — stack: [rhs, key1, …, keyN] (TOS = last key); pops N+1, pushes the new value.
Pool: compound-op byte ([crate::compiler::scalar_compound_op_to_byte]), stash hash name, key-slot count.
Only the last flattened key is updated (same as Op::HashSliceDerefCompound).
NamedHashSliceIncDec(u8, u16, u16)
++@name{k1,k2} / --… / @name{k1,k2}++ / …-- — stack: [key1, …, keyN]; pops N.
u8 kind matches Op::HashSliceDerefIncDec. Only the last key is updated.
NamedHashSlicePeekLast(u16, u16)
Multi-key @h{k1,k2} //= / ||= / &&= — stack [key1, …, keyN] unchanged; pushes the last
flattened slot (Perl only tests that slot). Pool: hash name, key-slot count.
NamedHashSliceDropKeysKeepCur(u16)
Stack [key1, …, keyN, cur] — pop N key slots, keep cur (short-circuit path).
SetNamedHashSliceLastKeep(u16, u16)
Assign list RHS’s last element to the last flattened key; stack [val, key1, …, keyN] (TOS = last key). Pushes val.
HashSliceDerefPeekLast(u16)
Multi-key @$href{k1,k2} //= — stack [container, key1, …, keyN]; pushes last slice element (see Op::ArrowArraySlicePeekLast).
HashSliceDerefRollValUnderKeys(u16)
[container, key1, …, keyN, val] → [val, container, key1, …, keyN] for Op::HashSliceDerefSetLastKeep.
HashSliceDerefSetLastKeep(u16)
Assign to last flattened key only; stack [val, container, key1, …, keyN]. Pushes val.
HashSliceDerefDropKeysKeepCur(u16)
Stack [container, key1, …, keyN, cur] — drop container and keys; keep cur.
SetArrowArraySlice(u16)
@$aref[i1,i2,...] = LIST — stack: [value, aref, spec1, …, specN] (TOS = last spec);
pops N+2. Delegates to crate::interpreter::Interpreter::assign_arrow_array_slice.
ArrowArraySliceCompound(u8, u16)
@$aref[i1,i2,...] OP= rhs — stack: [rhs, aref, spec1, …, specN]; pops N+2, pushes new value.
u8 = [crate::compiler::scalar_compound_op_to_byte] encoding of the binop.
Perl 5 applies the op only to the last index. Delegates to crate::interpreter::Interpreter::compound_assign_arrow_array_slice.
ArrowArraySliceIncDec(u8, u16)
++@$aref[i1,i2,...] / --... / ...++ / ...-- — stack: [aref, spec1, …, specN];
pops N+1. Pre-forms push the new last-element value; post-forms push the old last value.
u8 kind matches Op::HashSliceDerefIncDec. Only the last index is updated. Delegates to
crate::interpreter::Interpreter::arrow_array_slice_inc_dec.
ArrowArraySlicePeekLast(u16)
Read the element at the last flattened index of @$aref[spec1,…] without popping aref
or specs. Stack: [aref, spec1, …, specN] (TOS = last spec) → same plus pushed scalar.
Used for @$r[i,j] //= / ||= / &&= short-circuit tests (Perl only tests the last slot).
ArrowArraySliceDropKeysKeepCur(u16)
Stack: [aref, spec1, …, specN, cur] — pop slice keys and container, keep cur (short-circuit
result). u16 = number of spec slots (same as Op::ArrowArraySlice).
ArrowArraySliceRollValUnderSpecs(u16)
Reorder [aref, spec1, …, specN, val] → [val, aref, spec1, …, specN] for
Op::SetArrowArraySliceLastKeep.
SetArrowArraySliceLastKeep(u16)
Assign val to the last flattened index only; stack [val, aref, spec1, …, specN]
(TOS = last spec). Pushes val (like Op::SetArrowArrayKeep).
NamedArraySliceIncDec(u8, u16, u16)
Like Op::ArrowArraySliceIncDec but for a named stash array (@a[i1,i2,...]).
Stack: [spec1, …, specN] (TOS = last spec). u16 = name pool index (stash-qualified).
Delegates to crate::interpreter::Interpreter::named_array_slice_inc_dec.
NamedArraySliceCompound(u8, u16, u16)
@name[spec1,…] OP= rhs — stack [rhs, spec1, …, specN] (TOS = last spec); pops N+1.
Only the last flattened index is updated (same as Op::ArrowArraySliceCompound).
NamedArraySlicePeekLast(u16, u16)
Read the last flattened slot of @name[spec1,…] without popping specs. Stack:
[spec1, …, specN] → same plus pushed scalar. u16 pairs: name pool index, spec count.
NamedArraySliceDropKeysKeepCur(u16)
Stack: [spec1, …, specN, cur] — pop specs, keep cur (short-circuit). u16 = spec count.
NamedArraySliceRollValUnderSpecs(u16)
[spec1, …, specN, val] → [val, spec1, …, specN] for Op::SetNamedArraySliceLastKeep.
SetNamedArraySliceLastKeep(u16, u16)
Assign to the last index only; stack [val, spec1, …, specN]. Pushes val.
SetNamedArraySlice(u16, u16)
@name[spec1,…] = LIST — stack [value, spec1, …, specN] (TOS = last spec); pops N+1.
Element-wise like Op::SetArrowArraySlice. Pool indices: stash-qualified array name, spec count.
BarewordRvalue(u16)
BAREWORD as an rvalue — at run time, look up a subroutine with this name; if found,
call it with no args (nullary), otherwise push the name as a string (Perl’s bareword-as-
stringifies behavior). u16 is a name-pool index. Delegates to
crate::interpreter::Interpreter::resolve_bareword_rvalue.
RuntimeErrorConst(u16)
Throw PerlError::runtime with the message at constant pool index u16. Used by the compiler
to hard-reject constructs whose only valid response is a runtime error
(e.g. ++@$r, %{...}--) without AST fallback.
MakeHash(u16)
Range
RangeStep
ScalarFlipFlop(u16, u8)
Scalar .. / ... flip-flop (numeric bounds vs $. — [Interpreter::scalar_flipflop_dot_line]).
Stack: [from, to] (ints); pushes 1 or 0. u16 indexes flip-flop slots; u8 is 1 for ...
(exclusive: right bound only after $. is strictly past the line where the left bound matched).
RegexFlipFlop(u16, u8, u16, u16, u16, u16)
Regex .. / ... flip-flop: both bounds are pattern literals; tests use $_ and $. like Perl
(Interpreter::regex_flip_flop_eval). Operand order: slot, exclusive, left pattern, left flags,
right pattern, right flags (constant pool indices). No stack operands; pushes 0/1.
RegexEofFlipFlop(u16, u8, u16, u16)
Regex .. / ... flip-flop with eof as the right operand (no arguments). Left bound matches $_;
right bound is [Interpreter::eof_without_arg_is_true] (Perl eof in -n/-p). Operand order:
slot, exclusive, left pattern, left flags.
RegexFlipFlopExprRhs(u16, u8, u16, u16, u16)
Regex .. / ... with a non-literal right operand (e.g. m/a/ ... (m/b/ or m/c/)). Left bound is
pattern + flags; right is evaluated in boolean context each line (pool index into
Chunk::regex_flip_flop_rhs_expr_entries / bytecode ranges). Operand order: slot, exclusive,
left pattern, left flags, rhs expr index.
RegexFlipFlopDotLineRhs(u16, u8, u16, u16, u16)
Regex .. / ... with a numeric right operand (Perl: right bound is [Interpreter::scalar_flipflop_dot_line]
vs literal line). Constant pool index holds the RHS line as PerlValue::integer. Operand order:
slot, exclusive, left pattern, left flags, rhs line constant index.
RegexMatch(u16, u16, bool, u16)
Match: pattern_const_idx, flags_const_idx, scalar_g, pos_key_name_idx (u16::MAX = $_);
stack: string operand → result
RegexSubst(u16, u16, u16, u16)
Substitution s///: pattern, replacement, flags constant indices; lvalue index into chunk.
stack: string (subject from LHS expr) → replacement count
RegexTransliterate(u16, u16, u16, u16)
Transliterate tr///: from, to, flags constant indices; lvalue index into chunk.
stack: string → transliteration count
RegexMatchDyn(bool)
Dynamic =~ / !~: pattern from RHS, subject from LHS; empty flags.
stack: [subject, pattern] (pattern on top) → 0/1; true = negate (!~).
LoadRegex(u16, u16)
Regex literal as a value (qr/PAT/FLAGS) — pattern and flags string pool indices.
RegexBoolToScalar
After [RegexMatchDyn] for bare m// in && / ||: pop 0/1; push "" or 1 (Perl scalar).
SetRegexPos
pos $var = EXPR / pos = EXPR (implicit $_). Stack: [value, key] (key string on top).
SetScalarKeep(u16)
SetScalar that also leaves the value on the stack (for chained assignment)
SetScalarKeepPlain(u16)
SetScalarKeep for non-special scalars (see SetScalarPlain).
MapWithBlock(u16)
map { BLOCK } @list — block_idx; stack: [list] → [mapped]
FlatMapWithBlock(u16)
flat_map { BLOCK } @list — like Op::MapWithBlock but peels one ARRAY ref per iteration (PerlValue::map_flatten_outputs)
GrepWithBlock(u16)
grep { BLOCK } @list — block_idx; stack: [list] → [filtered]
ForEachWithBlock(u16)
each { BLOCK } @list — block_idx; stack: [list] → [count]
MapWithExpr(u16)
map EXPR, LIST — index into Chunk::map_expr_entries / Chunk::map_expr_bytecode_ranges;
stack: [list] → [mapped]
FlatMapWithExpr(u16)
flat_map EXPR, LIST — same pools as Op::MapWithExpr; stack: [list] → [mapped]
GrepWithExpr(u16)
grep EXPR, LIST — index into Chunk::grep_expr_entries / Chunk::grep_expr_bytecode_ranges;
stack: [list] → [filtered]
ChunkByWithBlock(u16)
group_by { BLOCK } LIST / chunk_by { BLOCK } LIST — consecutive runs where the block’s
return value stringifies the same as the previous (str_eq); stack: [list] → [arrayrefs]
ChunkByWithExpr(u16)
group_by EXPR, LIST / chunk_by EXPR, LIST — same as Op::ChunkByWithBlock but key from
EXPR with $_ set each iteration; uses Chunk::map_expr_entries.
SortWithBlock(u16)
sort { BLOCK } @list — block_idx; stack: [list] → [sorted]
SortNoBlock
sort @list (no block) — stack: [list] → [sorted]
SortWithCodeComparator(u8)
sort $coderef LIST — stack: [list, coderef] (coderef on top); u8 = wantarray for comparator calls.
SortWithBlockFast(u8)
{ $a <=> $b } (0), { $a cmp $b } (1), { $b <=> $a } (2), { $b cmp $a } (3)
MapIntMul(i64)
map { $_ * k } with integer k — stack: [list] → [mapped]
GrepIntModEq(i64, i64)
grep { $_ % m == r } with integer m (non-zero), r — stack: [list] → [filtered]
PSortWithBlockFast(u8)
Parallel sort, same fast modes as Op::SortWithBlockFast.
ReadIntoVar(u16)
read(FH, $buf, LEN [, OFFSET]) — reads into a named variable.
Stack: [filehandle, length] (offset optional via ReadIntoVarOffset).
Writes result into $name[u16], pushes bytes-read count (or undef on error).
ChompInPlace(u16)
chomp on assignable expr: stack has value → chomped count; uses chunk.lvalues[idx].
ChopInPlace(u16)
chop on assignable expr: stack has value → chopped char; uses chunk.lvalues[idx].
SubstrFourArg(u16)
Four-arg substr LHS, OFF, LEN, REPL — index into Chunk::substr_four_arg_entries; stack: [] → extracted slice string
KeysExpr(u16)
keys EXPR when EXPR is not a bare %h — Chunk::keys_expr_entries /
Chunk::keys_expr_bytecode_ranges
ValuesExpr(u16)
values EXPR when not a bare %h — Chunk::values_expr_entries /
Chunk::values_expr_bytecode_ranges
KeysExprScalar(u16)
Scalar keys EXPR (dynamic) — same pools as Op::KeysExpr.
ValuesExprScalar(u16)
Scalar values EXPR — same pools as Op::ValuesExpr.
DeleteExpr(u16)
delete EXPR when not a fast %h{...} — index into Chunk::delete_expr_entries
ExistsExpr(u16)
exists EXPR when not a fast %h{...} — index into Chunk::exists_expr_entries
PushExpr(u16)
push EXPR, ... when not a bare @name — Chunk::push_expr_entries
PopExpr(u16)
pop EXPR when not a bare @name — Chunk::pop_expr_entries
ShiftExpr(u16)
shift EXPR when not a bare @name — Chunk::shift_expr_entries
UnshiftExpr(u16)
unshift EXPR, ... when not a bare @name — Chunk::unshift_expr_entries
SpliceExpr(u16)
splice EXPR, ... when not a bare @name — Chunk::splice_expr_entries
ConcatAppend(u16)
$var .= expr — append to scalar string in-place without cloning.
Stack: [value_to_append] → [resulting_string]. u16 = name pool index of target scalar.
ConcatAppendSlot(u8)
Slot-indexed $var .= expr — avoids frame walking and string comparison.
Stack: [value_to_append] → [resulting_string]. u8 = slot index.
AddAssignSlotSlot(u8, u8)
Fused $slot_a += $slot_b — no stack traffic. Pushes result.
SubAssignSlotSlot(u8, u8)
Fused $slot_a -= $slot_b — no stack traffic. Pushes result.
MulAssignSlotSlot(u8, u8)
Fused $slot_a *= $slot_b — no stack traffic. Pushes result.
SlotLtIntJumpIfFalse(u8, i32, usize)
Fused if ($slot < INT) goto target — replaces GetScalarSlot + LoadInt + NumLt + JumpIfFalse.
(slot, i32_limit, jump_target)
AddAssignSlotSlotVoid(u8, u8)
Void-context $slot_a += $slot_b — no stack push. Replaces AddAssignSlotSlot + Pop.
PreIncSlotVoid(u8)
Void-context ++$slot — no stack push. Replaces PreIncSlot + Pop.
ConcatAppendSlotVoid(u8)
Void-context $slot .= expr — no stack push. Replaces ConcatAppendSlot + Pop.
SlotIncLtIntJumpBack(u8, i32, usize)
Fused loop backedge: $slot += 1; if $slot < limit jump body_target; else fall through.
Replaces the trailing PreIncSlotVoid(s) + Jump(top) of a C-style for (my $i=0; $i<N; $i=$i+1)
loop whose top op is a SlotLtIntJumpIfFalse(s, limit, exit). The initial iteration still
goes through the top check; this op handles all subsequent iterations in a single dispatch,
halving the number of ops per loop trip for the bench_loop/bench_string/bench_array shape.
(slot, i32_limit, body_target)
AccumSumLoop(u8, u8, i32)
Fused accumulator loop: while $i < limit { $sum += $i; $i += 1 } — runs the entire
remaining counted-sum loop in native Rust, eliminating op dispatch per iteration.
Fused when a for (my $i = a; $i < N; $i = $i + 1) { $sum += $i } body compiles down to
exactly AddAssignSlotSlotVoid(sum, i) + SlotIncLtIntJumpBack(i, limit, body_target) with
body_target pointing at the AddAssign — i.e. the body is 1 Perl statement. Both slots are
left as integers on exit (same coercion as AddAssignSlotSlotVoid + PreIncSlotVoid).
(sum_slot, i_slot, i32_limit)
ConcatConstSlotLoop(u16, u8, u8, i32)
Fused string-append counted loop: while $i < limit { $s .= CONST; $i += 1 } — extends
the String buffer in place once and pushes the literal (limit - i) times in a tight
Rust loop, with Arc::get_mut → reserve → push_str. Falls back to the regular op
sequence if the slot is not a uniquely-owned heap String.
Fused when the loop body is exactly LoadConst(c) + ConcatAppendSlotVoid(s) + SlotIncLtIntJumpBack(i, limit, body_target) with body_target pointing at the LoadConst.
(const_idx, s_slot, i_slot, i32_limit)
PushIntRangeToArrayLoop(u16, u8, i32)
Fused array-push counted loop: while $i < limit { push @a, $i; $i += 1 } — reserves the
target Vec once and pushes PerlValue::integer(i) in a tight Rust loop. Emitted when
the loop body is exactly GetScalarSlot(i) + PushArray(arr) + ArrayLen(arr) + Pop + SlotIncLtIntJumpBack(i, limit, body_target) with body_target pointing at the
GetScalarSlot (i.e. the body is one push statement whose return is discarded).
(arr_name_idx, i_slot, i32_limit)
SetHashIntTimesLoop(u16, u8, i32, i32)
Fused hash-insert counted loop: while $i < limit { $h{$i} = $i * k; $i += 1 } — runs the
entire insert loop natively, reserving hash capacity once and writing (stringified i, i*k)
pairs in tight Rust. Emitted when the body is exactly
GetScalarSlot(i) + LoadInt(k) + Mul + GetScalarSlot(i) + SetHashElem(h) + Pop + SlotIncLtIntJumpBack(i, limit, body_target) with body_target at the first GetScalarSlot.
(hash_name_idx, i_slot, i32_multiplier, i32_limit)
AddHashElemPlainKeyToSlot(u8, u16, u16)
Fused $sum += $h{$k} body op for the inner loop of for my $k (keys %h) { $sum += $h{$k} }.
Replaces the 6-op sequence GetScalarSlot(sum) + GetScalarPlain(k) + GetHashElem(h) + Add + SetScalarSlotKeep(sum) + Pop with a single dispatch that reads the hash element directly
into the slot without going through the VM stack. (sum_slot, k_name_idx, h_name_idx)
AddHashElemSlotKeyToSlot(u8, u8, u16)
Like Op::AddHashElemPlainKeyToSlot but the key variable lives in a slot (for my $k
in slot-mode foreach). Pure slot read + hash lookup + slot write with zero VM stack traffic.
(sum_slot, k_slot, h_name_idx)
SumHashValuesToSlot(u8, u16)
Fused for my $k (keys %h) { $sum += $h{$k} } — walks hash.values() in a tight native
loop, accumulating integer or float sums directly into sum_slot. Emitted by the
bytecode-level peephole when the foreach shape + AddHashElemSlotKeyToSlot body + slot
counter/var declarations are detected. h_name_idx is the source hash’s name pool index.
(sum_slot, h_name_idx)
GetScalarSlot(u8)
Read scalar from current frame’s slot array. u8 = slot index.
SetScalarSlot(u8)
Write scalar to current frame’s slot array (pop, discard). u8 = slot index.
SetScalarSlotKeep(u8)
Write scalar to current frame’s slot array (pop, keep on stack). u8 = slot index.
DeclareScalarSlot(u8, u16)
Declare + initialize scalar in current frame’s slot array. u8 = slot index; u16 = name pool index (bare name) for closure capture.
GetArg(u8)
Read argument from caller’s stack region: push stack[call_frame.stack_base + idx]. Avoids @_ allocation + string-based shift for compiled sub argument passing.
ReverseListOp
reverse in list context — stack: [list] → [reversed list]
ReverseScalarOp
scalar reverse — stack: [list] → concatenated string with chars reversed (Perl).
RevListOp
rev in list context — reverse list, preserve iterators lazily.
RevScalarOp
rev in scalar context — char-reverse string.
StackArrayLen
Pop TOS (array/list), push to_list().len() as integer (Perl scalar on map/grep result).
ListSliceToScalar
Pop list-slice result array; push last element (Perl scalar (LIST)[i,...]).
PMapWithBlock(u16)
pmap { BLOCK } @list — block_idx; stack: [progress_flag, list] → [mapped] (progress_flag is 0/1)
PFlatMapWithBlock(u16)
pflat_map { BLOCK } @list — flatten array results; output in input order; stack same as Op::PMapWithBlock
PMapsWithBlock(u16)
pmaps { BLOCK } LIST — streaming parallel map; stack: [list] → [iterator]
PFlatMapsWithBlock(u16)
pflat_maps { BLOCK } LIST — streaming parallel flat map; stack: [list] → [iterator]
PMapRemote
pmap_on / pflat_map_on over SSH — stack: [progress_flag, list, cluster] → [mapped]; flat = 1 for flatten
Puniq
puniq LIST — hash-partition parallel distinct (first occurrence order); stack: [progress_flag, list] → [array]
PFirstWithBlock(u16)
pfirst { BLOCK } LIST — short-circuit parallel; stack: [progress_flag, list] → value or undef
PAnyWithBlock(u16)
pany { BLOCK } LIST — short-circuit parallel; stack: [progress_flag, list] → 0/1
PMapChunkedWithBlock(u16)
pmap_chunked N { BLOCK } @list — block_idx; stack: [progress_flag, chunk_n, list] → [mapped]
PGrepWithBlock(u16)
pgrep { BLOCK } @list — block_idx; stack: [progress_flag, list] → [filtered]
PGrepsWithBlock(u16)
pgreps { BLOCK } LIST — streaming parallel grep; stack: [list] → [iterator]
PForWithBlock(u16)
pfor { BLOCK } @list — block_idx; stack: [progress_flag, list] → []
PSortWithBlock(u16)
psort { BLOCK } @list — block_idx; stack: [progress_flag, list] → [sorted]
PSortNoBlockParallel
psort @list (no block) — stack: [progress_flag, list] → [sorted]
ReduceWithBlock(u16)
reduce { BLOCK } @list — block_idx; stack: [list] → [accumulator]
PReduceWithBlock(u16)
preduce { BLOCK } @list — block_idx; stack: [progress_flag, list] → [accumulator]
PReduceInitWithBlock(u16)
preduce_init EXPR, { BLOCK } @list — block_idx; stack: [progress_flag, list, init] → [accumulator]
PMapReduceWithBlocks(u16, u16)
pmap_reduce { MAP } { REDUCE } @list — map and reduce block indices; stack: [progress_flag, list] → [scalar]
PcacheWithBlock(u16)
pcache { BLOCK } @list — block_idx; stack: [progress_flag, list] → [array]
Pselect
pselect($rx1, ... [, timeout => SECS]) — stack: [rx0, …, rx_{n-1}] with optional timeout on top
ParLines(u16)
par_lines PATH, fn { } [, progress => EXPR] — index into Chunk::par_lines_entries; stack: [] → undef
ParWalk(u16)
par_walk PATH, fn { } [, progress => EXPR] — index into Chunk::par_walk_entries; stack: [] → undef
Pwatch(u16)
pwatch GLOB, fn { } — index into Chunk::pwatch_entries; stack: [] → result
FanWithBlock(u16)
fan N { BLOCK } — block_idx; stack: [progress_flag, count] (progress_flag is 0/1)
FanWithBlockAuto(u16)
fan { BLOCK } — block_idx; stack: [progress_flag]; COUNT = rayon pool size (stryke -j)
FanCapWithBlock(u16)
fan_cap N { BLOCK } — like fan; stack: [progress_flag, count] → array of block return values
FanCapWithBlockAuto(u16)
fan_cap { BLOCK } — like fan; stack: [progress_flag] → array
EvalBlock(u16, u8)
do { BLOCK } — block_idx + wantarray byte ([crate::interpreter::WantarrayCtx::as_byte]);
stack: [] → result
TraceBlock(u16)
trace { BLOCK } — block_idx; stack: [] → block value (stderr tracing for mysync mutations)
TimerBlock(u16)
timer { BLOCK } — block_idx; stack: [] → elapsed ms as float
BenchBlock(u16)
bench { BLOCK } N — block_idx; stack: [iterations] → benchmark summary string
Given(u16)
given (EXPR) { when ... default ... } — Chunk::given_entries /
Chunk::given_topic_bytecode_ranges; stack: [] → topic result
EvalTimeout(u16)
eval_timeout SECS { ... } — index into Chunk::eval_timeout_entries /
Chunk::eval_timeout_expr_bytecode_ranges; stack: [] → block value
AlgebraicMatch(u16)
Algebraic match (SUBJECT) { ... } — Chunk::algebraic_match_entries /
Chunk::algebraic_match_subject_bytecode_ranges; stack: [] → arm value
AsyncBlock(u16)
async { BLOCK } / spawn { BLOCK } — block_idx; stack: [] → AsyncTask
Await
await EXPR — stack: [value] → result
LoadCurrentSub
__SUB__ — push reference to currently executing sub (for anonymous recursion).
DeferBlock
defer { BLOCK } — register a block to run when the current scope exits.
Stack: [coderef] → []. The coderef is pushed to the frame’s defer list.
MakeScalarRef
Make a scalar reference from TOS (copies value into a new RwLock).
MakeScalarBindingRef(u16)
\$name when name is a plain scalar variable — ref aliases the live binding (same as tree scalar_binding_ref).
MakeArrayBindingRef(u16)
\@name — ref aliases the live array in scope (name pool index, stash-qualified like Op::GetArray).
MakeHashBindingRef(u16)
\%name — ref aliases the live hash in scope.
MakeArrayRefAlias
\@{ EXPR } after EXPR is on the stack — ARRAY ref aliasing the same storage as Perl (ref to existing ref or package array).
MakeHashRefAlias
\%{ EXPR } — HASH ref alias (same semantics as Op::MakeArrayRefAlias for hashes).
MakeArrayRef
Make an array reference from TOS (which should be an Array)
MakeHashRef
Make a hash reference from TOS (which should be a Hash)
MakeCodeRef(u16, u16)
Make an anonymous sub from a block — block_idx; stack: [] → CodeRef
Anonymous sub / coderef: block pool index + Chunk::code_ref_sigs index (may be empty vec).
LoadNamedSubRef(u16)
Push a code reference to a named sub (\&foo) — name pool index; resolves at run time.
LoadDynamicSubRef
\&{ EXPR } — stack: [sub name string] → code ref (resolves at run time).
LoadDynamicTypeglob
*{ EXPR } — stack: [stash / glob name string] → resolved handle string (IO alias map + identity).
CopyTypeglobSlots(u16, u16)
*lhs = *rhs — copy stash slots (sub, scalar, array, hash, IO alias); name pool indices for both sides.
TypeglobAssignFromValue(u16)
*name = $coderef — stack: pop value, install subroutine in typeglob, push value back (assignment result).
TypeglobAssignFromValueDynamic
*{LHS} = $coderef — stack: pop value, pop LHS glob name string, install sub, push value back.
CopyTypeglobSlotsDynamicLhs(u16)
*{LHS} = *rhs — stack: pop LHS glob name string; RHS name is pool index; copies stash like Op::CopyTypeglobSlots.
SymbolicDeref(u8)
Symbolic deref ($$r, @{...}, %{...}, *{...}): stack: [ref or name value] → result.
Byte: 0 = crate::ast::Sigil::Scalar, 1 = Array, 2 = Hash, 3 = Typeglob.
ArrowArray
Dereference arrow: ->[] — stack: [ref, index] → value
ArrowHash
Dereference arrow: ->{} — stack: [ref, key] → value
SetArrowHash
Assign to ->{}: stack: [value, ref, key] (key on top) — consumes three values.
SetArrowArray
Assign to ->[]: stack: [value, ref, index] (index on top) — consumes three values.
SetArrowArrayKeep
Like Op::SetArrowArray but leaves the assigned value on the stack (for ++$aref->[$i] value).
SetArrowHashKeep
Like Op::SetArrowHash but leaves the assigned value on the stack (for ++$href->{k} value).
ArrowArrayPostfix(u8)
Postfix ++ / -- on ->[]: stack [ref, index] (index on top) → old value; mutates slot.
Byte: 0 = increment, 1 = decrement.
ArrowHashPostfix(u8)
Postfix ++ / -- on ->{}: stack [ref, key] (key on top) → old value; mutates slot.
Byte: 0 = increment, 1 = decrement.
SetSymbolicScalarRef
$$r = $val — stack: [value, ref] (ref on top).
SetSymbolicScalarRefKeep
Like Op::SetSymbolicScalarRef but leaves the assigned value on the stack.
SetSymbolicArrayRef
@{ EXPR } = LIST — stack: [list value, ref-or-name] (top = ref / package name); delegates to
Interpreter::assign_symbolic_array_ref_deref.
SetSymbolicHashRef
%{ EXPR } = LIST — stack: [list value, ref-or-name]; pairs from list like %h = (k => v, …).
SetSymbolicTypeglobRef
*{ EXPR } = RHS — stack: [value, ref-or-name] (top = symbolic glob name); coderef install or *lhs = *rhs copy.
SymbolicScalarRefPostfix(u8)
Postfix ++ / -- on symbolic scalar ref ($$r); stack [ref] → old value. Byte: 0 = increment, 1 = decrement.
ArrowCall(u8)
Dereference arrow: ->() — stack: [ref, args_array] → value
$cr->(...) — wantarray byte (see VM WantarrayCtx threading on Call / MethodCall).
IndirectCall(u8, u8, u8)
Indirect call $coderef(ARG...) / &$coderef(ARG...) — stack (bottom→top): target, then
argc argument values (first arg pushed first). Third byte: 1 = ignore stack args and use
caller @_ (argc must be 0).
MethodCall(u16, u8, u8)
Method call: stack: [object, args…] → result; name_idx, argc, wantarray
MethodCallSuper(u16, u8, u8)
Like Op::MethodCall but uses SUPER / C3 parent chain (see interpreter method resolution for SUPER).
FileTestOp(u8)
File test: -e, -f, -d, etc. — test char; stack: [path] → 0/1
TryPush
Push a [crate::vm::TryFrame]; catch_ip / after_ip patched via Chunk::patch_try_push_catch
/ Chunk::patch_try_push_after; finally_ip via Chunk::patch_try_push_finally.
TryContinueNormal
Normal completion from try or catch body (jump to finally or merge).
TryFinallyEnd
End of finally block: pop try frame and jump to after_ip.
CatchReceive(u16)
Enter catch: consume crate::vm::VM::pending_catch_error, pop try scope, push catch scope, bind $var.
DeclareMySyncScalar(u16)
Stack: [init] → []. Declares ${name} as PerlValue::atomic (or deque/heap unwrapped).
DeclareMySyncArray(u16)
Stack: [init_list] → []. Declares @name as atomic array.
DeclareMySyncHash(u16)
Stack: [init_list] → []. Declares %name as atomic hash.
RuntimeSubDecl(u16)
Register RuntimeSubDecl at index (nested sub, including inside BEGIN).
Tie
tie $x | @arr | %h, 'Class', ... — stack bottom = class expr, then user args; argc = 1 + args.len().
target_kind: 0 = scalar (TIESCALAR), 1 = array (TIEARRAY), 2 = hash (TIEHASH). name_idx = bare name.
FormatDecl(u16)
format NAME = … — index into Chunk::format_decls; installs into current package at run time.
UseOverload(u16)
use overload 'op' => 'method', … — index into Chunk::use_overload_entries.
ScalarCompoundAssign
Scalar $x OP= $rhs — uses [Scope::atomic_mutate] so mysync scalars are RMW-safe.
Stack: [rhs] → [result]. op byte is from [crate::compiler::scalar_compound_op_to_byte].
SetGlobalPhase(u8)
Halt
EvalAstExpr(u16)
Delegate an AST expression to Interpreter::eval_expr_ctx at runtime.
Operand is an index into Chunk::ast_eval_exprs.
MapsWithBlock(u16)
maps { BLOCK } LIST — stack: [list] → lazy iterator (pull-based; stryke extension).
MapsFlatMapWithBlock(u16)
flat_maps { BLOCK } LIST — like Op::MapsWithBlock with flat_map-style flattening.
MapsWithExpr(u16)
maps EXPR, LIST — index into Chunk::map_expr_entries; stack: [list] → iterator.
MapsFlatMapWithExpr(u16)
flat_maps EXPR, LIST — same pools as Op::MapsWithExpr.
FilterWithBlock(u16)
filter / fi { BLOCK } LIST — stack: [list] → lazy iterator (stryke; grep remains eager).
FilterWithExpr(u16)
filter / fi EXPR, LIST — index into Chunk::grep_expr_entries; stack: [list] → iterator.
Trait Implementations§
Source§impl<'de> Deserialize<'de> for Op
impl<'de> Deserialize<'de> for Op
Source§fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
fn deserialize<__D>(__deserializer: __D) -> Result<Self, __D::Error>where
__D: Deserializer<'de>,
impl StructuralPartialEq for Op
Auto Trait Implementations§
impl Freeze for Op
impl RefUnwindSafe for Op
impl Send for Op
impl Sync for Op
impl Unpin for Op
impl UnsafeUnpin for Op
impl UnwindSafe for Op
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<F, T> IntoSample<T> for Fwhere
T: FromSample<F>,
impl<F, T> IntoSample<T> for Fwhere
T: FromSample<F>,
fn into_sample(self) -> T
Source§impl<T> Pointable for T
impl<T> Pointable for T
Source§impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
impl<SS, SP> SupersetOf<SS> for SPwhere
SS: SubsetOf<SP>,
Source§fn to_subset(&self) -> Option<SS>
fn to_subset(&self) -> Option<SS>
self from the equivalent element of its
superset. Read moreSource§fn is_in_subset(&self) -> bool
fn is_in_subset(&self) -> bool
self is actually part of its subset T (and can be converted to it).Source§fn to_subset_unchecked(&self) -> SS
fn to_subset_unchecked(&self) -> SS
self.to_subset but without any property checks. Always succeeds.Source§fn from_subset(element: &SS) -> SP
fn from_subset(element: &SS) -> SP
self to the equivalent element of its superset.Source§impl<U, T> ToOwnedObj<U> for Twhere
U: FromObjRef<T>,
impl<U, T> ToOwnedObj<U> for Twhere
U: FromObjRef<T>,
Source§fn to_owned_obj(&self, data: FontData<'_>) -> U
fn to_owned_obj(&self, data: FontData<'_>) -> U
T, using the provided data to resolve any offsets.