Skip to main content

Scope

Struct Scope 

Source
pub struct Scope { /* private fields */ }
Expand description

Manages lexical scoping with a stack of frames. Innermost frame is last in the vector.

Implementations§

Source§

impl Scope

Source

pub fn new() -> Self

Source

pub fn set_parallel_guard(&mut self, enabled: bool)

Enable Self::parallel_guard for parallel worker interpreters (pmap, fan, …).

Source

pub fn parallel_guard(&self) -> bool

Source

pub fn depth(&self) -> usize

Source

pub fn pop_to_depth(&mut self, target_depth: usize)

Pop frames until we’re at target_depth. Used by VM ReturnValue to cleanly unwind through if/while/for blocks on return.

Source

pub fn push_frame(&mut self)

Source

pub fn get_scalar_slot(&self, slot: u8) -> PerlValue

Read scalar from slot — innermost binding for slot wins (same index can exist on nested frames; padding entries without [Frame::owns_scalar_slot_index] do not shadow outers).

Source

pub fn set_scalar_slot(&mut self, slot: u8, val: PerlValue)

Write scalar to slot — innermost binding for slot wins (see Self::get_scalar_slot).

Source

pub fn set_scalar_slot_checked( &mut self, slot: u8, val: PerlValue, slot_name: Option<&str>, ) -> Result<(), PerlError>

Like [set_scalar_slot] but respects the parallel guard — returns Err when assigning to a slot that belongs to an outer frame inside a parallel block. slot_name is resolved from the bytecode’s name table by the caller when available.

Source

pub fn declare_scalar_slot( &mut self, slot: u8, val: PerlValue, name: Option<&str>, )

Declare + initialize scalar in the current frame’s slot array. name (bare identifier, e.g. x for $x) is stored for Scope::capture when the binding is slot-only (no duplicate frame.scalars row).

Source

pub fn scalar_slot_concat_repeat_inplace( &mut self, slot: u8, rhs: &str, n: usize, ) -> bool

Slot-indexed .= — avoids frame walking and string comparison on every iteration.

Returns a PerlValue::shallow_clone (Arc::clone) of the stored value rather than a full Clone, which would deep-copy the entire String payload and turn a $s .= "x" loop into O(N²) memcpy. Repeated $slot .= rhs fused-loop fast path: locates the slot’s frame once, tries try_concat_repeat_inplace (unique heap-String → single reserve+push_str burst), and returns true on success. Returns false when the slot is not a uniquely-held String so the caller can fall back to the per-iteration slow path. Called from Op::ConcatConstSlotLoop.

Source

pub fn scalar_slot_concat_repeat_slow(&mut self, slot: u8, rhs: &str, n: usize)

Slow fallback for the fused string-append loop: clones the RHS into a new PerlValue::string once and runs the existing scalar_slot_concat_inplace path n times. Used by Op::ConcatConstSlotLoop when the slot is aliased and the in-place fast path rejected the mutation.

Source

pub fn scalar_slot_concat_inplace( &mut self, slot: u8, rhs: &PerlValue, ) -> PerlValue

Source

pub fn pop_frame(&mut self)

Source

pub fn local_set_scalar( &mut self, name: &str, val: PerlValue, ) -> Result<(), PerlError>

local $name — save current value, assign val; restore on pop_frame.

Source

pub fn local_set_array( &mut self, name: &str, val: Vec<PerlValue>, ) -> Result<(), PerlError>

local @name — not valid for mysync arrays.

Source

pub fn local_set_hash( &mut self, name: &str, val: IndexMap<String, PerlValue>, ) -> Result<(), PerlError>

local %name

Source

pub fn local_set_hash_element( &mut self, name: &str, key: &str, val: PerlValue, ) -> Result<(), PerlError>

local $h{key} = val — save key state; restore one slot on pop_frame.

Source

pub fn local_set_array_element( &mut self, name: &str, index: i64, val: PerlValue, ) -> Result<(), PerlError>

local $a[i] = val — save element (as returned by Self::get_array_element), assign; restore on Self::pop_frame.

Source

pub fn declare_scalar(&mut self, name: &str, val: PerlValue)

Source

pub fn declare_scalar_frozen( &mut self, name: &str, val: PerlValue, frozen: bool, ty: Option<PerlTypeName>, ) -> Result<(), PerlError>

Declare a lexical scalar; frozen means no further assignment to this binding. ty is from typed my $x : Int — enforced on every assignment.

Source

pub fn is_scalar_frozen(&self, name: &str) -> bool

True if the innermost lexical scalar binding for name is frozen.

Source

pub fn is_array_frozen(&self, name: &str) -> bool

True if the innermost lexical array binding for name is frozen.

Source

pub fn is_hash_frozen(&self, name: &str) -> bool

True if the innermost lexical hash binding for name is frozen.

Source

pub fn check_frozen(&self, sigil: &str, name: &str) -> Option<&'static str>

Returns Some(sigil) if the named variable is frozen, None if mutable.

Source

pub fn get_scalar(&self, name: &str) -> PerlValue

Source

pub fn scalar_binding_exists(&self, name: &str) -> bool

True if any frame has a lexical scalar binding for name (my / our / assignment).

Source

pub fn all_scalar_names(&self) -> Vec<String>

Collect all scalar variable names across all frames (for debugger).

Source

pub fn array_binding_exists(&self, name: &str) -> bool

True if any frame or atomic slot holds an array named name.

Source

pub fn hash_binding_exists(&self, name: &str) -> bool

True if any frame or atomic slot holds a hash named name.

Source

pub fn get_scalar_raw(&self, name: &str) -> PerlValue

Get the raw scalar value WITHOUT unwrapping Atomic. Used by scope.capture() to preserve the Arc for sharing across threads.

Source

pub fn atomic_mutate( &mut self, name: &str, f: impl FnOnce(&PerlValue) -> PerlValue, ) -> PerlValue

Atomically read-modify-write a scalar. Holds the Mutex lock for the entire cycle so mysync variables are race-free under fan/pfor. Returns the NEW value.

Source

pub fn atomic_mutate_post( &mut self, name: &str, f: impl FnOnce(&PerlValue) -> PerlValue, ) -> PerlValue

Like atomic_mutate but returns the OLD value (for postfix $x++).

Source

pub fn scalar_concat_inplace( &mut self, name: &str, rhs: &PerlValue, ) -> Result<PerlValue, PerlError>

Append rhs to a scalar string in-place (no clone of the existing string). If the scalar is not yet a String, it is converted first.

The binding and the returned PerlValue share the same heap Arc via PerlValue::shallow_clone on the store — a full Clone would deep-copy the entire String each time and make repeated .= O(N²) in the total length.

Source

pub fn set_scalar( &mut self, name: &str, val: PerlValue, ) -> Result<(), PerlError>

Source

pub fn set_topic(&mut self, val: PerlValue)

Set the topic variable $_ and its numeric alias $_0 together. Use this for single-arg closures (map, grep, etc.) so both $_ and $_0 work. This declares them in the current scope (not global), suitable for sub calls.

Also sets outer topic aliases: $_< = previous $_, $_<< = previous $_<, etc. This allows nested blocks (e.g. fan inside >{}) to access enclosing topic values.

Source

pub fn set_closure_args(&mut self, args: &[PerlValue])

Set numeric closure argument aliases $_0, $_1, $_2, … for all args. Also sets $_ to the first argument (if any), shifting outer topics like [set_topic].

Source

pub fn push_defer(&mut self, coderef: PerlValue)

Register a defer { BLOCK } closure to run when this scope exits.

Source

pub fn take_defers(&mut self) -> Vec<PerlValue>

Take all deferred blocks from the current frame (for execution on scope exit). Returns them in reverse order (LIFO - last defer runs first).

Source

pub fn declare_atomic_array(&mut self, name: &str, val: Vec<PerlValue>)

Source

pub fn declare_atomic_hash( &mut self, name: &str, val: IndexMap<String, PerlValue>, )

Source

pub fn take_sub_underscore(&mut self) -> Option<Vec<PerlValue>>

Remove @_ from the innermost frame without cloning (move out of the frame sub_underscore field). Call sites restore with Self::declare_array before running a body that uses shift / @_.

Source

pub fn declare_array(&mut self, name: &str, val: Vec<PerlValue>)

Source

pub fn declare_array_frozen( &mut self, name: &str, val: Vec<PerlValue>, frozen: bool, )

Source

pub fn get_array(&self, name: &str) -> Vec<PerlValue>

Source

pub fn get_array_borrow(&self, name: &str) -> Option<&[PerlValue]>

Borrow the innermost binding for name when it is a plain Vec (not mysync). Used to pass @_ to [crate::list_util::native_dispatch] without cloning the vector.

Source

pub fn get_array_mut( &mut self, name: &str, ) -> Result<&mut Vec<PerlValue>, PerlError>

Source

pub fn push_to_array( &mut self, name: &str, val: PerlValue, ) -> Result<(), PerlError>

Push to array — works for both regular and atomic arrays.

Source

pub fn push_int_range_to_array( &mut self, name: &str, start: i64, end: i64, ) -> Result<(), PerlError>

Bulk push @name, start..end-1 for the fused counted-loop superinstruction: reserves the Vec once, then pushes PerlValue::integer(i) for i in start..end in a tight Rust loop. Atomic arrays take a single lock().push() burst.

Source

pub fn pop_from_array(&mut self, name: &str) -> Result<PerlValue, PerlError>

Pop from array — works for both regular and atomic arrays.

Source

pub fn shift_from_array(&mut self, name: &str) -> Result<PerlValue, PerlError>

Shift from array — works for both regular and atomic arrays.

Source

pub fn array_len(&self, name: &str) -> usize

Get array length — works for both regular and atomic arrays.

Source

pub fn set_array( &mut self, name: &str, val: Vec<PerlValue>, ) -> Result<(), PerlError>

Source

pub fn get_array_element(&self, name: &str, index: i64) -> PerlValue

Direct element access — works for both regular and atomic arrays.

Source

pub fn set_array_element( &mut self, name: &str, index: i64, val: PerlValue, ) -> Result<(), PerlError>

Source

pub fn exists_array_element(&self, name: &str, index: i64) -> bool

Perl exists $a[$i] — true when the slot index is within the current array length.

Source

pub fn delete_array_element( &mut self, name: &str, index: i64, ) -> Result<PerlValue, PerlError>

Perl delete $a[$i] — sets the element to undef, returns the previous value.

Source

pub fn declare_hash(&mut self, name: &str, val: IndexMap<String, PerlValue>)

Source

pub fn declare_hash_frozen( &mut self, name: &str, val: IndexMap<String, PerlValue>, frozen: bool, )

Source

pub fn get_hash(&self, name: &str) -> IndexMap<String, PerlValue>

Source

pub fn get_hash_mut( &mut self, name: &str, ) -> Result<&mut IndexMap<String, PerlValue>, PerlError>

Source

pub fn set_hash( &mut self, name: &str, val: IndexMap<String, PerlValue>, ) -> Result<(), PerlError>

Source

pub fn get_hash_element(&self, name: &str, key: &str) -> PerlValue

Source

pub fn atomic_hash_mutate( &mut self, name: &str, key: &str, f: impl FnOnce(&PerlValue) -> PerlValue, ) -> Result<PerlValue, PerlError>

Atomically read-modify-write a hash element. For atomic hashes, holds the Mutex for the full cycle. Returns the new value.

Source

pub fn atomic_array_mutate( &mut self, name: &str, index: i64, f: impl FnOnce(&PerlValue) -> PerlValue, ) -> Result<PerlValue, PerlError>

Atomically read-modify-write an array element. Returns the new value.

Source

pub fn set_hash_element( &mut self, name: &str, key: &str, val: PerlValue, ) -> Result<(), PerlError>

Source

pub fn set_hash_int_times_range( &mut self, name: &str, start: i64, end: i64, k: i64, ) -> Result<(), PerlError>

Bulk for i in start..end { $h{i} = i * k } for the fused hash-insert loop. Reserves capacity once and runs the whole range in a tight Rust loop. itoa is used to stringify each key without a transient format! allocation.

Source

pub fn delete_hash_element( &mut self, name: &str, key: &str, ) -> Result<PerlValue, PerlError>

Source

pub fn exists_hash_element(&self, name: &str, key: &str) -> bool

Source

pub fn for_each_hash_value(&self, name: &str, visit: impl FnMut(&PerlValue))

Walk all values of the named hash with a visitor. Used by the fused for my $k (keys %h) { $sum += $h{$k} } op so the hot loop runs without cloning the entire map into a keys array (vs the un-fused shape, which allocates one PerlValue::string per key).

Source

pub fn repl_binding_names(&self) -> Vec<String>

Sigil-prefixed names ($x, @a, %h) from all frames, for REPL tab-completion.

Source

pub fn capture(&mut self) -> Vec<(String, PerlValue)>

Source

pub fn capture_with_atomics( &self, ) -> (Vec<(String, PerlValue)>, Vec<(String, AtomicArray)>, Vec<(String, AtomicHash)>)

Extended capture that returns atomic arrays/hashes separately.

Source

pub fn restore_capture(&mut self, captured: &[(String, PerlValue)])

Source

pub fn restore_atomics( &mut self, arrays: &[(String, AtomicArray)], hashes: &[(String, AtomicHash)], )

Restore atomic arrays/hashes from capture_with_atomics.

Trait Implementations§

Source§

impl Clone for Scope

Source§

fn clone(&self) -> Scope

Returns a duplicate of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for Scope

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl Default for Scope

Source§

fn default() -> Self

Returns the “default value” for a type. Read more

Auto Trait Implementations§

§

impl Freeze for Scope

§

impl !RefUnwindSafe for Scope

§

impl Send for Scope

§

impl Sync for Scope

§

impl Unpin for Scope

§

impl UnsafeUnpin for Scope

§

impl !UnwindSafe for Scope

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> DynClone for T
where T: Clone,

Source§

fn __clone_box(&self, _: Private) -> *mut ()

Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts 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 more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts 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 more
Source§

impl<T> Pointable for T

Source§

const ALIGN: usize

The alignment of pointer.
Source§

type Init = T

The type for initializers.
Source§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
Source§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
Source§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
Source§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<SS, SP> SupersetOf<SS> for SP
where SS: SubsetOf<SP>,

Source§

fn to_subset(&self) -> Option<SS>

The inverse inclusion map: attempts to construct self from the equivalent element of its superset. Read more
Source§

fn is_in_subset(&self) -> bool

Checks if self is actually part of its subset T (and can be converted to it).
Source§

fn to_subset_unchecked(&self) -> SS

Use with care! Same as self.to_subset but without any property checks. Always succeeds.
Source§

fn from_subset(element: &SS) -> SP

The inclusion map: converts self to the equivalent element of its superset.
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V