wlambda/
vval.rs

1
2// This is a part of WLambda. See README.md and COPYING for details.
3
4/*!
5
6This module provides the core data structures used by the parser,
7compiler and evaluator of WLambda.
8
9*/
10
11use std::rc::Rc;
12use std::rc::Weak;
13use std::cell::RefCell;
14use std::fmt;
15use std::fmt::{Display, Debug, Formatter};
16
17use crate::str_int::*;
18use crate::compiler::{GlobalEnv, GlobalEnvRef};
19use crate::nvec::{NVec};
20use crate::ops::Prog;
21
22use fnv::FnvHashMap;
23
24#[derive(Debug, Clone, PartialEq)]
25pub struct FileRef {
26    s: Rc<String>,
27}
28
29impl Display for FileRef {
30    fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
31        write!(f, "{}", *self.s)
32    }
33}
34
35impl FileRef {
36    pub fn new(s: &str) -> Self {
37        FileRef { s: Rc::new(String::from(s)) }
38    }
39    pub fn s(&self) -> &str { &(*self.s) }
40}
41
42#[derive(Clone, PartialEq)]
43pub struct SynPosInfo {
44    pub line:       u32,
45    pub col:        u32,
46    pub file:       FileRef,
47    pub name:       Option<String>,
48}
49
50/// Structure for holding information about origin
51/// of an AST node.
52#[derive(Clone, PartialEq)]
53pub struct SynPos {
54    pub syn:  Syntax,
55    pub info: Rc<SynPosInfo>,
56}
57
58impl SynPos {
59    pub fn empty() -> Self {
60        Self {
61            syn:  Syntax::Block,
62            info: Rc::new(SynPosInfo {
63                line: 0,
64                col:  0,
65                file: FileRef::new("?"),
66                name: None,
67            }),
68        }
69    }
70
71    pub fn new(syn: Syntax, line: u32, col: u32, file: FileRef) -> Self {
72        Self {
73            syn,
74            info: Rc::new(SynPosInfo { line, col, file, name: None, }),
75        }
76    }
77
78    pub fn has_info(&self) -> bool { self.info.line > 0 }
79
80    pub fn line(&self) -> u32 { self.info.line }
81    pub fn col(&self) -> u32 { self.info.col }
82
83    pub fn filename(&self) -> &str {
84        self.info.file.s()
85    }
86
87    pub fn syn(&self) -> Syntax { self.syn }
88
89    pub fn set_syn(&mut self, syn: Syntax) {
90        self.syn = syn;
91    }
92
93    pub fn set_name(&mut self, name: &str) {
94        let mut new_info = (*self.info).clone();
95        new_info.name = Some(name.to_string());
96        self.info = Rc::new(new_info);
97    }
98
99    pub fn s_short(&self) -> String {
100        format!("({:?}[{}:{}])", self.syn, self.info.line, self.info.col)
101    }
102
103    pub fn s_only_pos(&self) -> String {
104        format!("({}:[{}:{}])", self.info.file.s(), self.info.line, self.info.col)
105    }
106}
107
108impl Display for SynPos {
109    fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
110        if self.has_info() {
111            if self.info.name.is_some() && !self.info.name.as_ref().unwrap().is_empty() {
112                write!(f, "{}:{}:{} {:?}[{}]",
113                       self.info.file.s(),
114                       self.info.line,
115                       self.info.col,
116                       self.syn,
117                       self.info.name.as_ref().unwrap())
118            } else {
119                write!(f, "{}:{}:{} {:?}",
120                       self.info.file.s(),
121                       self.info.line,
122                       self.info.col,
123                       self.syn)
124            }
125        } else {
126            write!(f, "")
127        }
128    }
129}
130
131impl Debug for SynPos {
132    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
133        write!(f, "{}", self)
134    }
135}
136
137#[derive(Debug, Clone, PartialEq)]
138pub struct CompileError {
139    pub pos:    SynPos,
140    pub msg:    String,
141}
142
143impl Display for CompileError {
144    fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
145        write!(
146            f,
147            "{}:{}:{} Compilation Error: {}",
148            self.pos.info.file,
149            self.pos.info.line,
150            self.pos.info.col,
151            self.msg)
152    }
153}
154
155
156/// Encodes the different types of AST nodes.
157#[derive(Debug, Clone, Copy, PartialEq)]
158#[allow(dead_code)]
159pub enum Syntax {
160    Var,
161    Key,
162    SetKey,
163    GetKey,
164    GetKey2,
165    GetKey3,
166    GetSym,
167    GetSym2,
168    GetSym3,
169    GetIdx,
170    GetIdx2,
171    GetIdx3,
172    BinOpAdd,
173    BinOpSub,
174    BinOpMul,
175    BinOpDiv,
176    BinOpMod,
177    BinOpLe,
178    BinOpLt,
179    BinOpGe,
180    BinOpGt,
181    BinOpEq,
182    BinOpSomeOr,
183    BinOpExtSomeOr,
184    BinOpNoneOr,
185    BinOpErrOr,
186    BinOpOptOr,
187    OpNewPair,
188    OpCallLwR,
189    OpCallRwL,
190    OpCallApplyLwR,
191    OpCallApplyRwL,
192    OpColAddL,
193    OpColAddR,
194    Str,
195    Lst,
196    IVec,
197    FVec,
198    Opt,
199    Iter,
200    Map,
201    Expr,
202    Func,
203    Block,
204    Err,
205    Call,
206    Apply,
207    And,
208    Or,
209    Assign,
210    Def,
211    Ref,
212    HRef,
213    WRef,
214    Deref,
215    CaptureRef,
216    AssignRef,
217    DefGlobRef,
218    DefConst,
219    SelfObj,
220    SelfData,
221    Import,
222    Export,
223    DumpStack,
224    DumpVM,
225    DebugPrint,
226    MapSplice,
227    VecSplice,
228    Accum,
229    GlobVar,
230    Selector,
231    Pattern,
232    StructPattern,
233    Formatter,
234}
235
236impl std::str::FromStr for Syntax {
237    type Err = ();
238
239    fn from_str(s: &str) -> Result<Syntax, ()> {
240        match s {
241            "Var"            => Ok(Syntax::Var),
242            "Key"            => Ok(Syntax::Key),
243            "SetKey"         => Ok(Syntax::SetKey),
244            "GetKey"         => Ok(Syntax::GetKey),
245            "GetKey2"        => Ok(Syntax::GetKey2),
246            "GetKey3"        => Ok(Syntax::GetKey3),
247            "GetSym"         => Ok(Syntax::GetSym),
248            "GetSym2"        => Ok(Syntax::GetSym2),
249            "GetSym3"        => Ok(Syntax::GetSym3),
250            "GetIdx"         => Ok(Syntax::GetIdx),
251            "GetIdx2"        => Ok(Syntax::GetIdx2),
252            "GetIdx3"        => Ok(Syntax::GetIdx3),
253            "BinOpAdd"       => Ok(Syntax::BinOpAdd),
254            "BinOpSub"       => Ok(Syntax::BinOpSub),
255            "BinOpMul"       => Ok(Syntax::BinOpMul),
256            "BinOpDiv"       => Ok(Syntax::BinOpDiv),
257            "BinOpMod"       => Ok(Syntax::BinOpMod),
258            "BinOpLe"        => Ok(Syntax::BinOpLe),
259            "BinOpLt"        => Ok(Syntax::BinOpLt),
260            "BinOpGe"        => Ok(Syntax::BinOpGe),
261            "BinOpGt"        => Ok(Syntax::BinOpGt),
262            "BinOpEq"        => Ok(Syntax::BinOpEq),
263            "BinOpSomeOr"    => Ok(Syntax::BinOpSomeOr),
264            "BinOpExtSomeOr" => Ok(Syntax::BinOpExtSomeOr),
265            "BinOpNoneOr"    => Ok(Syntax::BinOpNoneOr),
266            "BinOpErrOr"     => Ok(Syntax::BinOpErrOr),
267            "BinOpOptOr"     => Ok(Syntax::BinOpOptOr),
268            "OpNewPair"      => Ok(Syntax::OpNewPair),
269            "OpCallLwR"      => Ok(Syntax::OpCallLwR),
270            "OpCallRwL"      => Ok(Syntax::OpCallRwL),
271            "OpCallApplyLwR" => Ok(Syntax::OpCallApplyLwR),
272            "OpCallApplyRwL" => Ok(Syntax::OpCallApplyRwL),
273            "OpColAddL"      => Ok(Syntax::OpColAddL),
274            "OpColAddR"      => Ok(Syntax::OpColAddR),
275            "Str"            => Ok(Syntax::Str),
276            "Lst"            => Ok(Syntax::Lst),
277            "IVec"           => Ok(Syntax::IVec),
278            "FVec"           => Ok(Syntax::FVec),
279            "Opt"            => Ok(Syntax::Opt),
280            "Iter"           => Ok(Syntax::Iter),
281            "Map"            => Ok(Syntax::Map),
282            "Expr"           => Ok(Syntax::Expr),
283            "Func"           => Ok(Syntax::Func),
284            "Block"          => Ok(Syntax::Block),
285            "Err"            => Ok(Syntax::Err),
286            "Call"           => Ok(Syntax::Call),
287            "Apply"          => Ok(Syntax::Apply),
288            "And"            => Ok(Syntax::And),
289            "Or"             => Ok(Syntax::Or),
290            "Assign"         => Ok(Syntax::Assign),
291            "Def"            => Ok(Syntax::Def),
292            "Ref"            => Ok(Syntax::Ref),
293            "HRef"           => Ok(Syntax::HRef),
294            "WRef"           => Ok(Syntax::WRef),
295            "Deref"          => Ok(Syntax::Deref),
296            "CaptureRef"     => Ok(Syntax::CaptureRef),
297            "AssignRef"      => Ok(Syntax::AssignRef),
298            "DefGlobRef"     => Ok(Syntax::DefGlobRef),
299            "DefConst"       => Ok(Syntax::DefConst),
300            "SelfObj"        => Ok(Syntax::SelfObj),
301            "SelfData"       => Ok(Syntax::SelfData),
302            "Import"         => Ok(Syntax::Import),
303            "Export"         => Ok(Syntax::Export),
304            "DumpStack"      => Ok(Syntax::DumpStack),
305            "DumpVM"         => Ok(Syntax::DumpVM),
306            "DebugPrint"     => Ok(Syntax::DebugPrint),
307            "MapSplice"      => Ok(Syntax::MapSplice),
308            "VecSplice"      => Ok(Syntax::VecSplice),
309            "Accum"          => Ok(Syntax::Accum),
310            "GlobVar"        => Ok(Syntax::GlobVar),
311            "Selector"       => Ok(Syntax::Selector),
312            "Pattern"        => Ok(Syntax::Pattern),
313            "StructPattern"  => Ok(Syntax::StructPattern),
314            "Formatter"      => Ok(Syntax::Formatter),
315            _ => Err(()),
316        }
317    }
318}
319
320#[derive(Clone)]
321pub struct Stdio {
322    pub write: Rc<RefCell<dyn std::io::Write>>,
323    pub read:  Rc<RefCell<dyn std::io::BufRead>>,
324}
325
326impl Stdio {
327    pub fn new_rust_std() -> Self {
328        Self {
329            write: Rc::new(RefCell::new(std::io::stdout())),
330            read:  Rc::new(RefCell::new(std::io::BufReader::new(std::io::stdin()))),
331        }
332    }
333
334    pub fn new_from_mem(input: Rc<RefCell<std::io::Cursor<Vec<u8>>>>,
335                        output: Rc<RefCell<Vec<u8>>>)
336        -> Self
337    {
338        Self {
339            write: output,
340            read: input,
341        }
342    }
343}
344
345impl std::fmt::Debug for Stdio {
346    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
347        write!(f, "wlambda::vval::Stdio")
348    }
349}
350
351/// The maximum stack size.
352///
353/// Currently hardcoded, but later the API user will be able to specify it.
354const START_STACK_SIZE : usize = 512;
355
356#[derive(Default, Debug, Clone, Copy)]
357pub struct LoopInfo {
358    pub pc:       usize,
359    pub uw_depth: usize,
360    pub sp:       usize,
361    pub break_pc: usize,
362}
363
364impl LoopInfo {
365    #[inline]
366    pub fn new() -> Self {
367        Self { pc: 0, uw_depth: 0, sp: 0, break_pc: 0 }
368    }
369}
370
371/// Describes an action that needs to be done when returning from a function
372/// or somehow jumps unpredictably around the VM prog.
373#[derive(Debug, Clone)]
374pub enum UnwindAction {
375    Null,
376    RestoreAccum(VVal, VVal),
377    RestoreSP(usize),
378    ClearLocals(usize, usize),
379    RestoreSelf(VVal),
380    RestoreLoopInfo(LoopInfo),
381    RestoreIter(Option<Rc<RefCell<VValIter>>>),
382    FunctionCall(usize, usize, usize),
383}
384
385/// The runtime environment of the evaluator.
386///
387/// The easiest way to get an instance of this, is to create
388/// an EvalContext:
389///```
390/// use wlambda::{VVal, EvalContext};
391///
392/// let mut ctx = EvalContext::new_default();
393/// let res =
394///     VVal::new_str("a")
395///     .call(&mut *ctx.local.borrow_mut(), &[VVal::new_str("b")])
396///     .unwrap();
397///
398/// assert_eq!(res.s(), "\"ab\"");
399///```
400#[derive(Debug)]
401pub struct Env {
402    /// The argument stack, initialized to a size of `START_STACK_SIZE`.
403    pub args: std::vec::Vec<VVal>,
404    /// A stack of the currently called functions.
405    ///
406    /// Used for accessing the up values, backtrace
407    /// and other details about the function.
408    pub call_stack: std::vec::Vec<Rc<VValFun>>,
409    /// A stack that holds cleanup routines that need to be handled:
410    pub unwind_stack: std::vec::Vec<UnwindAction>,
411    /// Holds the object of the currently called method:
412    pub current_self: VVal,
413    /// The basepointer to reference arguments and
414    /// local variables.
415    ///
416    /// - `bp + n (n >= 0)` references a local variable
417    /// - `bp - n (n > 0)` references an argument
418    pub bp:   usize,
419    /// The current stack pointer.
420    pub sp:   usize,
421    /// The argument count to the current call.
422    pub argc: usize,
423    /// A user defined variable that holds user context information.
424    /// See also the [with_user_do](struct.Env.html#method.with_user_do) function.
425    pub user: Rc<RefCell<dyn std::any::Any>>,
426    /// The exported names of this module.
427    pub exports: FnvHashMap<Symbol, VVal>,
428    /// This is the standard output used for any functions in
429    /// WLambda that print something. Such as `std:displayln`
430    /// or `std:writeln`.
431    pub stdio: Stdio,
432    /// Current accumulator value:
433    pub accum_val: VVal,
434    /// Current accumulator function:
435    pub accum_fun: VVal,
436    /// A pointer to the global environment, holding stuff like
437    /// the module loader and thread creator.
438    pub global: GlobalEnvRef,
439    /// A counter that counts the nesting depth in vm() calls
440    pub vm_nest: usize,
441    /// Holds information to process 'next' and 'break' for loop
442    /// constructs:
443    pub loop_info: LoopInfo,
444    /// Holds the current iterator for the 'iter' construct.
445    pub iter: Option<Rc<RefCell<VValIter>>>,
446}
447
448//impl Default for Env {
449//    fn default() -> Self { Self::new() }
450//}
451//
452impl Env {
453    pub fn new(global: GlobalEnvRef) -> Env {
454        let mut e = Env {
455            args:               Vec::with_capacity(START_STACK_SIZE),
456            current_self:       VVal::None,
457            bp:                 0,
458            sp:                 0,
459            argc:               0,
460            user:               Rc::new(RefCell::new(VVal::vec())),
461            exports:            FnvHashMap::with_capacity_and_hasher(5, Default::default()),
462            stdio:              Stdio::new_rust_std(),
463            accum_fun:          VVal::None,
464            accum_val:          VVal::None,
465            call_stack:         vec![],
466            unwind_stack:       vec![],
467            loop_info:          LoopInfo::new(),
468            iter:               None,
469            vm_nest:            0,
470            global
471        };
472        e.args.resize(START_STACK_SIZE, VVal::None);
473        e
474    }
475
476    pub fn new_with_user(global: GlobalEnvRef, user: Rc<RefCell<dyn std::any::Any>>) -> Env {
477        let mut e = Env {
478            args:               Vec::with_capacity(START_STACK_SIZE),
479            current_self:       VVal::None,
480            bp:                 0,
481            sp:                 0,
482            argc:               0,
483            exports:            FnvHashMap::with_capacity_and_hasher(2, Default::default()),
484            stdio:              Stdio::new_rust_std(),
485            accum_fun:          VVal::None,
486            accum_val:          VVal::None,
487            call_stack:         vec![],
488            unwind_stack:       std::vec::Vec::with_capacity(1000),
489            loop_info:          LoopInfo::new(),
490            iter:               None,
491            vm_nest:            0,
492            user,
493            global,
494        };
495        e.args.resize(START_STACK_SIZE, VVal::None);
496        e
497    }
498
499    /// Sets a custom stdio procedure. This can be used to redirect the
500    /// standard input/output operations of WLambda to other sinks and sources.
501    /// For instance writing and reading from a Buffer when using WASM
502    /// or some other embedded application:
503    ///
504    /// ```
505    /// use wlambda::*;
506    /// use std::rc::Rc;
507    /// use std::cell::RefCell;
508    ///
509    /// let new_output : Rc<RefCell<Vec<u8>>> =
510    ///     Rc::new(RefCell::new(vec![]));
511    /// let new_input =
512    ///     Rc::new(RefCell::new(std::io::Cursor::new("abc\ndef\n1 2 3 4\n"
513    ///                          .to_string().as_bytes().to_vec())));
514    ///
515    /// let memory_stdio =
516    ///     vval::Stdio::new_from_mem(new_input, new_output.clone());
517    ///
518    /// let mut ctx = EvalContext::new_default();
519    /// ctx.local.borrow_mut().set_stdio(memory_stdio);
520    ///
521    /// ctx.eval("std:displayln :TEST 123").unwrap();
522    ///
523    /// let output = String::from_utf8(new_output.borrow().clone()).unwrap();
524    /// assert_eq!(output, "TEST 123\n");
525    ///
526    /// let out_lines =
527    ///     ctx.eval("!l = $[]; std:io:lines \\std:push l _; l").unwrap().s();
528    /// assert_eq!(out_lines, "$[\"abc\\n\",\"def\\n\",\"1 2 3 4\\n\"]");
529    /// ```
530    pub fn set_stdio(&mut self, stdio: Stdio) {
531        self.stdio = stdio;
532    }
533
534    /// Returns the passed in user context value.
535    pub fn get_user(&self) -> Rc<RefCell<dyn std::any::Any>> {
536        self.user.clone()
537    }
538
539    /// Easier access to the user data field in Env
540    ///
541    /// In the following example the user supplies a registry
542    /// vector for storing VVals. A callback is stored, which is
543    /// then later executed.
544    ///
545    /// ```
546    /// use wlambda::{VVal, EvalContext, GlobalEnv};
547    /// use wlambda::vval::Env;
548    /// use std::rc::Rc;
549    /// use std::cell::RefCell;
550    ///
551    /// let global = GlobalEnv::new_default();
552    ///
553    /// global.borrow_mut().add_func("reg", |env: &mut Env, _argc: usize| {
554    ///     let fun = env.arg(0);
555    ///     env.with_user_do(|v: &mut Vec<VVal>| v.push(fun.clone()));
556    ///     Ok(VVal::None)
557    /// }, Some(1), Some(1));
558    ///
559    /// let reg : Rc<RefCell<Vec<VVal>>> =
560    ///     Rc::new(RefCell::new(Vec::new()));
561    ///
562    /// let mut ctx = EvalContext::new_with_user(global, reg.clone());
563    /// ctx.eval("reg { _ + 10 }").unwrap();
564    ///
565    /// let n = reg.borrow_mut()[0].clone();
566    /// let ret = ctx.call(&n, &vec![VVal::Int(11)]).unwrap();
567    /// assert_eq!(ret.i(), 21);
568    /// ```
569    #[allow(dead_code)]
570    pub fn with_user_do<T: 'static, F, X>(&mut self, f: F) -> X
571        where F: Fn(&mut T) -> X {
572        let mut any = self.user.borrow_mut();
573        let ref_reg = any.downcast_mut::<T>().unwrap();
574        f(ref_reg)
575    }
576
577    pub fn export_name(&mut self, name: &str, value: &VVal) {
578        self.exports.insert(s2sym(name), value.clone());
579    }
580
581    #[inline]
582    pub fn set_bp(&mut self, env_size: usize) -> usize {
583        let new_bp = self.sp;
584        self.sp += env_size;
585        if self.sp >= self.args.len() {
586            self.args.resize(self.sp * 2, VVal::None);
587        }
588        std::mem::replace(&mut self.bp, new_bp)
589    }
590
591    #[inline]
592    pub fn reset_bp(&mut self, env_size: usize, oldbp: usize) {
593        for i in self.bp..self.sp {
594            self.args[i] = VVal::None;
595        }
596//        self.sp -= env_size;
597        self.popn(env_size);
598        self.bp = oldbp;
599    }
600
601    pub fn self_object(&self) -> VVal {
602        self.current_self.clone()
603    }
604
605    #[inline]
606    pub fn with_object<T>(&mut self, object: VVal, f: T) -> Result<VVal, StackAction>
607        where T: Fn(&mut Env) -> Result<VVal, StackAction> {
608        let old_self = std::mem::replace(&mut self.current_self, object);
609        let ret = f(self);
610        self.current_self = old_self;
611        ret
612    }
613
614    #[inline]
615    pub fn with_local_call_info<T>(&mut self, argc: usize, f: T) -> Result<VVal, StackAction>
616        where T: Fn(&mut Env) -> Result<VVal, StackAction> {
617        let local_size = 0;
618        let old_argc = std::mem::replace(&mut self.argc, argc);
619        let old_bp   = self.set_bp(local_size);
620
621        let ret = f(self);
622
623        self.reset_bp(local_size, old_bp);
624        self.argc = old_argc;
625
626        ret
627    }
628
629    #[inline]
630    pub fn with_restore_sp<T>(&mut self, f: T) -> Result<VVal, StackAction>
631        where T: Fn(&mut Env) -> Result<VVal, StackAction> {
632
633        let old_sp = self.sp;
634        let ret = f(self);
635        self.popn(self.sp - old_sp);
636        ret
637    }
638
639    #[inline]
640    pub fn push_sp(&mut self, n: usize) {
641        self.sp += n;
642        if self.sp >= self.args.len() {
643            self.args.resize(self.sp * 2, VVal::None);
644        }
645        //d// println!("PUSH_SP {} => {}", n, self.sp);
646    }
647
648    #[inline]
649    pub fn push(&mut self, v: VVal) -> usize {
650        if self.sp >= self.args.len() {
651            self.args.resize(self.sp * 2, VVal::None);
652        }
653        self.args[self.sp] = v;
654        self.sp += 1;
655        self.sp - 1
656    }
657
658    #[inline]
659    pub fn stk(&self, offs: usize) -> &VVal {
660        &self.args[self.sp - offs] // implicit self.sp - 1! We must not call with 0!
661    }
662
663    #[inline]
664    pub fn stk_i(&self, offs: usize) -> i64 {
665        if let VVal::Int(i) = &self.args[(self.sp - 1) +  offs] {
666            *i
667        } else {
668            0
669        }
670    }
671
672    #[inline]
673    pub fn inc_local(&mut self, idx: usize, inc: i16) -> i64 {
674        if let VVal::Int(i) = &mut self.args[self.bp + idx] {
675            if inc > 0 { *i += 1; }
676            else { *i -= 1; }
677
678            *i
679        } else {
680            0
681        }
682    }
683
684    #[inline]
685    pub fn pop(&mut self) -> VVal {
686        if self.sp < 1 {
687            panic!("Stack pointer underflow {} {}", self.sp, 1);
688        }
689        self.sp -= 1;
690        std::mem::replace(&mut self.args[self.sp], VVal::None)
691    }
692
693    #[inline]
694    pub fn null_locals(&mut self, from: usize, to: usize) {
695        for i in from..to {
696            self.args[self.bp + i] = VVal::None;
697        }
698    }
699
700    #[inline]
701    pub fn popn(&mut self, n: usize) {
702        if self.sp < n {
703            panic!("Stack pointer underflow {} {}", self.sp, n);
704        }
705        if n > 0 {
706            //d// println!("SP={}, N={}", self.sp, n);
707            for i in (self.sp - n)..self.sp {
708                //d// println!("POP[{}] {} [of {}]", i, self.args[i].s(), n);
709                self.args[i] = VVal::None;
710            }
711        }
712        self.sp -= n;
713        //d// println!("POPN {} => {}", n, self.sp);
714    }
715
716    /// Prints a dump of the stack state.
717    pub fn dump_stack(&self) {
718        //d// println!("* SP={}, BP={}", self.sp, self.bp);
719        for (i, v) in self.args.iter().enumerate() {
720            let mut mark = String::from("");
721            if i == self.bp { mark = format!("{} BP", mark); }
722            if i == self.sp { mark = format!("{} SP", mark); }
723            if !mark.is_empty() { mark = format!("{} ->", mark); }
724
725            println!("    {:9} [{:3}] = {}", mark, i, v.s());
726            if i >= (1 + self.sp) { break; }
727        }
728        if !self.call_stack.is_empty() {
729            for (i, u) in self.call_stack.last().unwrap().upvalues.iter().enumerate() {
730                println!("  UP[{:3}] = {}", i, u.s());
731            }
732        }
733    }
734
735    #[inline]
736    pub fn stk2vec(&self, count: usize) -> VVal {
737        let v = VVal::vec();
738        for i in 0..count {
739            v.push(self.args[self.sp - (count - i)].clone());
740        }
741        v
742    }
743
744
745    #[inline]
746    pub fn argv(&self) -> VVal {
747        VVal::vec_from(&self.args[(self.bp - self.argc)..self.bp])
748    }
749
750    #[inline]
751    pub fn argv_ref(&self) -> &[VVal] {
752        &self.args[(self.bp - self.argc)..self.bp]
753    }
754
755    #[inline]
756    pub fn get_up_raw(&mut self, i: usize) -> VVal {
757        //d// println!("GET UP {}: {:?}", i, self.fun.upvalues);
758        self.call_stack.last().unwrap().upvalues[i].clone()
759    }
760
761    #[inline]
762    pub fn get_up_captured_ref(&self, i: usize) -> VVal {
763        self.call_stack.last().unwrap().upvalues[i].to_ref()
764    }
765
766    #[inline]
767    pub fn get_up(&self, i: usize) -> VVal {
768        match &self.call_stack.last().unwrap().upvalues[i] {
769            VVal::HRef(hr)  => hr.borrow().clone(),
770            VVal::WWRef(r) => {
771                match r.upgrade() {
772                    Some(v) => v.borrow().clone(),
773                    None    => VVal::None,
774                }
775            },
776            v => v.clone(),
777        }
778    }
779
780    #[inline]
781    pub fn arg_ref(&self, i: usize) -> Option<&VVal> {
782        if i >= self.argc { return None; }
783        Some(&self.args[(self.bp - self.argc) + i])
784    }
785
786    #[inline]
787    pub fn arg_err_internal(&self, i: usize) -> Option<VVal> {
788        let v = &self.args[(self.bp - self.argc) + i];
789        match v {
790            VVal::Err(_) => Some(v.clone()),
791            _            => None,
792        }
793    }
794
795    #[inline]
796    pub fn arg(&self, i: usize) -> VVal {
797        //d// println!("GET ARGC [{}] = {}", i, self.argc);
798        if i >= self.argc { return VVal::None; }
799        let v = &self.args[(self.bp - self.argc) + i];
800        //d// println!("GET ARG [{}/{}] = {}", i, self.sp - (i + 1), v.s());
801        v.clone()
802    }
803
804    pub fn get_local_up_promotion(&mut self, i: usize) -> VVal {
805        let idx = self.bp + i;
806        match &self.args[idx] {
807            VVal::HRef(r)  => VVal::HRef(r.clone()),
808//            VVal::Ref(r)   => VVal::Ref(r.clone()),
809            VVal::WWRef(r) => VVal::WWRef(r.clone()),
810            v => {
811                let new_v = v.to_hidden_boxed_ref();
812                self.args[idx] = new_v.clone();
813                new_v
814            }
815        }
816    }
817
818    pub fn get_local_captured_ref(&self, i: usize) -> VVal {
819        let idx = self.bp + i;
820        self.args[idx].to_ref()
821    }
822
823    #[inline]
824    pub fn reg(&self, i: i32) -> VVal {
825        if i >= 0 {
826            self.get_local(i as usize)
827        } else {
828            self.stk((-i) as usize).clone()
829        }
830    }
831
832    #[inline]
833    pub fn get_local(&self, i: usize) -> VVal {
834        match &self.args[self.bp + i] {
835            VVal::HRef(r)  => r.borrow().clone(),
836            v              => v.clone(),
837        }
838    }
839
840    pub fn assign_ref_up(&mut self, i: usize, value: VVal) {
841        let fun = self.call_stack.last().unwrap().clone();
842        let upv = &fun.upvalues[i];
843
844        match upv {
845//            VVal::Ref(r)     => { r.replace(value); }
846            VVal::HRef(r)    => { r.borrow_mut().assign_ref(value); }
847            VVal::WWRef(l)   => {
848                if let Some(r) = l.upgrade() {
849                    r.borrow_mut().assign_ref(value);
850                }
851            },
852            _ => (),
853        }
854    }
855
856    pub fn assign_ref_local(&mut self, i: usize, value: VVal) {
857        let idx = self.bp + i;
858        self.args[idx].assign_ref(value);
859    }
860
861    pub fn set_up(&mut self, index: usize, value: VVal) {
862        let fun = self.call_stack.last().unwrap().clone();
863        let upv = &fun.upvalues[index];
864
865        match upv {
866//            VVal::Ref(r)   => { r.replace(value); }
867            VVal::HRef(r)  => { r.replace(value); }
868            VVal::WWRef(r) => {
869                if let Some(r) = Weak::upgrade(r) {
870                    r.replace(value);
871                }
872            },
873            _ => {}
874        }
875    }
876
877    #[inline]
878    pub fn set_consume(&mut self, i: usize, value: VVal) {
879        let idx = self.bp + i;
880        if idx >= self.args.len() {
881            self.args.resize(idx * 2, VVal::None);
882        }
883        match &mut self.args[idx] {
884            VVal::HRef(r)  => { r.replace(value); }
885            v              => { *v = value }
886        }
887    }
888
889    #[inline]
890    pub fn unwind_depth(&self) -> usize {
891        self.unwind_stack.len()
892    }
893
894    #[inline]
895    pub fn push_unwind(&mut self, uwa: UnwindAction) {
896        self.unwind_stack.push(uwa);
897    }
898
899    #[inline]
900    pub fn unwind_to_depth(&mut self, depth: usize) {
901        while self.unwind_stack.len() > depth {
902            self.unwind_one();
903        }
904    }
905
906    #[inline]
907    pub fn push_fun_call(&mut self, fu: Rc<VValFun>, argc: usize) {
908        let local_size = fu.local_size;
909        let old_bp = self.set_bp(local_size);
910        let uwa =
911            UnwindAction::FunctionCall(
912                std::mem::replace(&mut self.argc, argc),
913                old_bp,
914                local_size);
915        self.push_unwind(uwa);
916        self.call_stack.push(fu);
917    }
918
919    #[inline]
920    pub fn push_clear_locals(&mut self, from: usize, to: usize) {
921        self.push_unwind(UnwindAction::ClearLocals(from, to));
922    }
923
924    #[inline]
925    pub fn push_unwind_self(&mut self, new_self: VVal) {
926        let uwa =
927            UnwindAction::RestoreSelf(
928                std::mem::replace(&mut self.current_self, new_self));
929        self.push_unwind(uwa);
930    }
931
932    #[inline]
933    pub fn cleanup_loop(&mut self) {
934        while self.sp > self.loop_info.sp {
935            self.pop();
936        }
937        self.unwind_to_depth(self.loop_info.uw_depth);
938    }
939
940    #[inline]
941    pub fn push_loop_info(&mut self, current_pc: usize, break_pc: usize, uw_depth_offs: usize) {
942        let uw_depth = self.unwind_depth() + 1 + uw_depth_offs;
943        let uwa =
944            UnwindAction::RestoreLoopInfo(
945                std::mem::replace(&mut self.loop_info, LoopInfo {
946                    pc:       current_pc,
947                    sp:       self.sp,
948                    uw_depth,
949                    break_pc,
950                }));
951        self.push_unwind(uwa);
952    }
953
954    #[inline]
955    pub fn push_iter(&mut self, iter: Rc<RefCell<VValIter>>) {
956        let uwa =
957            UnwindAction::RestoreIter(
958                std::mem::replace(
959                    &mut self.iter, Some(iter)));
960        self.push_unwind(uwa);
961    }
962
963    pub fn dump_unwind_stack(&self) -> String {
964        let mut s = String::new();
965        for i in 0..self.unwind_stack.len() {
966            let add =
967                match &self.unwind_stack[self.unwind_stack.len() - (i + 1)] {
968                    UnwindAction::RestoreSP(sp) =>
969                        format!("rsp({})", *sp),
970                    UnwindAction::ClearLocals(from, to) =>
971                        format!("cl({},{})", *from, *to),
972                    UnwindAction::RestoreLoopInfo(li) =>
973                        format!("loinf(uws:{},sp:{})", li.uw_depth, li.sp),
974                    UnwindAction::RestoreAccum(_fun, _val) =>
975                        ("raccm".to_string()),
976                    UnwindAction::RestoreSelf(_slf) =>
977                        ("rslf".to_string()),
978                    UnwindAction::RestoreIter(_i) =>
979                        ("ritr".to_string()),
980                    UnwindAction::FunctionCall(argc, old_bp, local_size) =>
981                        format!("fcal({},{},{})", argc, old_bp, local_size),
982                    UnwindAction::Null =>
983                        ("nul".to_string()),
984                };
985
986            if !s.is_empty() {
987                s += ";";
988            }
989            s += &add[..];
990        }
991        s
992    }
993
994    #[inline]
995    pub fn unwind(&mut self, ua: UnwindAction) {
996        match ua {
997            UnwindAction::RestoreSP(sp) => {
998                while self.sp > sp {
999                    self.pop();
1000                }
1001            },
1002            UnwindAction::ClearLocals(from, to) => {
1003                self.null_locals(from, to);
1004            },
1005            UnwindAction::RestoreLoopInfo(li) => {
1006                self.loop_info = li;
1007            },
1008            UnwindAction::RestoreAccum(fun, val) => {
1009                self.accum_fun = fun;
1010                self.accum_val = val;
1011            },
1012            UnwindAction::RestoreSelf(slf) => {
1013                self.current_self = slf;
1014            },
1015            UnwindAction::RestoreIter(i) => {
1016                self.iter = i;
1017            },
1018            UnwindAction::FunctionCall(argc, old_bp, local_size) => {
1019                self.reset_bp(local_size, old_bp);
1020                self.call_stack.pop();
1021                self.argc = argc;
1022            },
1023            UnwindAction::Null => (),
1024        }
1025    }
1026
1027    #[inline]
1028    pub fn unwind_one(&mut self) {
1029        let uwa = self.unwind_stack.pop().unwrap();
1030        self.unwind(uwa);
1031    }
1032
1033    pub fn setup_accumulator(&mut self, v: VVal) {
1034        let f =
1035            match v {
1036                VVal::Map(_) => {
1037                    VValFun::new_fun(
1038                        move |env: &mut Env, _argc: usize| {
1039                            let k = env.arg(0);
1040                            let v = env.arg(1);
1041                            env.accum_val.set_key(&k, v.clone())?;
1042                            Ok(v)
1043                        }, Some(2), Some(2), false)
1044                },
1045                _ => {
1046                    VValFun::new_fun(
1047                        move |env: &mut Env, _argc: usize| {
1048                            let v = env.arg(0);
1049                            env.accum_val.accum(&v);
1050                            Ok(v)
1051                        }, Some(1), Some(1), false)
1052                }
1053            };
1054
1055        let uwa =
1056            UnwindAction::RestoreAccum(
1057                std::mem::replace(&mut self.accum_fun, f),
1058                std::mem::replace(&mut self.accum_val, v));
1059        self.push_unwind(uwa);
1060    }
1061
1062    pub fn with_accum<T>(&mut self, v: VVal, acfun: T) -> Result<VVal, StackAction>
1063        where T: Fn(&mut Env) -> Result<VVal, StackAction>
1064    {
1065        self.setup_accumulator(v);
1066
1067        let ret = acfun(self);
1068
1069        let val = self.accum_val.clone();
1070        self.unwind_one();
1071
1072        ret?;
1073        Ok(val)
1074    }
1075
1076    pub fn get_accum_value(&self) -> VVal {
1077        self.accum_val.clone()
1078    }
1079
1080    pub fn get_accum_function(&self) -> VVal {
1081        self.accum_fun.clone()
1082    }
1083
1084    /// Creates a new error VVal with the given string as error message.
1085    /// Takes care to annotate the error value with the current function
1086    /// information.
1087    ///
1088    ///```
1089    /// use wlambda::compiler::EvalContext;
1090    /// use wlambda::vval::{VVal, VValFun, Env};
1091    ///
1092    /// let mut ctx = EvalContext::new_default();
1093    ///
1094    /// ctx.set_global_var("xyz",
1095    ///     &VValFun::new_fun(
1096    ///         move |env: &mut Env, argc: usize| {
1097    ///             let ok = false;
1098    ///             if !ok {
1099    ///                 Ok(env.new_err(
1100    ///                     format!("Something was not ok!")))
1101    ///             } else {
1102    ///                 Ok(VVal::Bol(true))
1103    ///             }
1104    ///         }, None, None, false));
1105    ///```
1106    pub fn new_err(&self, s: String) -> VVal {
1107        for i in self.call_stack.iter().rev() {
1108            if i.syn_pos.is_some() {
1109                return
1110                    VVal::err(
1111                        VVal::new_str_mv(s),
1112                        i.syn_pos.clone().unwrap());
1113            }
1114        };
1115
1116        if self.call_stack.last().is_some() {
1117            VVal::err(
1118                VVal::new_str_mv(s),
1119                self.call_stack.last().unwrap().syn_pos.clone().or_else(
1120                    || Some(SynPos::empty())).unwrap())
1121        } else {
1122            VVal::err(VVal::new_str_mv(s), SynPos::empty())
1123        }
1124    }
1125
1126    pub fn new_panic(&self, val: VVal) -> StackAction {
1127        for i in self.call_stack.iter().rev() {
1128            if i.syn_pos.is_some() {
1129                return StackAction::panic(val, i.syn_pos.clone(), VVal::None);
1130            }
1131        };
1132
1133        StackAction::panic(val,
1134            self.call_stack.last().unwrap().syn_pos.clone().or_else(
1135                || Some(SynPos::empty())),
1136            VVal::None)
1137    }
1138
1139    pub fn new_panic_argv(&self, val: VVal, args: VVal) -> StackAction {
1140        for i in self.call_stack.iter().rev() {
1141            if i.syn_pos.is_some() {
1142                return StackAction::panic(val, i.syn_pos.clone(), args);
1143            }
1144        };
1145
1146        StackAction::panic(val,
1147            self.call_stack.last().unwrap().syn_pos.clone().or_else(
1148                || Some(SynPos::empty())),
1149            args)
1150    }
1151}
1152
1153/// Encodes all kinds of jumps up the call stack, like `break` and `next` in Loops.
1154///
1155/// As WLambda is not using a VM, it uses return values of the
1156/// closure call tree to handle jumping up the stack.
1157#[derive(Clone)]
1158#[allow(clippy::type_complexity)]
1159pub enum StackAction {
1160    Panic(Box<(VVal, Vec<(Option<SynPos>, VVal)>)>),
1161    Return(Box<(VVal, VVal)>),
1162    Break(Box<VVal>),
1163    Next,
1164}
1165
1166fn fmt_shorten_ellipses(f: &mut Formatter, len: &mut usize, s: String) -> std::fmt::Result {
1167    if *len > 250 { return Ok(()); }
1168
1169    if s.len() > 35 { *len += 35 + 3;  write!(f, "{}...", &s[0..35]) }
1170    else            { *len += s.len(); write!(f, "{}", s) }
1171}
1172
1173fn fmt_argv(f: &mut Formatter, v: &VVal) -> std::fmt::Result {
1174    let mut cur_len = 0;
1175
1176    if !v.is_map()
1177       && v.iter_over_vvals()
1178    {
1179        write!(f, "[")?;
1180        v.with_iter(|it| {
1181            let mut first = true;
1182            for (v, _) in it {
1183                if cur_len > 250 {
1184                    break;
1185                }
1186
1187                if first {
1188                    first = false;
1189                } else {
1190                    cur_len += 2;
1191                    write!(f, ", ")?;
1192                }
1193
1194                fmt_shorten_ellipses(f, &mut cur_len, v.s())?;
1195            }
1196
1197            Ok(()) as std::fmt::Result
1198        })?;
1199
1200        if cur_len > 250 {
1201            write!(f, "...")?
1202        }
1203
1204        write!(f, "]")?;
1205
1206    } else {
1207        fmt_shorten_ellipses(f, &mut cur_len, v.s())?
1208    }
1209
1210    Ok(())
1211}
1212
1213impl Display for StackAction {
1214    fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
1215        match self {
1216            StackAction::Panic(panic) => {
1217                if panic.1.is_empty() {
1218                    write!(f, "Panic: {}", panic.0.s())
1219                } else {
1220                    writeln!(f, "Panic: {}", panic.0.s())?;
1221
1222                    for t in panic.1.iter() {
1223                        write!(f, "    ")?;
1224
1225                        if let (Some(p), v) = t {
1226                            write!(f, "{} ", p)?;
1227                            fmt_argv(f, v)?;
1228                        } else {
1229                            write!(f, "    ")?;
1230                            fmt_argv(f, &t.1)?;
1231                        }
1232
1233                        writeln!(f)?;
1234                    }
1235
1236                    Ok(())
1237                }
1238            },
1239            StackAction::Return(ret) => write!(f, "Return[lbl={}] {}", ret.0.s(), ret.1.s()),
1240            StackAction::Break(v) => write!(f, "Break: {}", v.s()),
1241            StackAction::Next     => write!(f, "Next"),
1242        }
1243    }
1244}
1245
1246impl Debug for StackAction {
1247    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1248        write!(f, "{}", self)
1249    }
1250}
1251
1252impl StackAction {
1253    pub fn panic_borrow(v: &VVal) -> Self {
1254        Self::panic_msg(format!("Can't mutate borrowed value: {}", v.s()))
1255    }
1256
1257    pub fn panic_msg(err: String) -> Self {
1258        StackAction::Panic(Box::new(
1259            (VVal::new_str_mv(err), vec![])))
1260    }
1261
1262    pub fn panic_str(err: String, sp: Option<SynPos>, args: VVal) -> Self {
1263        StackAction::Panic(Box::new(
1264            (VVal::new_str_mv(err), vec![(sp, args)])))
1265    }
1266
1267    pub fn panic(err: VVal, sp: Option<SynPos>, args: VVal) -> Self {
1268        StackAction::Panic(Box::new(
1269            (err, vec![(sp, args)])))
1270    }
1271
1272    pub fn wrap_panic(self, sp: Option<SynPos>, args: VVal) -> Self {
1273        match self {
1274            StackAction::Panic(mut panic) => {
1275                panic.as_mut().1.push((sp, args));
1276                StackAction::Panic(panic)
1277            },
1278            _ => self,
1279        }
1280    }
1281}
1282
1283impl From<VVal> for StackAction {
1284    fn from(v: VVal) -> StackAction {
1285        StackAction::panic(v, None, VVal::None)
1286    }
1287}
1288
1289/// Position of a variable represented in the `CompileEnv`.
1290#[derive(Debug, Clone)]
1291pub enum VarPos {
1292    /// No position of the variable. Mostly placeholder value for non existing variable.
1293    NoPos,
1294    /// Variable is stored in upvalue at the specified position.
1295    UpValue(usize),
1296    /// Variable is stored in local variables on the stack at the specified position.
1297    Local(usize),
1298    /// Variable is stored in the global variables with the given value.
1299    Global(VVal),
1300    /// A constant value, major difference to Global is, that it is not a reference
1301    /// and a slight bit faster.
1302    Const(VVal),
1303}
1304
1305pub type EvalNode = Box<dyn Fn(&mut Env) -> Result<VVal,StackAction>>;
1306pub type ClosNodeRef = Rc<RefCell<dyn Fn(&mut Env, usize) -> Result<VVal,StackAction>>>;
1307
1308#[derive(Clone)]
1309pub enum FunType {
1310    ClosureNode(ClosNodeRef),
1311    VMProg(Rc<Prog>),
1312}
1313
1314#[derive(Clone)]
1315/// This structure is the runtime representation of a WLambda function value.
1316pub struct VValFun {
1317    /// The closure or vm program that runs the function.
1318    pub fun:        FunType,
1319    /// The positions of the upvalues that are being captured by this function.
1320    pub upvalue_pos: Rc<std::vec::Vec<VarPos>>,
1321    /// Contains any caught upvalues.
1322    pub upvalues:   std::vec::Vec<VVal>,
1323    /// The number of local variables defined in this functions.
1324    ///
1325    /// This value is used to reserve stack space for storing them.
1326    pub local_size: usize,
1327    /// Min number of arguments this functions requires.
1328    pub min_args:   Option<usize>,
1329    /// Max number of arguments this functions requires.
1330    pub max_args:   Option<usize>,
1331    /// If true, then this function accepts error values without panic.
1332    /// Functions by default don't accept errors as argument. It needs to be
1333    /// explicitly enabled.
1334    pub err_arg_ok: bool,
1335    /// The location of the definition of this function.
1336    pub syn_pos:    Option<SynPos>,
1337    /// The return label of the function:
1338    pub label:      VVal,
1339}
1340
1341impl VValFun {
1342    /// Creates a new VVal containing the given closure with the given minimum
1343    /// and maximum parameters (see also [`add_func` of GlobalEnv](compiler/struct.GlobalEnv.html#method.add_func)).
1344    ///
1345    /// There is also a new more convenient (because provided by VVal itself)
1346    /// function: `VVal::new_fun` which has the same parameters.
1347    ///
1348    /// The `err_arg_ok` parameter specifies whether the function accepts
1349    /// error values as arguments. If it doesn't, the program will panic
1350    /// once an error value is encountered. This makes programs more maintainable.
1351    ///
1352    /// This is usually useful if you want to add functions to the [EvalContext](compiler/struct.EvalContext.html).
1353    /// at runtime.
1354    ///
1355    ///```rust
1356    /// use wlambda::compiler::EvalContext;
1357    /// use wlambda::vval::{VVal, VValFun, Env};
1358    ///
1359    /// let mut ctx = wlambda::compiler::EvalContext::new_empty_global_env();
1360    ///
1361    /// ctx.set_global_var("xyz",
1362    ///     &VValFun::new_fun(
1363    ///         move |env: &mut Env, argc: usize| {
1364    ///             Ok(VVal::new_str("xyz"))
1365    ///         }, None, None, false));
1366    ///
1367    /// assert_eq!(ctx.eval("xyz[]").unwrap().s_raw(), "xyz")
1368    ///```
1369    pub fn new_fun<T>(fun: T, min_args: Option<usize>, max_args: Option<usize>, err_arg_ok: bool) -> VVal
1370        where T: 'static + Fn(&mut Env, usize) -> Result<VVal, StackAction> {
1371
1372        VValFun::new_val(Rc::new(RefCell::new(fun)), Vec::new(), 0, min_args, max_args, err_arg_ok, None, Rc::new(vec![]))
1373    }
1374
1375    pub fn new_fun_with_pos<T>(fun: T, min_args: Option<usize>, max_args: Option<usize>, err_arg_ok: bool, spos: SynPos) -> VVal
1376        where T: 'static + Fn(&mut Env, usize) -> Result<VVal, StackAction> {
1377
1378        VValFun::new_val(Rc::new(RefCell::new(fun)), Vec::new(), 0, min_args, max_args, err_arg_ok, Some(spos), Rc::new(vec![]))
1379    }
1380
1381    /// Internal utility function. Use at your own risk, API might change.
1382    #[allow(clippy::too_many_arguments)]
1383    pub fn new_val(fun: ClosNodeRef, upvalues: std::vec::Vec<VVal>,
1384                   env_size: usize, min_args: Option<usize>,
1385                   max_args: Option<usize>, err_arg_ok: bool, syn_pos: Option<SynPos>,
1386                   upvalue_pos: Rc<std::vec::Vec<VarPos>>) -> VVal {
1387        VVal::Fun(Rc::new(VValFun {
1388            upvalue_pos,
1389            upvalues,
1390            fun: FunType::ClosureNode(fun),
1391            local_size: env_size,
1392            min_args,
1393            max_args,
1394            err_arg_ok,
1395            syn_pos,
1396            label: VVal::None,
1397        }))
1398    }
1399
1400    /// Internal utility function. Use at your own risk, API might change.
1401    #[allow(clippy::too_many_arguments)]
1402    pub fn new_prog(prog: Rc<Prog>, upvalues: std::vec::Vec<VVal>,
1403                   env_size: usize, min_args: Option<usize>,
1404                   max_args: Option<usize>, err_arg_ok: bool, syn_pos: Option<SynPos>,
1405                   upvalue_pos: Rc<std::vec::Vec<VarPos>>,
1406                   label: VVal) -> VVal {
1407        VVal::Fun(Rc::new(VValFun {
1408            upvalue_pos,
1409            upvalues,
1410            fun: FunType::VMProg(prog),
1411            local_size: env_size,
1412            min_args,
1413            max_args,
1414            err_arg_ok,
1415            syn_pos,
1416            label
1417        }))
1418    }
1419
1420    /// Returns a dummy function that does nothing.
1421    pub fn new_dummy() -> Rc<VValFun> {
1422        Rc::new(VValFun {
1423            fun:         FunType::ClosureNode(Rc::new(RefCell::new(|_: &mut Env, _a: usize| { Ok(VVal::None) }))),
1424            upvalue_pos: Rc::new(vec![]),
1425            upvalues:    Vec::new(),
1426            local_size:  0,
1427            min_args:    None,
1428            max_args:    None,
1429            err_arg_ok:  false,
1430            syn_pos:     None,
1431            label:       VVal::None,
1432        })
1433    }
1434
1435    /// Dumps captured up values of this function. Useful only if you want to
1436    /// debug functions/closures creates by WLambda code.
1437    pub fn dump_upvals(&self) -> VVal {
1438        let v = VVal::vec();
1439        for uv in self.upvalues.iter() {
1440            v.push(uv.clone());
1441        }
1442        v
1443    }
1444}
1445
1446/// You can implement your own VVal data type and provide it
1447/// via global functions:
1448///
1449///```
1450/// use std::rc::Rc;
1451/// use std::cell::RefCell;
1452/// use wlambda::vval::Env;
1453/// use wlambda::{VVal, GlobalEnv, StackAction};
1454///
1455/// #[derive(Clone, Debug)]
1456/// struct MyType {
1457///     x: Rc<RefCell<(i64, i64)>>,
1458/// }
1459///
1460/// impl wlambda::vval::VValUserData for MyType {
1461///     fn s(&self) -> String { format!("$<MyType({:?})>", self.x.borrow()) }
1462///     fn i(&self) -> i64    { self.x.borrow_mut().1 }
1463///     fn get_key(&self, key: &str) -> Option<VVal> {
1464///         Some(VVal::new_str(key))
1465///     }
1466///     fn call_method(&self, key: &str, env: &mut Env) -> Result<VVal, StackAction> {
1467///         let args = env.argv_ref();
1468///         match key {
1469///             "test" => Ok(VVal::Int(42)),
1470///             _ => Ok(VVal::err_msg(&format!("Unknown method called: {}", key))),
1471///         }
1472///     }
1473///     fn call(&self, env: &mut Env) -> Result<VVal, StackAction> {
1474///         let args = env.argv_ref();
1475///         if args.len() < 0 {
1476///             return Err(StackAction::panic_msg(
1477///                 format!("{} called with too few arguments", self.s())));
1478///         }
1479///         Ok(args[0].clone())
1480///     }
1481///     fn as_any(&mut self) -> &mut dyn std::any::Any { self }
1482///     fn clone_ud(&self) -> Box<dyn wlambda::vval::VValUserData> {
1483///         Box::new(self.clone())
1484///     }
1485/// }
1486///
1487/// let global_env = GlobalEnv::new_default();
1488/// global_env.borrow_mut().add_func(
1489///     "new_mytype",
1490///     |_env: &mut Env, _argc: usize| {
1491///         Ok(VVal::new_usr(MyType { x: Rc::new(RefCell::new((13, 42))) }))
1492///     }, Some(0), Some(0));
1493///
1494/// global_env.borrow_mut().add_func(
1495///     "modify_mytype",
1496///     |env: &mut Env, _argc: usize| {
1497///         Ok(if let VVal::Usr(mut u) = env.arg(0) {
1498///             if let Some(ud) = u.as_any().downcast_mut::<MyType>() {
1499///                 ud.x.borrow_mut().0 += 1;
1500///                 ud.x.borrow_mut().1 *= 2;
1501///                 VVal::Int(ud.x.borrow().0 + ud.x.borrow().1)
1502///             } else {
1503///                 VVal::None
1504///             }
1505///         } else { VVal::None })
1506///     }, Some(1), Some(1));
1507///
1508/// let mut ctx = wlambda::compiler::EvalContext::new(global_env);
1509///
1510/// let r = &mut ctx.eval(r#"
1511///     !x = new_mytype[];
1512///     !i = modify_mytype x;
1513///     $[i, x]
1514/// "#).unwrap();
1515///
1516/// assert_eq!(
1517///     r.s(), "$[98,$<MyType((14, 84))>]", "Userdata implementation works");
1518///```
1519
1520/// Sometimes, if your UserData is a Rc<RefCell<...>>, it can pay off defining
1521/// some wrapper and From/Into traits for easier handling:
1522///
1523/// Here an example from a game I worked on:
1524///```
1525/// use wlambda::vval::{VVal, StackAction, VValUserData};
1526/// use std::rc::Rc;
1527/// use std::cell::RefCell;
1528///
1529/// #[derive(Clone)]
1530/// struct Ship { }
1531///
1532/// #[derive(Clone)]
1533/// struct ShipWlWrapper(Rc<RefCell<Ship>>);
1534///
1535/// impl From<Rc<RefCell<Ship>>> for ShipWlWrapper {
1536///     fn from(r: Rc<RefCell<Ship>>) -> ShipWlWrapper {
1537///         ShipWlWrapper(r)
1538///     }
1539/// }
1540///
1541/// impl Into<VVal> for ShipWlWrapper {
1542///     fn into(self) -> VVal { VVal::new_usr(self) }
1543/// }
1544///
1545/// impl VValUserData for ShipWlWrapper {
1546///     // ...
1547///     fn as_any(&mut self) -> &mut dyn std::any::Any { self }
1548///     fn clone_ud(&self) -> Box<dyn wlambda::vval::VValUserData> {
1549///         Box::new(self.clone())
1550///     }
1551/// }
1552///```
1553
1554#[allow(clippy::borrowed_box)]
1555pub trait VValUserData {
1556    /// This method should return a human readable syntax representation
1557    /// of your VValUserData.
1558    fn s(&self)     -> String { format!("$<userdata:{:p}>", self) }
1559    /// If your data has a plain string representation,
1560    /// you can return the string directly from here.
1561    fn s_raw(&self) -> String { self.s() }
1562    /// Returns the i64 representation of your data.
1563    fn i(&self)     -> i64    { -1 }
1564    /// Returns the byte representation of your data.
1565    fn byte(&self)  -> u8     { self.i() as u8 }
1566    /// Returns the char representation of your data.
1567    fn c(&self)     -> char   { std::char::from_u32(self.i() as u32).unwrap_or('?') }
1568    /// Returns the f64 representation of your data.
1569    fn f(&self)     -> f64    { self.i() as f64 }
1570    /// Returns the boolean representation of your data. Can for instance
1571    /// be used to check if your data is _valid_ or something.
1572    fn b(&self)     -> bool   { true }
1573    /// Allows you to specify how two instances of your data
1574    /// should be compared for equivalentness.
1575    fn eqv(&self, _other: &Box<dyn VValUserData>) -> bool { false }
1576    /// Should clone your user data instance. Whether you are doing
1577    /// a deep clone or a shallow clone or something else is up to you.
1578    fn clone_ud(&self) -> Box<dyn VValUserData>;
1579    /// Makes your user data act like a map. This can be useful
1580    /// for implementing your own registries or data structures.
1581    /// Implement this method for setting a key to a value.
1582    fn set_key(&self, _key: &VVal, _val: VVal) -> Result<(), StackAction> { Ok(()) }
1583    /// This method is called when the user wants to remove a key.
1584    /// Typically called when `std:delete` from the prelude is called.
1585    fn delete_key(&self, _key: &VVal) -> Result<VVal, StackAction> { Ok(VVal::None) }
1586    /// This method returns some value that your user data
1587    /// associates with the given key.
1588    fn get_key(&self, _key: &str) -> Option<VVal> { None }
1589    /// This method is called, when the user data object is used in a method call directly.
1590    /// Use this to implement convenient APIs for the user of the user data object.
1591    /// To quickly get the arguments you may use `env.argv_ref()`.
1592    fn call_method(&self, _key: &str, _env: &mut Env) -> Result<VVal, StackAction> { Ok(VVal::None) }
1593    /// This method is called when the user data is called.
1594    /// To quickly get the arguments you may use `env.argv_ref()`.
1595    fn call(&self, _env: &mut Env) -> Result<VVal, StackAction> { Ok(VVal::None) }
1596    /// This should be implemented simply by returning
1597    /// a mutable reference to the concrete type self.
1598    /// It allows you to access your data structure from inside
1599    /// a function yourself.
1600    ///
1601    /// This is a good default implementation for your struct/type:
1602    ///
1603    ///```rust,no_run,compile_fail
1604    /// fn as_any(&mut self) -> &mut dyn std::any::Any { self }
1605    ///```
1606    fn as_any(&mut self) -> &mut dyn std::any::Any;
1607
1608    /// This function is called when you try to pass a user data value
1609    /// between threads via the Atoms provided by the thread implementation
1610    /// of WLambda.
1611    ///
1612    /// You need to return something that implements the `ThreadSafeUsr` trait,
1613    /// that handles transformation into and from an `AVal`.
1614    fn as_thread_safe_usr(&mut self) -> Option<Box<dyn crate::threads::ThreadSafeUsr>> {
1615        None
1616    }
1617}
1618
1619impl std::fmt::Debug for dyn VValUserData {
1620    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1621        write!(f, "{}", self.s())
1622    }
1623}
1624
1625impl std::clone::Clone for Box<dyn VValUserData> {
1626    fn clone(&self) -> Self {
1627        (**self).clone_ud()
1628    }
1629}
1630
1631/// Handles calling of destructor functions.
1632#[derive(Debug, Clone)]
1633pub struct DropFun {
1634    pub fun: VVal,
1635}
1636
1637impl Drop for DropFun {
1638    #[allow(unused_must_use)]
1639    fn drop(&mut self) {
1640        let global = GlobalEnv::new_default();
1641        let mut e = Env::new(global);
1642        if let Err(e) = self.fun.call_internal(&mut e, 0) {
1643            eprintln!("Error in drop function: {}", e);
1644        }
1645    }
1646}
1647
1648/// This type gives the end where to add the `VVal::add` function.
1649#[derive(Debug,Clone,Copy,PartialEq)]
1650pub enum CollectionAdd {
1651    Push,
1652    Unshift,
1653}
1654
1655/// The internal distinction between a character and a byte.
1656/// They share parts of the lexical represenation and also the
1657/// semantic purspose is similar.
1658#[derive(Debug, Clone, PartialEq, PartialOrd)]
1659pub enum VValChr {
1660    Char(char),
1661    Byte(u8),
1662}
1663
1664impl std::fmt::Display for VValChr {
1665    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1666        match self {
1667            VValChr::Char(c) => write!(f, "'{}'", format_escape_char(*c, false)),
1668            VValChr::Byte(b) => write!(f, "$b'{}'",
1669                format_escape_char(
1670                    std::char::from_u32(*b as u32).unwrap_or('?'),
1671                    true)),
1672        }
1673    }
1674}
1675
1676impl VValChr {
1677    pub fn byte(&self) -> u8 {
1678        match self {
1679            VValChr::Char(c) => {
1680                let c = *c as u32;
1681                if c > 0xFF { b'?' } else { c as u8 }
1682            },
1683            VValChr::Byte(b) => *b,
1684        }
1685    }
1686
1687    pub fn c(&self) -> char {
1688        match self {
1689            VValChr::Char(c) => *c,
1690            VValChr::Byte(b) =>
1691                std::char::from_u32(*b as u32).unwrap_or('?'),
1692        }
1693    }
1694}
1695
1696/// VVal aka. VariantValue is a data structure to represent
1697/// all kinds of WLambda data structures.
1698///
1699/// It's used for the AST, for internal data and for runtime data structures.
1700#[derive(Debug, Clone)]
1701#[allow(dead_code)]
1702#[repr(u8)]
1703pub enum VVal {
1704    /// The none value, the default value of all non initialized data.
1705    None,
1706    /// The err value is a special sentinel value for representing any kind of
1707    /// application error condition. It's created using the special $e <expr> or $error <expr>
1708    /// syntax.
1709    Err(Rc<RefCell<(VVal, SynPos)>>),
1710    /// Representation of a boolean value.
1711    Bol(bool),
1712    /// Representation of an interned string aka symbol or key.
1713    Sym(Symbol),
1714    /// Representation of a single character (or byte)
1715    Chr(VValChr),
1716    /// Representation of a unicode/text string.
1717    Str(Rc<String>),
1718    /// Representation of a byte buffer.
1719    Byt(Rc<Vec<u8>>),
1720    /// Integer value
1721    Int(i64),
1722    /// Float value
1723    Flt(f64),
1724    /// A syntax node in the AST, records the position too.
1725    Syn(SynPos),
1726    /// A pair
1727    Pair(Rc<(VVal, VVal)>),
1728    /// An optional value. While VVal::None basically has the same meaning
1729    /// as "no value", an optional value provides functions a way to say
1730    /// that they don't even return none value but nothing. Yes, it sounds
1731    /// weird, and it is weird. But in case of iterator functions that
1732    /// iterate over an array you can find out whether the iterator is at
1733    /// the end or will provide more values.
1734    Opt(Option<Rc<VVal>>),
1735    /// A special internal iterator type for built in VVal data structures.
1736    Iter(Rc<RefCell<VValIter>>),
1737    /// A list (or vector) of VVals.
1738    Lst(Rc<RefCell<std::vec::Vec<VVal>>>),
1739    /// A mapping of strings to VVals.
1740    Map(Rc<RefCell<FnvHashMap<Symbol, VVal>>>),
1741    /// A function, see also [VValFun](struct.VValFun.html)
1742    Fun(Rc<VValFun>),
1743    /// A guarded VVal, that executes a given function when it is
1744    /// no longer referenced.
1745    DropFun(Rc<DropFun>),
1746    /// A numerical (mathematical) vector storing integers. See NVec for more information.
1747    FVec(Box<NVec<f64>>),
1748    /// A numerical (mathematical) vector storing floats. See NVec for more information.
1749    IVec(Box<NVec<i64>>),
1750    /// A (strong) reference to a VVal.
1751    Ref(Rc<RefCell<VVal>>),
1752    /// A hidden strong reference to a VVal. Generated either explicitly by `$&`
1753    /// or if a variable is captured by a closure.
1754    HRef(Rc<RefCell<VVal>>),
1755    /// A (weak) reference to a VVal. Might turn VVal::None anytime.
1756    WWRef(Weak<RefCell<VVal>>),
1757    /// A vval that can box some user data which can later be accessed
1758    /// from inside user supplied Rust functions via std::any::Any.
1759    Usr(Box<dyn VValUserData>),
1760}
1761impl PartialEq for VVal {
1762    fn eq(&self, rhs: &Self) -> bool {
1763        self.eqv(rhs)
1764    }
1765}
1766
1767impl std::fmt::Debug for VValFun {
1768    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
1769        write!(f, "&VValFun")
1770    }
1771}
1772
1773pub fn format_escape_char(c: char, narrow_ascii: bool) -> String {
1774    match c {
1775        '\\' => { String::from("\\\\") },
1776        '\n' => { String::from("\\n")  },
1777        '\t' => { String::from("\\t")  },
1778        '\r' => { String::from("\\r")  },
1779        '\0' => { String::from("\\0")  },
1780        '\'' => { String::from("\\'")  },
1781        '\"' => { String::from("\\\"") },
1782        _ if narrow_ascii
1783             && c.is_ascii()
1784             && (c.is_ascii_alphanumeric()
1785                 || c.is_ascii_graphic()
1786                 || c.is_ascii_punctuation()
1787                 || c == ' ') => { format!("{}", c) },
1788        _ if narrow_ascii => { format!("\\x{:02X}", c as u32) },
1789        _ if !narrow_ascii && c.is_ascii_control() => { format!("\\x{:02X}", c as u32) },
1790        _ if !narrow_ascii && c.is_control() => { c.escape_unicode().to_string() },
1791        _ => { format!("{}", c) }
1792
1793    }
1794}
1795
1796pub fn format_vval_str(s: &str, narrow_ascii: bool) -> String {
1797    // TODO: FIXME: Use writers to write into a buffered writer.
1798    let mut v : Vec<String> =
1799        s.chars().map(|c| { format_escape_char(c, narrow_ascii) }).collect();
1800    v.insert(0, String::from("\""));
1801    v.push(String::from("\""));
1802    v.concat()
1803}
1804
1805pub fn format_vval_byt(v: &[u8]) -> String {
1806    let mut s = String::from("");
1807    for b in v.iter() {
1808        s.push(*b as char);
1809    }
1810    format_vval_str(&s, true)
1811}
1812
1813struct CycleCheck {
1814    refs: FnvHashMap<i64, i64>,
1815    backref_counter: i64,
1816}
1817
1818impl CycleCheck {
1819    fn new() -> Self {
1820        CycleCheck {
1821            refs: FnvHashMap::with_capacity_and_hasher(2, Default::default()),
1822            backref_counter: 1,
1823        }
1824    }
1825
1826    fn touch_walk(&mut self, v: &VVal) {
1827        if self.touch(v).is_some() { return; }
1828
1829        match v {
1830            VVal::Err(e) => self.touch_walk(&(*e).borrow().0),
1831            VVal::Pair(b) => {
1832                self.touch_walk(&b.0);
1833                self.touch_walk(&b.1);
1834            },
1835            VVal::Opt(b) => {
1836                if let Some(x) = b {
1837                    self.touch_walk(x);
1838                }
1839            },
1840            VVal::Lst(l) => {
1841                for v in l.borrow().iter() { self.touch_walk(v); }
1842            },
1843            VVal::Map(l) => {
1844                for (_k, v) in l.borrow().iter() { self.touch_walk(v); }
1845            },
1846            VVal::DropFun(f) => {
1847                if let VVal::Fun(f) = &f.fun {
1848                    for v in f.upvalues.iter() {
1849                        self.touch_walk(v);
1850                    }
1851                }
1852            },
1853            VVal::Fun(f) => {
1854                for v in f.upvalues.iter() {
1855                    self.touch_walk(v);
1856                }
1857            },
1858            VVal::Ref(l)   => { self.touch_walk(&(*l).borrow()); },
1859            VVal::HRef(l)  => { self.touch_walk(&(*l).borrow()); },
1860            VVal::WWRef(l) => {
1861                if let Some(v) = l.upgrade() {
1862                    self.touch_walk(&(*v).borrow());
1863                }
1864            },
1865              VVal::Str(_)
1866            | VVal::Byt(_)
1867            | VVal::None
1868            | VVal::Bol(_)
1869            | VVal::Sym(_)
1870            | VVal::Syn(_)
1871            | VVal::Iter(_)
1872            | VVal::FVec(_)
1873            | VVal::IVec(_)
1874            | VVal::Int(_)
1875            | VVal::Flt(_)
1876            | VVal::Chr(_)
1877            | VVal::Usr(_) => {},
1878        }
1879    }
1880
1881    fn touch(&mut self, v: &VVal) -> Option<i64> {
1882        let id = v.ref_id()?;
1883
1884        if let Some(backref) = self.refs.get(&id) {
1885            if *backref == 0 {
1886                let bkr_count = self.backref_counter;
1887                self.backref_counter += 1;
1888                self.refs.insert(id, bkr_count);
1889                Some(bkr_count)
1890            } else {
1891                Some(*backref)
1892            }
1893        } else {
1894            self.refs.insert(id, 0);
1895            None
1896        }
1897    }
1898
1899    fn backref(&mut self, v: &VVal) -> Option<(bool, String)> {
1900        // Do not generate back refs for symbols. they are interned
1901        // anyways!
1902        if let VVal::Sym(_) = v { return None; }
1903
1904        let id = v.ref_id()?;
1905
1906        if let Some(backref) = self.refs.get(&id) {
1907            match *backref {
1908                br if br > 0 => {
1909                    self.refs.insert(id, -br);
1910                    Some((true, format!("$<{}=>", br)))
1911                },
1912                br if br < 0 =>
1913                    Some((false, format!("$<{}>", -br))),
1914                _ => None,
1915            }
1916        } else {
1917            None
1918        }
1919    }
1920}
1921
1922pub type VValIter =
1923    std::iter::FromFn<Box<dyn FnMut() -> Option<(VVal, Option<VVal>)>>>;
1924
1925macro_rules! swizzle_char2value {
1926    ($c: expr, $i: expr, $x: ident, $y: ident, $z: ident, $w: ident) => (
1927        match $c.chars().nth($i).unwrap_or(' ') {
1928            'r' => $x,
1929            'g' => $y,
1930            'b' => $z,
1931            'a' => $w,
1932            'h' => $x,
1933            's' => $y,
1934            'v' => $z,
1935            '0' => $x,
1936            '1' => $y,
1937            '2' => $z,
1938            '3' => $w,
1939            'x' => $x,
1940            'y' => $y,
1941            'z' => $z,
1942            'w' => $w,
1943            _ => return VVal::None,
1944        }
1945    )
1946}
1947
1948#[allow(clippy::many_single_char_names)]
1949fn swizzle_i(s: &str, x: i64, y: i64, z: i64, w: i64) -> VVal {
1950    match s.len() {
1951        2 =>
1952            VVal::IVec(Box::new(NVec::Vec2(
1953                swizzle_char2value!(s, 0, x, y, z, w),
1954                swizzle_char2value!(s, 1, x, y, z, w)))),
1955        3 =>
1956            VVal::IVec(Box::new(NVec::Vec3(
1957                swizzle_char2value!(s, 0, x, y, z, w),
1958                swizzle_char2value!(s, 1, x, y, z, w),
1959                swizzle_char2value!(s, 2, x, y, z, w)))),
1960        4 =>
1961            VVal::IVec(Box::new(NVec::Vec4(
1962                swizzle_char2value!(s, 0, x, y, z, w),
1963                swizzle_char2value!(s, 1, x, y, z, w),
1964                swizzle_char2value!(s, 2, x, y, z, w),
1965                swizzle_char2value!(s, 3, x, y, z, w)))),
1966        _ => VVal::None,
1967    }
1968}
1969
1970#[allow(clippy::many_single_char_names)]
1971fn swizzle_f(s: &str, x: f64, y: f64, z: f64, w: f64) -> VVal {
1972    match s.len() {
1973        2 =>
1974            VVal::FVec(Box::new(NVec::Vec2(
1975                swizzle_char2value!(s, 0, x, y, z, w),
1976                swizzle_char2value!(s, 1, x, y, z, w)))),
1977        3 =>
1978            VVal::FVec(Box::new(NVec::Vec3(
1979                swizzle_char2value!(s, 0, x, y, z, w),
1980                swizzle_char2value!(s, 1, x, y, z, w),
1981                swizzle_char2value!(s, 2, x, y, z, w)))),
1982        4 =>
1983            VVal::FVec(Box::new(NVec::Vec4(
1984                swizzle_char2value!(s, 0, x, y, z, w),
1985                swizzle_char2value!(s, 1, x, y, z, w),
1986                swizzle_char2value!(s, 2, x, y, z, w),
1987                swizzle_char2value!(s, 3, x, y, z, w)))),
1988        _ => VVal::None,
1989    }
1990}
1991
1992macro_rules! iter_next {
1993    ($i: expr) => {
1994        if let Some((v, k)) = $i.next() {
1995            if let Some(k) = k {
1996                VVal::opt(VVal::pair(v, k))
1997            } else {
1998                VVal::opt(v)
1999            }
2000        } else {
2001            VVal::opt_none()
2002        }
2003    }
2004}
2005
2006macro_rules! iter_next_value {
2007    ($i: expr, $v: ident, $conv: block, $def: expr) => {
2008        if let Some(($v, _)) = $i.next() { $conv } else { $def }
2009    }
2010}
2011
2012macro_rules! iter_int_a_to_b {
2013    ($a: expr, $b: expr) => {
2014        {
2015            let mut i = $a;
2016            let b = $b;
2017            std::iter::from_fn(Box::new(move || {
2018                if i >= b { return None; }
2019                let ret = Some((VVal::Int(i), None));
2020                i += 1;
2021                ret
2022            }))
2023        }
2024    }
2025}
2026
2027macro_rules! pair_key_to_iter {
2028    ($p: ident) => {
2029        if let VVal::Iter(ai) = &$p.0 {
2030            let ai = ai.clone();
2031
2032            if let VVal::Iter(bi) = &$p.1 {
2033                let bi = bi.clone();
2034
2035                std::iter::from_fn(Box::new(move || {
2036                    let a = ai.borrow_mut().next();
2037                    if let Some((a, ak)) = a {
2038                        let a =
2039                            if let Some(ak) = ak {
2040                                VVal::pair(a, ak)
2041                            } else {
2042                                a
2043                            };
2044
2045                        let b = bi.borrow_mut().next();
2046                        if let Some((b, bk)) = b {
2047                            let b =
2048                                if let Some(bk) = bk {
2049                                    VVal::pair(b, bk)
2050                                } else {
2051                                    b
2052                                };
2053
2054                            Some((a, Some(b)))
2055                        } else {
2056                            None
2057                        }
2058                    } else {
2059                        None
2060                    }
2061                }))
2062            } else {
2063                let mut bi = $p.1.iter();
2064                std::iter::from_fn(Box::new(move || {
2065                    let a = ai.borrow_mut().next();
2066                    if let Some((a, ak)) = a {
2067                        let a =
2068                            if let Some(ak) = ak {
2069                                VVal::pair(a, ak)
2070                            } else {
2071                                a
2072                            };
2073
2074                        if let Some((b, bk)) = bi.next() {
2075                            let b =
2076                                if let Some(bk) = bk {
2077                                    VVal::pair(b, bk)
2078                                } else {
2079                                    b
2080                                };
2081
2082                            Some((VVal::pair(a, b), None))
2083                        } else {
2084                            None
2085                        }
2086                    } else {
2087                        None
2088                    }
2089                }))
2090            }
2091        } else if $p.0.is_int() {
2092            iter_int_a_to_b!($p.0.i(), $p.1.i())
2093
2094        } else {
2095            $p.0.with_s_ref(|key: &str| -> VValIter {
2096                let l =
2097                    match &key[..] {
2098                        "keys"      => $p.1.keys(),
2099                        "values"    => $p.1.values(),
2100                        "enumerate" => $p.1.enumerate(),
2101                        _ => {
2102                            return std::iter::from_fn(
2103                                Box::new(move || { None }))
2104                        }
2105                    };
2106                if let VVal::Lst(l) = l {
2107                    let l = l.clone();
2108                    let mut idx = 0;
2109                    std::iter::from_fn(Box::new(move || {
2110                        if idx >= l.borrow().len() {
2111                            return None;
2112                        }
2113                        let r = Some((l.borrow()[idx].clone(), None));
2114                        idx += 1;
2115                        r
2116                    }))
2117                } else {
2118                    std::iter::from_fn(Box::new(move || { None }))
2119                }
2120            })
2121        }
2122    }
2123}
2124
2125#[allow(clippy::cognitive_complexity)]
2126#[allow(clippy::comparison_chain)]
2127#[allow(clippy::while_let_on_iterator)]
2128fn range_extract(from: i64, cnt: i64, val: &VVal) -> VVal {
2129    match val {
2130        VVal::Chr(VValChr::Char(c)) => {
2131            let c = *c as i64;
2132            VVal::Bol(from <= c && cnt >= c)
2133        },
2134        VVal::Chr(VValChr::Byte(c)) => {
2135            let c = *c as i64;
2136            VVal::Bol(from <= c && cnt >= c)
2137        },
2138        VVal::Byt(s) => {
2139            VVal::new_byt(
2140                s.iter()
2141                 .skip(from as usize)
2142                 .take(cnt as usize).copied().collect())
2143        },
2144        VVal::Str(s) => {
2145            VVal::new_str_mv(
2146                s.chars()
2147                 .skip(from as usize)
2148                 .take(cnt as usize).collect())
2149        },
2150        VVal::IVec(b) => {
2151            let mut out = vec![];
2152            match b.as_ref() {
2153                NVec::Vec2(a, b) => {
2154                    if cnt == 1 {
2155                        match from {
2156                            0 => out.push(VVal::Int(*a)),
2157                            1 => out.push(VVal::Int(*b)),
2158                            _ => (),
2159                        }
2160                    } else if cnt > 1 {
2161                        match from {
2162                            0 => {
2163                                out.push(VVal::Int(*a));
2164                                out.push(VVal::Int(*b));
2165                            },
2166                            1 => out.push(VVal::Int(*b)),
2167                            _ => (),
2168                        }
2169                    }
2170                },
2171                NVec::Vec3(a, b, c) => {
2172                    if cnt == 1 {
2173                        match from {
2174                            0 => out.push(VVal::Int(*a)),
2175                            1 => out.push(VVal::Int(*b)),
2176                            2 => out.push(VVal::Int(*c)),
2177                            _ => (),
2178                        }
2179                    } else if cnt == 2 {
2180                        match from {
2181                            0 => {
2182                                out.push(VVal::Int(*a));
2183                                out.push(VVal::Int(*b));
2184                            },
2185                            1 => {
2186                                out.push(VVal::Int(*b));
2187                                out.push(VVal::Int(*c));
2188                            },
2189                            2 => {
2190                                out.push(VVal::Int(*c));
2191                            },
2192                            _ => (),
2193                        }
2194                    } else if cnt > 2 {
2195                        match from {
2196                            0 => {
2197                                out.push(VVal::Int(*a));
2198                                out.push(VVal::Int(*b));
2199                                out.push(VVal::Int(*c));
2200                            },
2201                            1 => {
2202                                out.push(VVal::Int(*b));
2203                                out.push(VVal::Int(*c));
2204                            }
2205                            2 => out.push(VVal::Int(*c)),
2206                            _ => (),
2207                        }
2208                    }
2209                },
2210                NVec::Vec4(a, b, c, d) => {
2211                    if cnt == 1 {
2212                        match from {
2213                            0 => out.push(VVal::Int(*a)),
2214                            1 => out.push(VVal::Int(*b)),
2215                            2 => out.push(VVal::Int(*c)),
2216                            3 => out.push(VVal::Int(*d)),
2217                            _ => (),
2218                        }
2219                    } else if cnt == 2 {
2220                        match from {
2221                            0 => {
2222                                out.push(VVal::Int(*a));
2223                                out.push(VVal::Int(*b));
2224                            },
2225                            1 => {
2226                                out.push(VVal::Int(*b));
2227                                out.push(VVal::Int(*c));
2228                            },
2229                            2 => {
2230                                out.push(VVal::Int(*c));
2231                                out.push(VVal::Int(*d));
2232                            },
2233                            3 => {
2234                                out.push(VVal::Int(*d));
2235                            },
2236                            _ => (),
2237                        }
2238                    } else if cnt == 3 {
2239                        match from {
2240                            0 => {
2241                                out.push(VVal::Int(*a));
2242                                out.push(VVal::Int(*b));
2243                                out.push(VVal::Int(*c));
2244                            },
2245                            1 => {
2246                                out.push(VVal::Int(*b));
2247                                out.push(VVal::Int(*c));
2248                                out.push(VVal::Int(*d));
2249                            },
2250                            2 => {
2251                                out.push(VVal::Int(*c));
2252                                out.push(VVal::Int(*d));
2253                            },
2254                            3 => {
2255                                out.push(VVal::Int(*d));
2256                            },
2257                            _ => (),
2258                        }
2259                    } else if cnt > 2 {
2260                        match from {
2261                            0 => {
2262                                out.push(VVal::Int(*a));
2263                                out.push(VVal::Int(*b));
2264                                out.push(VVal::Int(*c));
2265                                out.push(VVal::Int(*d));
2266                            },
2267                            1 => {
2268                                out.push(VVal::Int(*b));
2269                                out.push(VVal::Int(*c));
2270                                out.push(VVal::Int(*d));
2271                            },
2272                            2 => {
2273                                out.push(VVal::Int(*c));
2274                                out.push(VVal::Int(*d));
2275                            },
2276                            3 => {
2277                                out.push(VVal::Int(*d));
2278                            },
2279                            _ => (),
2280                        }
2281                    }
2282                }
2283            }
2284
2285            VVal::vec_mv(out)
2286        },
2287        VVal::FVec(b) => {
2288            let mut out = vec![];
2289            match b.as_ref() {
2290                NVec::Vec2(a, b) => {
2291                    if cnt == 1 {
2292                        match from {
2293                            0 => out.push(VVal::Flt(*a)),
2294                            1 => out.push(VVal::Flt(*b)),
2295                            _ => (),
2296                        }
2297                    } else if cnt > 1 {
2298                        match from {
2299                            0 => {
2300                                out.push(VVal::Flt(*a));
2301                                out.push(VVal::Flt(*b));
2302                            },
2303                            1 => out.push(VVal::Flt(*b)),
2304                            _ => (),
2305                        }
2306                    }
2307                },
2308                NVec::Vec3(a, b, c) => {
2309                    if cnt == 1 {
2310                        match from {
2311                            0 => out.push(VVal::Flt(*a)),
2312                            1 => out.push(VVal::Flt(*b)),
2313                            2 => out.push(VVal::Flt(*c)),
2314                            _ => (),
2315                        }
2316                    } else if cnt == 2 {
2317                        match from {
2318                            0 => {
2319                                out.push(VVal::Flt(*a));
2320                                out.push(VVal::Flt(*b));
2321                            },
2322                            1 => {
2323                                out.push(VVal::Flt(*b));
2324                                out.push(VVal::Flt(*c));
2325                            },
2326                            2 => {
2327                                out.push(VVal::Flt(*c));
2328                            },
2329                            _ => (),
2330                        }
2331                    } else if cnt > 2 {
2332                        match from {
2333                            0 => {
2334                                out.push(VVal::Flt(*a));
2335                                out.push(VVal::Flt(*b));
2336                                out.push(VVal::Flt(*c));
2337                            },
2338                            1 => {
2339                                out.push(VVal::Flt(*b));
2340                                out.push(VVal::Flt(*c));
2341                            }
2342                            2 => out.push(VVal::Flt(*c)),
2343                            _ => (),
2344                        }
2345                    }
2346                },
2347                NVec::Vec4(a, b, c, d) => {
2348                    if cnt == 1 {
2349                        match from {
2350                            0 => out.push(VVal::Flt(*a)),
2351                            1 => out.push(VVal::Flt(*b)),
2352                            2 => out.push(VVal::Flt(*c)),
2353                            3 => out.push(VVal::Flt(*d)),
2354                            _ => (),
2355                        }
2356                    } else if cnt == 2 {
2357                        match from {
2358                            0 => {
2359                                out.push(VVal::Flt(*a));
2360                                out.push(VVal::Flt(*b));
2361                            },
2362                            1 => {
2363                                out.push(VVal::Flt(*b));
2364                                out.push(VVal::Flt(*c));
2365                            },
2366                            2 => {
2367                                out.push(VVal::Flt(*c));
2368                                out.push(VVal::Flt(*d));
2369                            },
2370                            3 => {
2371                                out.push(VVal::Flt(*d));
2372                            },
2373                            _ => (),
2374                        }
2375                    } else if cnt == 3 {
2376                        match from {
2377                            0 => {
2378                                out.push(VVal::Flt(*a));
2379                                out.push(VVal::Flt(*b));
2380                                out.push(VVal::Flt(*c));
2381                            },
2382                            1 => {
2383                                out.push(VVal::Flt(*b));
2384                                out.push(VVal::Flt(*c));
2385                                out.push(VVal::Flt(*d));
2386                            },
2387                            2 => {
2388                                out.push(VVal::Flt(*c));
2389                                out.push(VVal::Flt(*d));
2390                            },
2391                            3 => {
2392                                out.push(VVal::Flt(*d));
2393                            },
2394                            _ => (),
2395                        }
2396                    } else if cnt > 2 {
2397                        match from {
2398                            0 => {
2399                                out.push(VVal::Flt(*a));
2400                                out.push(VVal::Flt(*b));
2401                                out.push(VVal::Flt(*c));
2402                                out.push(VVal::Flt(*d));
2403                            },
2404                            1 => {
2405                                out.push(VVal::Flt(*b));
2406                                out.push(VVal::Flt(*c));
2407                                out.push(VVal::Flt(*d));
2408                            },
2409                            2 => {
2410                                out.push(VVal::Flt(*c));
2411                                out.push(VVal::Flt(*d));
2412                            },
2413                            3 => {
2414                                out.push(VVal::Flt(*d));
2415                            },
2416                            _ => (),
2417                        }
2418                    }
2419                }
2420            }
2421
2422            VVal::vec_mv(out)
2423        },
2424        VVal::Lst(l) => {
2425            let v : Vec<VVal> =
2426                l.borrow()
2427                 .iter()
2428                 .skip(from as usize)
2429                 .take(cnt as usize)
2430                 .cloned()
2431                 .collect();
2432            VVal::vec_mv(v)
2433        },
2434        VVal::Iter(i) => {
2435            let mut out = Vec::with_capacity(cnt as usize);
2436            let mut i = i.borrow_mut();
2437            let mut idx = 0;
2438            while let Some((v, _)) = i.next() {
2439                if idx >= (from as usize) && idx < ((from + cnt) as usize) {
2440                    out.push(v);
2441                }
2442                idx += 1;
2443            }
2444            VVal::vec_mv(out)
2445        },
2446        _ => VVal::None,
2447    }
2448}
2449
2450
2451fn pair_extract(a: &VVal, b: &VVal, val: &VVal) -> VVal {
2452    match val {
2453        VVal::Int(i) =>
2454            if i % 2 == 0 { a.clone() }
2455            else          { b.clone() },
2456        VVal::Byt(_) => {
2457            match (a, b) {
2458                (VVal::Int(from), VVal::Int(cnt)) => {
2459                    range_extract(*from, *cnt, val)
2460                },
2461                (VVal::Int(start_idx), b) if b.is_sym() || b.is_str() || b.is_byte() || b.is_char() || b.is_bytes() => {
2462                    val.find(b, *start_idx as usize, true)
2463                },
2464                (VVal::Chr(_splitstr), VVal::Int(max)) => {
2465                    val.split(a, *max as usize, true)
2466                },
2467                (VVal::Str(_splitstr), VVal::Int(max)) => {
2468                    val.split(a, *max as usize, true)
2469                },
2470                (VVal::Byt(_splitstr), VVal::Int(max)) => {
2471                    val.split(a, *max as usize, true)
2472                },
2473                (VVal::Str(_needle), b) if b.is_sym() || b.is_str() || b.is_byte() || b.is_char() || b.is_bytes() => {
2474                    val.bytes_replace(a, b)
2475                },
2476                (VVal::Byt(_needle), b) if b.is_sym() || b.is_str() || b.is_byte() || b.is_char() || b.is_bytes() => {
2477                    val.bytes_replace(a, b)
2478                },
2479                (VVal::Chr(_needle), b) if b.is_sym() || b.is_str() || b.is_byte() || b.is_char() || b.is_bytes() => {
2480                    val.bytes_replace(a, b)
2481                },
2482                _ => VVal::None
2483            }
2484        },
2485        VVal::Str(s) => {
2486            match (a, b) {
2487                (VVal::Int(from), VVal::Int(cnt)) => {
2488                    range_extract(*from, *cnt, val)
2489                },
2490                (VVal::Int(start_idx), b) if b.is_sym() || b.is_str() || b.is_byte() || b.is_char() || b.is_bytes() => {
2491                    val.find(b, *start_idx as usize, false)
2492                },
2493                (VVal::Chr(_splitstr), VVal::Int(max)) => {
2494                    val.split(a, *max as usize, false)
2495                },
2496                (VVal::Byt(_splitstr), VVal::Int(max)) => {
2497                    val.split(a, *max as usize, false)
2498                },
2499                (VVal::Str(_splitstr), VVal::Int(max)) => {
2500                    val.split(a, *max as usize, false)
2501                },
2502                (VVal::Chr(needle), VVal::Chr(replace)) => {
2503                    let mut buf = [0; 6];
2504                    let chrstr = replace.c().encode_utf8(&mut buf);
2505                    VVal::new_str_mv(
2506                        s.as_ref()
2507                         .replace(needle.c(), chrstr))
2508                },
2509                (VVal::Str(needle), VVal::Str(replace)) => {
2510                    VVal::new_str_mv(
2511                        s.as_ref()
2512                         .replace(
2513                            needle.as_ref(), replace.as_ref()))
2514                },
2515                _ => VVal::None
2516            }
2517        },
2518        VVal::Lst(_) => {
2519            match (a, b) {
2520                (VVal::Int(from), VVal::Int(cnt)) => {
2521                    range_extract(*from, *cnt, val)
2522                },
2523                _ => VVal::None,
2524            }
2525        },
2526        VVal::Iter(_) => {
2527            match (a, b) {
2528                (VVal::Int(from), VVal::Int(cnt)) => {
2529                    range_extract(*from, *cnt, val)
2530                },
2531                _ => VVal::None,
2532            }
2533        },
2534        VVal::IVec(_) => {
2535            match (a, b) {
2536                (VVal::Int(from), VVal::Int(cnt)) => {
2537                    range_extract(*from, *cnt, val)
2538                },
2539                _ => VVal::None,
2540            }
2541        },
2542        VVal::FVec(_) => {
2543            match (a, b) {
2544                (VVal::Int(from), VVal::Int(cnt)) => {
2545                    range_extract(*from, *cnt, val)
2546                },
2547                _ => VVal::None,
2548            }
2549        },
2550        VVal::Chr(VValChr::Byte(c)) => {
2551            match (a, b) {
2552                (VVal::Chr(from), VVal::Chr(to)) => {
2553                    let a = from.c() as u32;
2554                    let b = to.c()   as u32;
2555                    let c = *c       as u32;
2556                    VVal::Bol(a <= c && b >= c)
2557                },
2558                (VVal::Int(a), VVal::Int(b)) => {
2559                    let c = *c as i64;
2560                    VVal::Bol(*a <= c && *b >= c)
2561                },
2562                _ => VVal::None,
2563            }
2564        },
2565        VVal::Chr(VValChr::Char(c)) => {
2566            match (a, b) {
2567                (VVal::Chr(from), VVal::Chr(to)) => {
2568                    let a = from.c() as u32;
2569                    let b = to.c()   as u32;
2570                    let c = *c       as u32;
2571                    VVal::Bol(a <= c && b >= c)
2572                },
2573                (VVal::Int(a), VVal::Int(b)) => {
2574                    let c = *c as i64;
2575                    VVal::Bol(*a <= c && *b >= c)
2576                },
2577                _ => VVal::None,
2578            }
2579        },
2580        _ => VVal::None
2581    }
2582}
2583
2584fn vval_rc_ptr_eq(v: &VVal, l: &Rc<RefCell<VVal>>) -> bool {
2585    match v {
2586        VVal::Ref(r2)   => Rc::ptr_eq(l, r2),
2587        VVal::HRef(r2)  => Rc::ptr_eq(l, r2),
2588        VVal::WWRef(r2) =>
2589            match r2.upgrade() {
2590                Some(v2) => Rc::ptr_eq(l, &v2),
2591                None => false,
2592            },
2593        _ => false,
2594    }
2595}
2596
2597fn concat_operation(bytes: bool, first: &VVal, argc: usize, env: &mut Env) -> Result<VVal, StackAction> {
2598    if bytes {
2599        let mut buf = first.with_bv_ref(|bv| bv.to_vec());
2600        for i in 0..argc {
2601            env.arg_ref(i).unwrap().with_bv_ref(|bv|
2602                buf.extend_from_slice(bv));
2603        }
2604        Ok(VVal::new_byt(buf))
2605    } else {
2606        let mut st = first.with_s_ref(|s: &str| String::from(s));
2607        for i in 0..argc {
2608            env.arg_ref(i).unwrap().with_s_ref(|s: &str| st += s);
2609        }
2610        Ok(VVal::new_str_mv(st))
2611    }
2612
2613}
2614
2615#[allow(dead_code)]
2616impl VVal {
2617    #[inline]
2618    pub fn new_str(s: &str) -> VVal {
2619        VVal::Str(Rc::new(String::from(s)))
2620    }
2621
2622    #[inline]
2623    pub fn new_str_mv(s: String) -> VVal {
2624        VVal::Str(Rc::new(s))
2625    }
2626
2627    #[inline]
2628    pub fn new_char(c: char) -> VVal {
2629        VVal::Chr(VValChr::Char(c))
2630    }
2631
2632    #[inline]
2633    pub fn new_byte(b: u8) -> VVal {
2634        VVal::Chr(VValChr::Byte(b))
2635    }
2636
2637    #[inline]
2638    pub fn new_sym(s: &str) -> VVal {
2639        VVal::Sym(s2sym(s))
2640    }
2641
2642    #[inline]
2643    pub fn new_sym_mv(s: String) -> VVal {
2644        VVal::Sym(new_sym_mv(s))
2645    }
2646
2647    #[inline]
2648    pub fn new_byt(v: Vec<u8>) -> VVal {
2649        VVal::Byt(Rc::new(v))
2650    }
2651
2652    #[inline]
2653    pub fn err(v: VVal, pos: SynPos) -> VVal {
2654        VVal::Err(Rc::new(RefCell::new((v, pos))))
2655    }
2656
2657    pub fn err_msg(s: &str) -> VVal {
2658        VVal::Err(Rc::new(RefCell::new(
2659            (VVal::new_str(s), SynPos::empty()))))
2660    }
2661
2662    pub fn new_usr<T: VValUserData + 'static>(o: T) -> VVal {
2663        VVal::Usr(Box::new(o))
2664    }
2665
2666    #[inline]
2667    pub fn ivec2(x: i64, y: i64) -> VVal {
2668        VVal::IVec(Box::new(NVec::Vec2(x, y)))
2669    }
2670
2671    #[inline]
2672    pub fn ivec3(x: i64, y: i64, z: i64) -> VVal {
2673        VVal::IVec(Box::new(NVec::Vec3(x, y, z)))
2674    }
2675
2676    #[inline]
2677    pub fn ivec4(x: i64, y: i64, z: i64, w: i64) -> VVal {
2678        VVal::IVec(Box::new(NVec::Vec4(x, y, z, w)))
2679    }
2680
2681    #[inline]
2682    pub fn fvec2(x: f64, y: f64) -> VVal {
2683        VVal::FVec(Box::new(NVec::Vec2(x, y)))
2684    }
2685
2686    #[inline]
2687    pub fn fvec3(x: f64, y: f64, z: f64) -> VVal {
2688        VVal::FVec(Box::new(NVec::Vec3(x, y, z)))
2689    }
2690
2691    #[inline]
2692    pub fn fvec4(x: f64, y: f64, z: f64, w: f64) -> VVal {
2693        VVal::FVec(Box::new(NVec::Vec4(x, y, z, w)))
2694    }
2695
2696    pub fn ivec_from_tpl2(tpl: (i64, i64)) -> VVal {
2697        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, None, None)) {
2698            VVal::IVec(Box::new(nv))
2699        } else {
2700            VVal::None
2701        }
2702    }
2703
2704    pub fn ivec_from_tpl3(tpl: (i64, i64, i64)) -> VVal {
2705        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, Some(tpl.2), None)) {
2706            VVal::IVec(Box::new(nv))
2707        } else {
2708            VVal::None
2709        }
2710    }
2711
2712    pub fn ivec_from_tpl4(tpl: (i64, i64, i64, i64)) -> VVal {
2713        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, Some(tpl.2), Some(tpl.3))) {
2714            VVal::IVec(Box::new(nv))
2715        } else {
2716            VVal::None
2717        }
2718    }
2719
2720    pub fn fvec_from_tpl2(tpl: (f64, f64)) -> VVal {
2721        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, None, None)) {
2722            VVal::FVec(Box::new(nv))
2723        } else {
2724            VVal::None
2725        }
2726    }
2727
2728    pub fn fvec_from_tpl3(tpl: (f64, f64, f64)) -> VVal {
2729        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, Some(tpl.2), None)) {
2730            VVal::FVec(Box::new(nv))
2731        } else {
2732            VVal::None
2733        }
2734    }
2735
2736    pub fn fvec_from_tpl4(tpl: (f64, f64, f64, f64)) -> VVal {
2737        if let Some(nv) = NVec::from_tpl((tpl.0, tpl.1, Some(tpl.2), Some(tpl.3))) {
2738            VVal::FVec(Box::new(nv))
2739        } else {
2740            VVal::None
2741        }
2742    }
2743
2744    #[inline]
2745    pub fn vec() -> VVal {
2746        VVal::Lst(Rc::new(RefCell::new(Vec::new())))
2747    }
2748
2749    #[inline]
2750    pub fn vec1(a: VVal) -> VVal {
2751        let v = Self::vec();
2752        v.push(a);
2753        v
2754    }
2755
2756    #[inline]
2757    pub fn vec2(a: VVal, b: VVal) -> VVal {
2758        let v = Self::vec();
2759        v.push(a);
2760        v.push(b);
2761        v
2762    }
2763
2764    #[inline]
2765    pub fn vec3(a: VVal, b: VVal, c: VVal) -> VVal {
2766        let v = Self::vec();
2767        v.push(a);
2768        v.push(b);
2769        v.push(c);
2770        v
2771    }
2772
2773    #[inline]
2774    #[allow(clippy::many_single_char_names)]
2775    pub fn vec4(a: VVal, b: VVal, c: VVal, d: VVal) -> VVal {
2776        let v = Self::vec();
2777        v.push(a);
2778        v.push(b);
2779        v.push(c);
2780        v.push(d);
2781        v
2782    }
2783
2784    #[inline]
2785    pub fn opt(v: VVal) -> VVal {
2786        VVal::Opt(Some(Rc::new(v)))
2787    }
2788
2789    #[inline]
2790    pub fn opt_none() -> VVal { VVal::Opt(None) }
2791
2792    #[inline]
2793    pub fn unwrap_opt(&self) -> VVal {
2794        if let VVal::Opt(Some(o)) = self {
2795            o.as_ref().clone()
2796        } else {
2797            VVal::None
2798        }
2799    }
2800
2801    /// Creates a pair from two VVals.
2802    #[inline]
2803    pub fn pair(a: VVal, b: VVal) -> VVal {
2804        VVal::Pair(Rc::new((a, b)))
2805    }
2806
2807    /// Returns an iterator of the current value.
2808    pub fn as_iter(&self) -> VVal {
2809        VVal::Iter(Rc::new(RefCell::new(self.iter())))
2810    }
2811
2812    pub fn to_vec(&self) -> Vec<VVal> {
2813        if let VVal::Lst(l) = self {
2814            let r : Vec<VVal> = l.borrow_mut().iter().cloned().collect();
2815            r
2816        } else {
2817            vec![self.clone()]
2818        }
2819    }
2820
2821    pub fn vec_from(vl: &[VVal]) -> VVal {
2822        let mut v = Vec::new();
2823        v.extend_from_slice(vl);
2824        VVal::Lst(Rc::new(RefCell::new(v)))
2825    }
2826
2827    pub fn vec_mv(v: Vec<VVal>) -> VVal {
2828        VVal::Lst(Rc::new(RefCell::new(v)))
2829    }
2830
2831    /// Creates a new WLambda function that wraps the given Rust
2832    /// closure. See also `VValFun::new_fun`. For a more detailed
2833    /// discussion of the parameters.
2834    ///
2835    ///```rust
2836    /// use wlambda::compiler::EvalContext;
2837    /// use wlambda::vval::{VVal, VValFun, Env};
2838    ///
2839    /// let mut ctx = wlambda::compiler::EvalContext::new_empty_global_env();
2840    ///
2841    /// ctx.set_global_var("xyz",
2842    ///     &VVal::new_fun(
2843    ///         move |env: &mut Env, argc: usize| {
2844    ///             Ok(VVal::new_str("xyz"))
2845    ///         }, None, None, false));
2846    ///
2847    /// assert_eq!(ctx.eval("xyz[]").unwrap().s_raw(), "xyz")
2848    ///```
2849    pub fn new_fun<T>(fun: T, min_args: Option<usize>,
2850                      max_args: Option<usize>,
2851                      err_arg_ok: bool) -> VVal
2852        where T: 'static + Fn(&mut Env, usize) -> Result<VVal, StackAction> {
2853
2854        VValFun::new_val(
2855            Rc::new(RefCell::new(fun)),
2856            Vec::new(),
2857            0, min_args, max_args, err_arg_ok, None,
2858            Rc::new(vec![]))
2859    }
2860
2861    pub fn call(&self, env: &mut Env, args: &[VVal]) -> Result<VVal, StackAction> {
2862        let argc = args.len();
2863        for v in args.iter() {
2864            env.push(v.clone());
2865        }
2866        let ret = self.call_internal(env, argc);
2867        env.popn(argc);
2868        ret
2869    }
2870
2871    pub fn compare_str(&self, b: &VVal) -> std::cmp::Ordering {
2872        self.with_s_ref(|a: &str| b.with_s_ref(|b: &str| a.cmp(b)))
2873    }
2874
2875    pub fn shallow_clone(&self) -> VVal {
2876        match self {
2877            VVal::Lst(l) => {
2878                let out = VVal::vec();
2879                for v in l.borrow().iter() { out.push(v.clone()); }
2880                out
2881            },
2882            VVal::Map(m) => {
2883                let out = VVal::map();
2884                for (k, v) in m.borrow_mut().iter() {
2885                    if out.set_key_sym(k.clone(), v.clone()).is_err() {
2886                        continue;
2887                    }
2888                }
2889                out
2890            },
2891            VVal::Str(s) => {
2892                VVal::new_str_mv(s.as_ref().clone())
2893            },
2894            v => v.with_deref(
2895                |v| v.shallow_clone(),
2896                |v| if let Some(v) = v { v.clone() }
2897                    else { VVal::None }),
2898        }
2899    }
2900
2901    pub fn compare_num(&self, b: &VVal) -> std::cmp::Ordering {
2902        if self.is_float() {
2903            self.f().partial_cmp(&b.f())
2904                .unwrap_or(std::cmp::Ordering::Greater)
2905        } else {
2906            self.i().cmp(&b.i())
2907        }
2908    }
2909
2910    pub fn sort<F>(&self, compare: F)
2911        where F: FnMut(&VVal, &VVal) -> std::cmp::Ordering
2912    {
2913        if let VVal::Lst(v) = self {
2914            v.borrow_mut().sort_by(compare);
2915        }
2916    }
2917
2918    pub fn fisher_yates_shuffle<I>(&mut self, mut rand: I)
2919        where I: FnMut() -> i64
2920    {
2921        if let VVal::Lst(list) = self {
2922            let len = list.borrow().len();
2923            if len <= 1 { return; }
2924
2925            for k in 1..len {
2926                let i = len - k;
2927                let j = rand().abs() as usize % (i + 1);
2928                list.borrow_mut().swap(j, i);
2929            }
2930        }
2931    }
2932
2933    pub fn split(&self, pat: &VVal, max: usize, bytes: bool) -> VVal {
2934        let l = VVal::vec();
2935
2936        if bytes {
2937            self.with_bv_ref(|inp| {
2938                pat.with_bv_ref(|pat| {
2939                    let len    = inp.len();
2940                    let ss_len = pat.len();
2941
2942                    if ss_len > len {
2943                        l.push(VVal::new_byt(inp[..].to_vec()));
2944                    } else {
2945                        let mut i            = 0;
2946                        let mut last_split_i = 0;
2947
2948                        while i < len {
2949                            if i + ss_len > len { break; }
2950                            if inp[i..(i + ss_len)] == *pat {
2951                                l.push(
2952                                    VVal::new_byt(
2953                                        inp[last_split_i..i]
2954                                        .to_vec()));
2955
2956                                i += ss_len;
2957                                last_split_i = i;
2958
2959                                if max > 0
2960                                   && (l.len() + 1) >= max as usize
2961                                {
2962                                    l.push(
2963                                        VVal::new_byt(
2964                                            inp[last_split_i..len]
2965                                            .to_vec()));
2966                                    i += inp[last_split_i..len].len();
2967                                    last_split_i = i + 1; // total end!
2968                                    break;
2969                                }
2970                            } else {
2971                                i += 1;
2972                            }
2973                        }
2974
2975                        match last_split_i {
2976                            ls if ls < i  => {
2977                                l.push(
2978                                    VVal::new_byt(
2979                                        inp[last_split_i..len]
2980                                        .to_vec()));
2981                            },
2982                            ls if ls == i => {
2983                                l.push(VVal::new_byt(vec![]));
2984                            },
2985                            _ => (),
2986                        }
2987                    }
2988                })
2989            })
2990        } else {
2991            self.with_s_ref(|s| {
2992                pat.with_s_ref(|pat| {
2993                    if max > 0 {
2994                        for part in s.splitn(max as usize, pat) {
2995                            l.push(VVal::new_str(part));
2996                        }
2997                    } else {
2998                        for part in s.split(pat) {
2999                            l.push(VVal::new_str(part));
3000                        }
3001                    }
3002                })
3003            })
3004        }
3005
3006        l
3007    }
3008
3009    pub fn find(&self, pat: &VVal, start_idx: usize, bytes: bool) -> VVal {
3010        if bytes {
3011            self.with_s_ref(|s|
3012                pat.with_s_ref(|pat| {
3013                    if start_idx >= s.len() {
3014                        return VVal::None;
3015                    }
3016
3017                    match s[start_idx..].find(pat) {
3018                        Some(idx)   => VVal::Int((start_idx + idx) as i64),
3019                        None        => VVal::None,
3020                    }
3021                }))
3022        } else {
3023            self.with_bv_ref(|data|
3024                pat.with_bv_ref(|pat| {
3025                    if pat.len() > (data.len() + start_idx) {
3026                        return VVal::None;
3027                    }
3028
3029                    for i in start_idx..=(data.len() - pat.len()) {
3030                        if pat[..] == data[i..(i + pat.len())] {
3031                            return VVal::Int(i as i64);
3032                        }
3033                    }
3034
3035                    VVal::None
3036                }))
3037        }
3038    }
3039
3040    pub fn bytes_replace(&self, pat: &VVal, repl: &VVal) -> Self {
3041        use std::cmp::Ordering;
3042
3043        let mut bv = self.as_bytes();
3044        pat.with_bv_ref(|pat|
3045            repl.with_bv_ref(|repl| {
3046                let mut len = bv.len();
3047                let mut i = 0;
3048                let plen = pat.len();
3049                let rlen = repl.len();
3050                while i < len {
3051                    if bv[i..].starts_with(pat) {
3052                        match plen.cmp(&rlen) {
3053                            Ordering::Less => {
3054                                let len_delta = rlen - plen;
3055                                bv.resize(len + len_delta, 0);
3056                                bv.copy_within((i + plen)..len, i + rlen);
3057                                len += len_delta;
3058
3059                                bv[i..(rlen + i)].clone_from_slice(&repl[..rlen]);
3060
3061                                i += rlen;
3062                            }
3063                            Ordering::Greater => {
3064                                let len_delta = plen - rlen;
3065                                bv.copy_within((i + plen)..len, i + rlen);
3066                                bv.resize(len - len_delta, 0);
3067                                len -= len_delta;
3068
3069                                bv[i..(rlen + i)].clone_from_slice(&repl[..rlen]);
3070                            }
3071                            Ordering::Equal => {
3072                                bv[i..(plen + i)].clone_from_slice(&repl[..plen]);
3073                                if plen > 0 {
3074                                    i += plen - 1;
3075                                }
3076                            }
3077                        }
3078                    }
3079
3080                    i += 1;
3081                }
3082            }));
3083
3084        VVal::new_byt(bv)
3085    }
3086
3087    #[allow(clippy::while_let_on_iterator)]
3088    pub fn reverse(&self) -> VVal {
3089        match self.deref() {
3090            VVal::Str(s) => {
3091                VVal::new_str_mv(s.chars().rev().collect::<String>())
3092            },
3093            VVal::Byt(b) => {
3094                VVal::new_byt(b.iter().rev().copied().collect::<Vec<u8>>())
3095            },
3096            VVal::Lst(l) => {
3097                VVal::vec_mv(l.borrow().iter().rev().cloned().collect::<Vec<VVal>>())
3098            },
3099            VVal::IVec(b) => {
3100                match b.as_ref() {
3101                    NVec::Vec2(a, b)       =>
3102                        VVal::IVec(Box::new(NVec::Vec2(*b, *a))),
3103                    NVec::Vec3(a, b, c)    =>
3104                        VVal::IVec(Box::new(NVec::Vec3(*c, *b, *a))),
3105                    NVec::Vec4(a, b, c, d) =>
3106                        VVal::IVec(Box::new(NVec::Vec4(*d, *c, *b, *a))),
3107                }
3108            },
3109            VVal::FVec(b) => {
3110                match b.as_ref() {
3111                    NVec::Vec2(a, b)       =>
3112                        VVal::FVec(Box::new(NVec::Vec2(*b, *a))),
3113                    NVec::Vec3(a, b, c)    =>
3114                        VVal::FVec(Box::new(NVec::Vec3(*c, *b, *a))),
3115                    NVec::Vec4(a, b, c, d) =>
3116                        VVal::FVec(Box::new(NVec::Vec4(*d, *c, *b, *a))),
3117                }
3118            },
3119            VVal::Iter(i) => {
3120                let mut out = vec![];
3121                let mut i = i.borrow_mut();
3122                while let Some((v, _)) = i.next() {
3123                    out.push(v);
3124                }
3125                out.reverse();
3126                VVal::vec_mv(out)
3127            },
3128            _ => VVal::None
3129        }
3130    }
3131
3132    #[allow(clippy::while_let_on_iterator)]
3133    pub fn keys(&self) -> VVal {
3134        match self {
3135            VVal::Map(m) => {
3136                let out = VVal::vec();
3137                for (k, _) in m.borrow_mut().iter() {
3138                    out.push(VVal::new_str_mv(k.to_string()));
3139                }
3140                out
3141            },
3142            VVal::Iter(i) => {
3143                let out = VVal::vec();
3144                let mut i = i.borrow_mut();
3145                while let Some((_, k)) = i.next() {
3146                    if let Some(k) = k {
3147                        out.push(k);
3148                    }
3149                }
3150                out
3151            },
3152            VVal::Lst(l) => {
3153                let out = VVal::vec();
3154                for (i, _) in l.borrow_mut().iter().enumerate() {
3155                    out.push(VVal::Int(i as i64));
3156                }
3157                out
3158            },
3159            VVal::IVec(b) => {
3160                match b.as_ref() {
3161                    NVec::Vec2(_, _) =>
3162                        VVal::vec2(VVal::Int(0), VVal::Int(1)),
3163                    NVec::Vec3(_, _, _) =>
3164                        VVal::vec3(VVal::Int(0), VVal::Int(1), VVal::Int(2)),
3165                    NVec::Vec4(_, _, _, _) =>
3166                        VVal::vec4(VVal::Int(0), VVal::Int(1), VVal::Int(2), VVal::Int(3))
3167                }
3168            },
3169            VVal::FVec(b) => {
3170                match b.as_ref() {
3171                    NVec::Vec2(_, _) =>
3172                        VVal::vec2(VVal::Int(0), VVal::Int(1)),
3173                    NVec::Vec3(_, _, _) =>
3174                        VVal::vec3(VVal::Int(0), VVal::Int(1), VVal::Int(2)),
3175                    NVec::Vec4(_, _, _, _) =>
3176                        VVal::vec4(VVal::Int(0), VVal::Int(1), VVal::Int(2), VVal::Int(3))
3177                }
3178            },
3179            v => v.with_deref(
3180                |v| v.keys(),
3181                |_| VVal::None),
3182        }
3183    }
3184
3185    #[allow(clippy::while_let_on_iterator)]
3186    pub fn values(&self) -> VVal {
3187        match self {
3188            VVal::Map(m) => {
3189                let out = VVal::vec();
3190                for (_, v) in m.borrow_mut().iter() {
3191                    out.push(v.clone());
3192                }
3193                out
3194            },
3195            VVal::Lst(l) => {
3196                let out = VVal::vec();
3197                for v in l.borrow_mut().iter() {
3198                    out.push(v.clone());
3199                }
3200                out
3201            },
3202            VVal::Iter(i) => {
3203                let out = VVal::vec();
3204                let mut i = i.borrow_mut();
3205                while let Some((v, _)) = i.next() {
3206                    out.push(v);
3207                }
3208                out
3209            },
3210            VVal::IVec(b) => {
3211                let out = VVal::vec();
3212                match b.as_ref() {
3213                    NVec::Vec2(a, b) => {
3214                        out.push(VVal::Int(*a));
3215                        out.push(VVal::Int(*b));
3216                    },
3217                    NVec::Vec3(a, b, c) => {
3218                        out.push(VVal::Int(*a));
3219                        out.push(VVal::Int(*b));
3220                        out.push(VVal::Int(*c));
3221                    },
3222                    NVec::Vec4(a, b, c, d) => {
3223                        out.push(VVal::Int(*a));
3224                        out.push(VVal::Int(*b));
3225                        out.push(VVal::Int(*c));
3226                        out.push(VVal::Int(*d));
3227                    }
3228                }
3229                out
3230            },
3231            VVal::FVec(b) => {
3232                let out = VVal::vec();
3233                match b.as_ref() {
3234                    NVec::Vec2(a, b) => {
3235                        out.push(VVal::Flt(*a));
3236                        out.push(VVal::Flt(*b));
3237                    },
3238                    NVec::Vec3(a, b, c) => {
3239                        out.push(VVal::Flt(*a));
3240                        out.push(VVal::Flt(*b));
3241                        out.push(VVal::Flt(*c));
3242                    },
3243                    NVec::Vec4(a, b, c, d) => {
3244                        out.push(VVal::Flt(*a));
3245                        out.push(VVal::Flt(*b));
3246                        out.push(VVal::Flt(*c));
3247                        out.push(VVal::Flt(*d));
3248                    }
3249                }
3250                out
3251            },
3252            v => v.with_deref(
3253                |v| v.values(),
3254                |_| VVal::None),
3255        }
3256    }
3257
3258    #[allow(clippy::while_let_on_iterator)]
3259    pub fn enumerate(&self) -> VVal {
3260        match self {
3261            VVal::Map(m) => {
3262                let out = VVal::vec();
3263                for (i, _) in m.borrow_mut().iter().enumerate() {
3264                    out.push(VVal::Int(i as i64));
3265                }
3266                out
3267            },
3268            VVal::Lst(l) => {
3269                let out = VVal::vec();
3270                for (i, _) in l.borrow_mut().iter().enumerate() {
3271                    out.push(VVal::Int(i as i64));
3272                }
3273                out
3274            },
3275            VVal::Iter(i) => {
3276                let out = VVal::vec();
3277                let mut i = i.borrow_mut();
3278                let mut c = 0;
3279                while let Some(_) = i.next() {
3280                    out.push(VVal::Int(c));
3281                    c += 1;
3282                }
3283                out
3284            },
3285            v => v.with_deref(
3286                |v| v.enumerate(),
3287                |_| VVal::None),
3288        }
3289    }
3290
3291    /// Returns true if this vval is containing (multiple) other VVals.
3292    /// Usually true for: Maps, Vectors, Pairs and Opt.
3293    ///
3294    /// Helpful if you want to iterate through a data structure by recursively
3295    /// iterating over a vval. Without getting iterations over individual
3296    /// string characters.
3297    pub fn iter_over_vvals(&self) -> bool {
3298        self.with_deref(
3299            |v| matches!(v, VVal::Lst(_) | VVal::Map(_) | VVal::Opt(_)),
3300            |v| matches!(v, Some(VVal::Lst(_)) | Some(VVal::Map(_)) | Some(VVal::Opt(_))))
3301    }
3302
3303    /// This function returns you an iterator over the VVal.
3304    /// It will iterate over data such as VVal::Str, VVal::Sym, VVal::Lst,
3305    /// VVal::Map and VVal::Byt.
3306    ///
3307    /// **See also:** [VVal::with_iter] which is the better option for iterating
3308    /// over a VVal, because it catches the special case when the VVal itself
3309    /// is an iterator already.
3310    /// This function will not return the same iterator again when called
3311    /// on an VVal iterator value!
3312    ///
3313    /// This functionality provides the `for` keyword/function in WLambda.
3314    ///
3315    /// ```
3316    /// use wlambda::*;
3317    ///
3318    /// let some_vec = VVal::vec();
3319    /// some_vec.push(VVal::Int(10));
3320    /// some_vec.push(VVal::Int(22));
3321    /// some_vec.push(VVal::Int(36));
3322    ///
3323    /// let mut sum = 0;
3324    /// for (v, _) in some_vec.iter() {
3325    ///     sum += v.i();
3326    /// }
3327    ///
3328    /// assert_eq!(sum, 68);
3329    /// ```
3330    pub fn iter(&self) -> VValIter {
3331        match self {
3332            VVal::Lst(l) => {
3333                let l = l.clone();
3334                let mut idx = 0;
3335                std::iter::from_fn(Box::new(move || {
3336                    if idx >= l.borrow().len() { return None; }
3337                    let r = Some((l.borrow()[idx].clone(), None));
3338                    idx += 1;
3339                    r
3340                }))
3341            },
3342            VVal::Map(m) => {
3343                let m = m.clone();
3344                let mut idx = 0;
3345                std::iter::from_fn(Box::new(move || {
3346                    let r =
3347                        m.borrow().iter().nth(idx)
3348                         .map(|(k, v)|
3349                            (v.clone(), Some(VVal::new_str(k.as_ref()))));
3350                    idx += 1;
3351                    r
3352                }))
3353            },
3354            VVal::Byt(b) => {
3355                let b = b.clone();
3356                let mut idx = 0;
3357                std::iter::from_fn(Box::new(move || {
3358                    if idx >= b.len() { return None; }
3359                    let r = Some((VVal::new_byte(b[idx]), None));
3360                    idx += 1;
3361                    r
3362                }))
3363            },
3364            VVal::Sym(s) => {
3365                let s = s.clone();
3366                let mut idx = 0;
3367                std::iter::from_fn(Box::new(move || {
3368                    let r =
3369                        s.chars().nth(idx)
3370                         .map(|chr| (VVal::new_char(chr), None));
3371                    idx += 1;
3372                    r
3373                }))
3374            },
3375            VVal::Str(s) => {
3376                let s = s.clone();
3377                let mut idx = 0;
3378                std::iter::from_fn(Box::new(move || {
3379                    match s[idx..].chars().next() {
3380                        Some(chr) => {
3381                            idx += chr.len_utf8();
3382                            Some((VVal::new_char(chr), None))
3383                        },
3384                        None => None,
3385                    }
3386                }))
3387            },
3388            VVal::None => {
3389                std::iter::from_fn(Box::new(move || { None }))
3390            },
3391            VVal::Pair(p) => {
3392                pair_key_to_iter!(p)
3393            },
3394            VVal::IVec(b) => {
3395                match b.as_ref() {
3396                    NVec::Vec2(a, b) => {
3397                        iter_int_a_to_b!(*a, *b)
3398                    },
3399                    NVec::Vec3(a, b, skip) => {
3400                        let mut i = *a;
3401                        let b = *b;
3402                        let skip = *skip;
3403                        std::iter::from_fn(Box::new(move || {
3404                            if i >= b { return None; }
3405                            let ret = Some((VVal::Int(i), None));
3406                            i += skip;
3407                            ret
3408                        }))
3409                    },
3410                    _ => { std::iter::from_fn(Box::new(move || { None })) },
3411                }
3412            },
3413            VVal::FVec(b) => {
3414                match b.as_ref() {
3415                    NVec::Vec2(a, b) => {
3416                        let mut i = *a;
3417                        let b = *b;
3418                        std::iter::from_fn(Box::new(move || {
3419                            if i >= b { return None; }
3420                            let r = Some((VVal::Flt(i), None));
3421                            i += 1.0;
3422                            r
3423                        }))
3424                    },
3425                    NVec::Vec3(a, b, s) => {
3426                        let mut i = *a;
3427                        let b = *b;
3428                        let s = *s;
3429                        std::iter::from_fn(Box::new(move || {
3430                            if i >= b { return None; }
3431                            let ret = Some((VVal::Flt(i), None));
3432                            i += s;
3433                            ret
3434                        }))
3435                    },
3436                    _ => { std::iter::from_fn(Box::new(move || { None })) },
3437                }
3438            },
3439            VVal::Opt(Some(v)) => {
3440                let x = v.as_ref().clone();
3441                let mut used = false;
3442                std::iter::from_fn(Box::new(move || {
3443                    if used { return None; }
3444                    used = true;
3445                    Some((x.clone(), None))
3446                }))
3447            },
3448            VVal::Opt(None) => {
3449                std::iter::from_fn(Box::new(move || { None }))
3450            },
3451            _ => self.with_deref(
3452                |v| { v.iter() },
3453                |v| if let Some(v) = v {
3454                    let x = v.clone();
3455                    let mut used = false;
3456                    std::iter::from_fn(Box::new(move || {
3457                        if used { return None; }
3458                        used = true;
3459                        Some((x.clone(), None))
3460                    }))
3461                } else {
3462                    std::iter::from_fn(Box::new(move || { None }))
3463                })
3464        }
3465    }
3466
3467    /// Calls the given callback with an iterator through
3468    /// the vval. It catches the special case when the VVal itself
3469    /// is an iterator.
3470    ///
3471    /// ```
3472    /// use wlambda::VVal;
3473    /// use std::rc::Rc;
3474    /// use std::cell::RefCell;
3475    ///
3476    /// let x = VVal::vec();
3477    /// x.push(VVal::Int(10));
3478    /// x.push(VVal::Int(20));
3479    ///
3480    /// let it = x.as_iter();
3481    ///
3482    /// let mut sum = 0;
3483    /// it.with_iter(|iter| {
3484    ///     for (v, _) in iter {
3485    ///         sum += v.i();
3486    ///     }
3487    /// });
3488    ///
3489    /// assert_eq!(sum, 30);
3490    /// ```
3491    pub fn with_iter<F,R>(&self, mut f: F) -> R
3492        where F: FnMut(&mut VValIter) -> R
3493    {
3494        if let VVal::Iter(i) = self {
3495            f(&mut *i.borrow_mut())
3496        } else {
3497            let mut iter = self.iter();
3498            f(&mut iter)
3499        }
3500    }
3501
3502    pub fn with_value_or_iter_values<T>(self, mut f: T)
3503        where T: FnMut(VVal, Option<VVal>) -> bool
3504    {
3505        if let VVal::Iter(i) = self {
3506            while let Some((v, k)) = i.borrow_mut().next() {
3507                if !f(v, k) {
3508                    break;
3509                }
3510            }
3511        } else {
3512            f(self, None);
3513        }
3514    }
3515
3516    /// This method will disable all arity checks of the function in the VVal.
3517    /// Does nothing if the VVal is not a function.
3518    ///
3519    /// It is used for disabling checks of drop functions, as they are
3520    /// evaluated in their own environment and there is no proper way to report
3521    /// errors upwards.
3522    pub fn disable_function_arity(&self) -> VVal {
3523        if let VVal::Fun(fu) = self {
3524            let mut new_fu = fu.as_ref().clone();
3525            new_fu.min_args = None;
3526            new_fu.max_args = None;
3527            VVal::Fun(Rc::new(new_fu))
3528        } else {
3529            self.clone()
3530        }
3531    }
3532
3533    /// This function is an internal function that clones a function reference
3534    /// and assigns new upvalues to it for making a new closure instance.
3535    pub fn clone_and_rebind_upvalues<T>(&self, f: T) -> VVal
3536        where T: FnOnce(&std::vec::Vec<VarPos>, &mut std::vec::Vec<VVal>)
3537    {
3538        if let VVal::Fun(fu) = self {
3539            let mut new_fu = fu.as_ref().clone();
3540            f(&new_fu.upvalue_pos, &mut new_fu.upvalues);
3541            VVal::Fun(Rc::new(new_fu))
3542        } else {
3543            panic!("clone_and_rebind_upvalues does not work on non functions!");
3544        }
3545    }
3546
3547    pub fn call_no_args(&self, env: &mut Env) -> Result<VVal, StackAction> {
3548        self.call_internal(env, 0)
3549    }
3550
3551    pub(crate) fn call_internal(&self, env: &mut Env, argc: usize) -> Result<VVal, StackAction> {
3552        match self {
3553            VVal::None =>
3554                Err(StackAction::panic_str(
3555                    "Calling $none is invalid".to_string(),
3556                    None,
3557                    env.stk2vec(argc))),
3558            VVal::Fun(fu) => {
3559                if let Some(i) = fu.min_args {
3560                    if argc < i {
3561                        return Err(StackAction::panic_str(
3562                            format!(
3563                                "function expects at least {} arguments, got {}",
3564                                i, argc),
3565                            fu.syn_pos.clone(),
3566                            env.stk2vec(argc)));
3567                    }
3568                }
3569
3570                if let Some(i) = fu.max_args {
3571                    if argc > i {
3572                        return Err(StackAction::panic_str(
3573                            format!(
3574                                "function expects at most {} arguments, got {}",
3575                                i, argc),
3576                            fu.syn_pos.clone(),
3577                            env.stk2vec(argc)));
3578                    }
3579                }
3580
3581                env.push_fun_call(fu.clone(), argc);
3582                if !(*fu).err_arg_ok {
3583                    for i in 0..argc {
3584                        if let Some(VVal::Err(ev)) = env.arg_err_internal(i) {
3585                            return
3586                                Err(StackAction::panic_str(
3587                                    format!("Error value in parameter list: {}",
3588                                            ev.borrow().0.s()),
3589                                    Some(ev.borrow().1.clone()),
3590                                    env.argv()));
3591                        }
3592                    }
3593                }
3594
3595                let ret =
3596                    match &(*fu).fun {
3597                        FunType::ClosureNode(cn) => (cn.borrow())(env, argc),
3598                        FunType::VMProg(prog)    => {
3599                            match crate::vm::vm(&*prog, env) {
3600                                Ok(v) => Ok(v),
3601                                Err(StackAction::Return(ret)) => {
3602                                    if ret.0.eqv(&fu.label) {
3603                                        Ok(ret.1)
3604                                    } else {
3605                                        Err(StackAction::Return(ret))
3606                                    }
3607                                },
3608                                Err(e) => {
3609                                    Err(e.wrap_panic(
3610                                        fu.syn_pos.clone(),
3611                                        env.argv()))
3612                                },
3613                            }
3614                        },
3615                    };
3616                env.unwind_one();
3617                ret
3618            },
3619            VVal::Bol(b) => {
3620                env.with_local_call_info(argc, |e: &mut Env| {
3621                    let first = e.arg(0);
3622                    match first {
3623                        // Calling a boolean on a list converts the boolean into an integer
3624                        // and fetches the value at that index.
3625                        VVal::Lst(_) => Ok(first.at(*b as usize).unwrap_or(VVal::None)),
3626                        // Calling a boolean on a pair converts the boolean into an integer
3627                        // and fetches the value at that index.
3628                        VVal::Pair(_) => Ok(first.at(*b as usize).unwrap_or(VVal::None)),
3629                        // Calling a boolean with anything else becomes an implicit `if`,
3630                        // calling the first parameter if the boolean is true
3631                        // and the second if the boolean is false.
3632                        _ => {
3633                            let idx = if *b { 0 } else { 1 };
3634                            if argc > 0 {
3635                                let v = e.arg(idx);
3636                                if !v.is_none() {
3637                                    v.call_internal(e, 0)
3638                                } else {
3639                                    Ok(VVal::None)
3640                                }
3641                            } else { Ok(self.clone()) }
3642                        }
3643                    }
3644                })
3645            },
3646            VVal::Err(e) => {
3647                Err(StackAction::panic_msg(
3648                    format!("Called an error value: {}", e.borrow().0.s())))
3649            },
3650            VVal::Sym(sym) => {
3651                env.with_local_call_info(argc, |e: &mut Env| {
3652                    if argc > 0 {
3653                        let v = e.arg(0);
3654                        Ok(v.get_key(&*sym).unwrap_or(VVal::None))
3655                    } else { Ok(self.clone()) }
3656                })
3657            },
3658            VVal::Map(m) => {
3659                env.with_local_call_info(argc, |e: &mut Env| {
3660                    let f = e.arg(0);
3661
3662                    let mut ret = VVal::None;
3663                    for (k, v) in m.borrow().iter() {
3664                        e.push(v.clone());
3665                        e.push(VVal::new_str(k));
3666                        let el = f.call_internal(e, 2);
3667                        e.popn(2);
3668
3669                        match el {
3670                            Ok(v)                      => { ret = v; },
3671                            Err(StackAction::Break(v)) => { ret = *v; break; },
3672                            Err(StackAction::Next)     => { },
3673                            Err(e)                     => { return Err(e); },
3674                        }
3675                    }
3676                    Ok(ret)
3677                })
3678            },
3679            VVal::Lst(l) => {
3680                env.with_local_call_info(argc, |e: &mut Env| {
3681                    // calling a list with any other value is an implicit map, meaning that for
3682                    // each value in the list the argument is called and the respective element
3683                    // in the map is passed in as the parameter.
3684                    let f = e.arg(0);
3685
3686                    let mut ret = VVal::None;
3687                    for i in l.borrow().iter() {
3688                        e.push(i.clone());
3689                        let el = f.call_internal(e, 1);
3690                        e.popn(1);
3691
3692                        match el {
3693                            Ok(v)                      => { ret = v; },
3694                            Err(StackAction::Break(v)) => { ret = *v; break; },
3695                            Err(StackAction::Next)     => { },
3696                            Err(e)                     => { return Err(e); },
3697                        }
3698                    }
3699                    Ok(ret)
3700                })
3701            },
3702            VVal::Chr(VValChr::Char(_)) => {
3703                env.with_local_call_info(argc, |e: &mut Env| {
3704                    if argc > 0 {
3705                        let first_arg = e.arg(0);
3706                        match first_arg {
3707                            VVal::Pair(p) => {
3708                                Ok(pair_extract(&p.0, &p.1, self))
3709                            },
3710                            _ => {
3711                                concat_operation(false, self, argc, e)
3712                            },
3713                        }
3714                    } else { Ok(self.clone()) }
3715                })
3716            },
3717            VVal::Chr(VValChr::Byte(_)) => {
3718                env.with_local_call_info(argc, |e: &mut Env| {
3719                    if argc > 0 {
3720                        let first_arg = e.arg(0);
3721                        match first_arg {
3722                            VVal::Pair(p) => {
3723                                Ok(pair_extract(&p.0, &p.1, self))
3724                            },
3725                            _ => {
3726                                concat_operation(true, self, argc, e)
3727                            },
3728                        }
3729                    } else { Ok(self.clone()) }
3730                })
3731            },
3732            VVal::Byt(vval_bytes) => {
3733                env.with_local_call_info(argc, |e: &mut Env| {
3734                    if argc > 0 {
3735                        let first_arg = e.arg(0);
3736                        match first_arg {
3737                            VVal::Chr(_) | VVal::Byt(_) | VVal::Str(_) => {
3738                                concat_operation(true, self, argc, e)
3739                            },
3740                            VVal::Int(arg_int) => {
3741                                if argc > 1 {
3742                                    let from = arg_int as usize;
3743                                    let cnt  = e.arg(1).i() as usize;
3744                                    let r : Vec<u8> =
3745                                        vval_bytes.iter()
3746                                            .skip(from).take(cnt).copied()
3747                                            .collect();
3748                                    Ok(VVal::new_byt(r))
3749                                } else if arg_int as usize >= vval_bytes.len() {
3750                                    Ok(VVal::None)
3751                                } else {
3752                                    Ok(VVal::new_byte(vval_bytes[arg_int as usize]))
3753                                }
3754                            },
3755                            VVal::Fun(_) => {
3756                                let mut ret = VVal::None;
3757                                for c in vval_bytes.iter() {
3758                                    e.push(VVal::new_byt(vec![*c]));
3759                                    let el = first_arg.call_internal(e, 1);
3760                                    e.popn(1);
3761                                    match el {
3762                                        Ok(v)                      => { ret = v; },
3763                                        Err(StackAction::Break(v)) => { ret = *v; break; },
3764                                        Err(StackAction::Next)     => { },
3765                                        Err(e)                     => { return Err(e); },
3766                                    }
3767                                }
3768                                Ok(ret)
3769                            },
3770                            VVal::Lst(_) => {
3771                                let from =
3772                                    first_arg.at(0).unwrap_or(VVal::Int(0))
3773                                             .i() as usize;
3774                                let cnt  =
3775                                    first_arg.at(1).unwrap_or_else(
3776                                        || VVal::Int((vval_bytes.len() - from) as i64))
3777                                    .i() as usize;
3778                                let r : Vec<u8> =
3779                                    vval_bytes.iter()
3780                                        .skip(from).take(cnt).copied().collect();
3781                                Ok(VVal::new_byt(r))
3782                            },
3783                            VVal::Pair(p) => Ok(pair_extract(&p.0, &p.1, self)),
3784                            VVal::IVec(iv) => Ok(range_extract(iv.x_raw(), iv.y_raw(), self)),
3785                            VVal::Map(_) => Ok(self.with_s_ref(|key: &str| first_arg.get_key(key).unwrap_or(VVal::None))),
3786                            _ => Ok(VVal::None)
3787                        }
3788                    } else { Ok(self.clone()) }
3789                })
3790            },
3791            VVal::Str(vval_str) => {
3792                env.with_local_call_info(argc, |e: &mut Env| {
3793                    if argc > 0 {
3794                        let first_arg = e.arg(0);
3795                        match first_arg {
3796                            VVal::Int(arg_int) => {
3797                                if argc > 1 {
3798                                    let from = arg_int as usize;
3799                                    let cnt  = e.arg(1).i() as usize;
3800                                    Ok(VVal::new_str_mv(
3801                                        vval_str
3802                                            .chars().skip(from).take(cnt)
3803                                            .collect()))
3804                                } else {
3805                                    let r = vval_str.chars().nth(arg_int as usize);
3806                                    match r {
3807                                        None    => Ok(VVal::None),
3808                                        Some(c) => Ok(VVal::new_char(c)),
3809                                    }
3810                                }
3811                            },
3812                            VVal::Fun(_) => {
3813                                let mut ret = VVal::None;
3814                                for c in vval_str.chars() {
3815                                    e.push(VVal::new_str_mv(c.to_string()));
3816                                    let el = first_arg.call_internal(e, 1);
3817                                    e.popn(1);
3818                                    match el {
3819                                        Ok(v)                      => { ret = v; },
3820                                        Err(StackAction::Break(v)) => { ret = *v; break; },
3821                                        Err(StackAction::Next)     => { },
3822                                        Err(e)                     => { return Err(e); },
3823                                    }
3824                                }
3825                                Ok(ret)
3826                            },
3827                            VVal::Lst(_) => {
3828                                let from = first_arg.at(0).unwrap_or(VVal::Int(0)).i() as usize;
3829                                let cnt  = first_arg.at(1).unwrap_or_else(|| VVal::Int((vval_str.len() - from) as i64)).i() as usize;
3830                                let r : String = vval_str.chars().skip(from).take(cnt).collect();
3831                                Ok(VVal::new_str_mv(r))
3832                            },
3833                            VVal::Chr(_) | VVal::Byt(_) | VVal::Str(_) => {
3834                                concat_operation(false, self, argc, e)
3835                            },
3836                            VVal::Map(_) => Ok(
3837                                first_arg
3838                                    .get_key(vval_str.as_ref())
3839                                    .unwrap_or(VVal::None)),
3840                            VVal::Pair(p) => Ok(pair_extract(&p.0, &p.1, self)),
3841                            VVal::IVec(iv) => Ok(range_extract(iv.x_raw(), iv.y_raw(), self)),
3842                            _ => Ok(VVal::None)
3843                        }
3844                    } else { Ok(self.clone()) }
3845                })
3846            },
3847            VVal::Int(i) => {
3848                env.with_local_call_info(argc, |e: &mut Env| {
3849                    let v = e.arg(0);
3850                    if argc > 0 { Ok(v.at(*i as usize).unwrap_or(VVal::None)) }
3851                    else { Ok(self.clone()) }
3852                })
3853            },
3854            VVal::Pair(p) => {
3855                env.with_local_call_info(argc, |e: &mut Env| {
3856                    if argc == 0 {
3857                        match (&p.0, &p.1) {
3858                              (VVal::Chr(c), VVal::Int(cnt))
3859                            | (VVal::Int(cnt), VVal::Chr(c)) => {
3860                                let cnt = *cnt as usize;
3861                                match c {
3862                                    VValChr::Char(c) => {
3863                                        let mut s = String::with_capacity(cnt);
3864                                        for _ in 0..cnt { s.push(*c); }
3865                                        return Ok(VVal::new_str_mv(s));
3866                                    },
3867                                    VValChr::Byte(b) => {
3868                                        let mut v = Vec::with_capacity(cnt);
3869                                        v.resize(cnt, *b);
3870                                        return Ok(VVal::new_byt(v));
3871                                    },
3872                                }
3873                            },
3874                            _ => { return Ok(self.clone()); }
3875                        }
3876                    }
3877                    if argc != 1 { return Ok(self.clone()) }
3878                    Ok(pair_extract(&p.0, &p.1, e.arg_ref(0).unwrap()))
3879                })
3880            },
3881            VVal::IVec(iv) => {
3882                env.with_local_call_info(argc, |e: &mut Env| {
3883                    if argc != 1 { return Ok(self.clone()) }
3884                    Ok(range_extract(iv.x_raw(), iv.y_raw(), e.arg_ref(0).unwrap()))
3885                })
3886            },
3887            VVal::Iter(i) => {
3888                if argc == 1 {
3889                    env.with_local_call_info(argc, |e: &mut Env| {
3890                        let f = e.arg(0);
3891
3892                        let mut ret = VVal::None;
3893                        #[allow(clippy::while_let_loop)]
3894                        loop {
3895                            let v =
3896                                if let Some((v, k)) = i.borrow_mut().next() {
3897                                    if let Some(k) = k {
3898                                        VVal::pair(v, k)
3899                                    } else {
3900                                        v
3901                                    }
3902                                } else {
3903                                    break;
3904                                };
3905
3906                            e.push(v);
3907                            let el = f.call_internal(e, 1);
3908                            e.popn(1);
3909
3910                            match el {
3911                                Ok(v)                      => { ret = v; },
3912                                Err(StackAction::Break(v)) => { ret = *v; break; },
3913                                Err(StackAction::Next)     => { },
3914                                Err(e)                     => { return Err(e); },
3915                            }
3916                        }
3917                        Ok(ret)
3918                    })
3919                } else {
3920                    Ok(iter_next!(i.borrow_mut()))
3921                }
3922            },
3923            VVal::Opt(v) => {
3924                if argc == 0 {
3925                    if let Some(v) = v {
3926                        Ok(v.as_ref().clone())
3927                    } else {
3928                        Ok(VVal::None)
3929                    }
3930                } else {
3931                    let v =
3932                        if let Some(v) = v { v.as_ref().clone() }
3933                        else               { VVal::None };
3934
3935                    v.call_internal(env, argc)
3936                }
3937            },
3938            VVal::Usr(ud) => {
3939                env.with_local_call_info(argc, |e: &mut Env| ud.call(e))
3940            },
3941            VVal::Ref(v)     => v.borrow().call_internal(env, argc),
3942            VVal::HRef(v)    => v.borrow().call_internal(env, argc),
3943            VVal::WWRef(v)   =>
3944                if let Some(r) = v.upgrade() {
3945                    r.borrow().call_internal(env, argc)
3946                } else { Ok(VVal::None) },
3947            _ => { Ok(self.clone()) },
3948        }
3949    }
3950
3951    pub fn to_ref(&self) -> VVal {
3952        match self {
3953            VVal::HRef(r)    => VVal::Ref(r.clone()),
3954            VVal::Ref(r)     => VVal::Ref(r.clone()),
3955            VVal::WWRef(v)   =>
3956                if let Some(r) = v.upgrade() {
3957                    VVal::Ref(r)
3958                } else {
3959                    VVal::Ref(Rc::new(RefCell::new(VVal::None)))
3960                },
3961            _ => VVal::Ref(Rc::new(RefCell::new(self.clone()))),
3962        }
3963    }
3964
3965    pub fn to_hidden_boxed_ref(&self) -> VVal {
3966        VVal::HRef(Rc::new(RefCell::new(self.clone())))
3967    }
3968
3969    pub fn assign_ref(&mut self, value: VVal) {
3970        match self {
3971            VVal::Ref(_)   => { self.set_ref(value); },
3972            VVal::HRef(_)  => { self.set_ref(value); },
3973            VVal::WWRef(_) => { self.set_ref(value); },
3974            v              => { *v = value; },
3975        }
3976    }
3977
3978    pub fn set_ref(&self, v: VVal) -> VVal {
3979        match self {
3980            VVal::Ref(r)     => r.replace(v),
3981            VVal::HRef(r)    => r.replace(v),
3982            VVal::WWRef(l)   => {
3983                if let Some(r) = l.upgrade() {
3984                    r.replace(v)
3985                } else {
3986                    VVal::None
3987                }
3988            },
3989            _ => VVal::None
3990        }
3991    }
3992
3993    pub fn hide_ref(self) -> VVal {
3994        match self {
3995            VVal::HRef(f) => VVal::HRef(f),
3996            VVal::Ref(f)  => VVal::HRef(f),
3997            VVal::WWRef(f) => {
3998                if let Some(r) = f.upgrade() {
3999                    VVal::HRef(r)
4000                } else {
4001                    VVal::None.to_ref().hide_ref()
4002                }
4003            },
4004            _ => self.to_ref().hide_ref(),
4005        }
4006    }
4007
4008    pub fn upgrade(self) -> VVal {
4009        match self {
4010            VVal::HRef(f) => VVal::Ref(f),
4011            VVal::WWRef(f) => {
4012                if let Some(r) = f.upgrade() {
4013                    VVal::Ref(r)
4014                } else {
4015                    VVal::None.to_ref()
4016                }
4017            },
4018            _ => self.to_ref(),
4019        }
4020    }
4021
4022    pub fn downgrade(self) -> VVal {
4023        match self {
4024            VVal::Ref(f)  => VVal::WWRef(Rc::downgrade(&f)),
4025            VVal::HRef(f) => VVal::WWRef(Rc::downgrade(&f)),
4026            _ => self,
4027        }
4028    }
4029
4030    pub fn map() -> VVal {
4031        VVal::Map(Rc::new(RefCell::new(FnvHashMap::with_capacity_and_hasher(2, Default::default()))))
4032    }
4033
4034    pub fn map1(k: &str, v: VVal) -> VVal {
4035        let m = VVal::map();
4036        m.set_key_str(k, v).expect("single use");
4037        m
4038    }
4039
4040    pub fn map2(k: &str, v: VVal, k2: &str, v2: VVal) -> VVal {
4041        let m = VVal::map();
4042        m.set_key_str(k, v).expect("single use");
4043        m.set_key_str(k2, v2).expect("single use");
4044        m
4045    }
4046
4047    pub fn map3(k: &str, v: VVal, k2: &str, v2: VVal, k3: &str, v3: VVal) -> VVal {
4048        let m = VVal::map();
4049        m.set_key_str(k, v).expect("single use");
4050        m.set_key_str(k2, v2).expect("single use");
4051        m.set_key_str(k3, v3).expect("single use");
4052        m
4053    }
4054
4055    pub fn sym(s: &str) -> VVal {
4056        VVal::Sym(s2sym(s))
4057    }
4058
4059    pub fn to_sym(&self) -> Symbol {
4060        if let VVal::Sym(s) = self {
4061            s.clone()
4062        } else {
4063            self.with_s_ref(s2sym)
4064        }
4065    }
4066
4067    #[allow(clippy::cast_ptr_alignment)]
4068    pub fn ref_id(&self) -> Option<i64> {
4069        Some(match self {
4070            VVal::Err(r)     => { &*r.borrow() as *const (VVal, SynPos) as i64 },
4071            VVal::Str(s)     => { &*s.as_ref() as *const String as i64 },
4072            VVal::Byt(s)     => { &*s.as_ref() as *const Vec<u8> as i64 },
4073            VVal::Sym(s)     => { s.ref_id() },
4074            VVal::Lst(v)     => { &*v.borrow() as *const Vec<VVal> as i64 },
4075            VVal::Map(v)     => { &*v.borrow() as *const FnvHashMap<Symbol, VVal> as i64 },
4076            VVal::Iter(v)    => { &*v.borrow() as *const VValIter as i64 },
4077            VVal::Opt(p)     => { if let Some(p) = p { &*p.as_ref() as *const VVal as i64 } else { 0 } },
4078            VVal::Fun(f)     => { &**f as *const VValFun as i64 },
4079            VVal::DropFun(f) => { &**f as *const DropFun as i64 },
4080            VVal::Pair(v)    => { &**v as *const (VVal, VVal) as i64 },
4081            VVal::Ref(v)     => { &*v.borrow() as *const VVal as i64 },
4082            VVal::HRef(v)    => { &*v.borrow() as *const VVal as i64 },
4083            VVal::Usr(b)     => { &**b as *const dyn VValUserData as *const usize as i64 },
4084            VVal::WWRef(r)   => {
4085                if let Some(l) = r.upgrade() {
4086                    &*l.borrow() as *const VVal as i64
4087                } else {
4088                    return None;
4089                }
4090            },
4091            _ => return None,
4092        })
4093    }
4094
4095    pub fn eqv(&self, v: &VVal) -> bool {
4096        match self {
4097            VVal::None    => { matches!(v, VVal::None) },
4098            VVal::Bol(ia) => { if let VVal::Bol(ib) = v { ia == ib } else { false } },
4099            VVal::Int(ia) => { if let VVal::Int(ib) = v { ia == ib } else { false } },
4100            VVal::Chr(ca) => { if let VVal::Chr(cb) = v { ca == cb } else { false } },
4101            VVal::Flt(ia) => { if let VVal::Flt(ib) = v { (ia - ib).abs() < std::f64::EPSILON } else { false } },
4102            VVal::Sym(s)  => { if let VVal::Sym(ib) = v { s == ib } else { false } },
4103            VVal::Syn(s)  => { if let VVal::Syn(ib) = v { s.syn == ib.syn } else { false } },
4104            VVal::Str(s)  => { if let VVal::Str(ib) = v { *s == *ib } else { false } },
4105            VVal::Byt(s)  => { if let VVal::Byt(s2) = v { s[..] == s2[..] } else { false } },
4106            VVal::Pair(b)  => {
4107                if let VVal::Pair(b2) = v { b.0.eqv(&b2.0) && b.1.eqv(&b2.1) }
4108                else { false }
4109            },
4110            VVal::Opt(a)  => {
4111                if let VVal::Opt(b) = v {
4112                    if let Some(a) = a {
4113                        if let Some(b) = b {
4114                            a.eqv(b)
4115                        } else {
4116                            false
4117                        }
4118                    } else {
4119                        b.is_none()
4120                    }
4121                } else {
4122                    false
4123                }
4124            },
4125            VVal::Lst(l)  => {
4126                if let VVal::Lst(l2) = v { Rc::ptr_eq(l, l2) } else { false }
4127            },
4128            VVal::Map(l)  => {
4129                if let VVal::Map(l2) = v { Rc::ptr_eq(l, l2) } else { false }
4130            },
4131            VVal::Fun(l)  => {
4132                if let VVal::Fun(l2) = v { Rc::ptr_eq(l, l2) } else { false }
4133            },
4134            VVal::IVec(iv) => match v { VVal::IVec(v) => *v == *iv, _ => false },
4135            VVal::FVec(fv) => match v { VVal::FVec(v) => *v == *fv, _ => false },
4136            VVal::DropFun(l)  => {
4137                if let VVal::DropFun(l2) = v { Rc::ptr_eq(l, l2) } else { false }
4138            },
4139            VVal::Err(l)  => {
4140                if let VVal::Err(l2) = v { Rc::ptr_eq(l, l2) } else { false }
4141            },
4142            VVal::Iter(i) => {
4143                if let VVal::Iter(i2) = v {
4144                    Rc::ptr_eq(i, i2)
4145                } else {
4146                    false
4147                }
4148            },
4149            VVal::Ref(l)  => vval_rc_ptr_eq(v, l),
4150            VVal::HRef(l) => vval_rc_ptr_eq(v, l),
4151            VVal::WWRef(lw) => {
4152                if let Some(l) = lw.upgrade() {
4153                    vval_rc_ptr_eq(v, &l)
4154                } else {
4155                    false
4156                }
4157            },
4158            VVal::Usr(u)  => {
4159                if let VVal::Usr(u2) = v {
4160                    u.eqv(u2)
4161                } else {
4162                    false
4163                }
4164            }
4165        }
4166    }
4167
4168    fn dump_vec_as_str(v: &Rc<RefCell<std::vec::Vec<VVal>>>, c: &mut CycleCheck) -> String {
4169        let mut out : Vec<String> = Vec::new();
4170        let mut first = true;
4171        out.push(String::from("$["));
4172        for s in v.borrow().iter().map(|v| v.s_cy(c)) {
4173            if !first { out.push(String::from(",")); }
4174            else { first = false; }
4175            out.push(s);
4176        }
4177        out.push(String::from("]"));
4178        out.concat()
4179    }
4180
4181    fn dump_sym(s: &str) -> String {
4182        if s.chars().all(|c|
4183            c.is_alphanumeric()
4184            || c == '_' || c == '-' || c == '+'
4185            || c == '&' || c == '@')
4186        {
4187            format!(":{}", s)
4188        } else {
4189            format!(":\"{}\"", s)
4190        }
4191    }
4192
4193    fn dump_map_as_str(m: &Rc<RefCell<FnvHashMap<Symbol,VVal>>>, c: &mut CycleCheck) -> String {
4194        let mut out : Vec<String> = Vec::new();
4195        let mut first = true;
4196        out.push(String::from("${"));
4197        let hm = m.borrow();
4198
4199        let mut keys : Vec<&Symbol> = hm.keys().collect();
4200        keys.sort();
4201        for k in keys {
4202            let v = hm.get(k).unwrap();
4203            if !first { out.push(String::from(",")); }
4204            else { first = false; }
4205            if k.as_ref().chars().any(char::is_whitespace) {
4206                out.push(format!("\"{}\"", k.as_ref()));
4207            } else {
4208                out.push(k.as_ref().to_string());
4209            }
4210            out.push(String::from("="));
4211            out.push(v.s_cy(c));
4212        }
4213        out.push(String::from("}"));
4214        out.concat()
4215    }
4216
4217    pub fn map_ok_skip<T, R>(&self, mut op: T, skip: usize) -> Vec<R>
4218        where T: FnMut(&VVal) -> R {
4219
4220        let mut res : Vec<R> = Vec::new();
4221        if let VVal::Lst(b) = &self {
4222            for i in b.borrow().iter().skip(skip) {
4223                res.push(op(i));
4224            }
4225        }
4226        res
4227    }
4228
4229    pub fn map_skip<R, E, T>(&self, mut op: T, skip: usize) -> Result<Vec<R>, E>
4230        where T: FnMut(&VVal) -> Result<R, E> {
4231
4232        let mut res : Vec<R> = Vec::new();
4233        if let VVal::Lst(b) = &self {
4234            for i in b.borrow().iter().skip(skip) {
4235                res.push(op(i)?);
4236            }
4237        }
4238        Ok(res)
4239    }
4240
4241    pub fn unshift(&self, val: VVal) -> &VVal {
4242        if let VVal::Lst(b) = &self {
4243            b.borrow_mut().insert(0, val);
4244            self
4245        } else {
4246            self.with_deref(move |v| { v.unshift(val); }, |_| ());
4247            self
4248        }
4249    }
4250
4251    pub fn add(&self, vals: &[VVal], list_add: CollectionAdd) -> VVal {
4252        let mut collection = if self.is_ref() { self.deref() } else { self.clone() };
4253        //d// println!("ADD: {:?}", vals);
4254
4255        match &collection {
4256            VVal::Lst(lst) => {
4257                for v in vals.iter() {
4258                    v.clone().with_value_or_iter_values(|v, _k| {
4259                        match list_add {
4260                            CollectionAdd::Push => {
4261                                lst.borrow_mut().push(v);
4262                            },
4263                            CollectionAdd::Unshift => {
4264                                lst.borrow_mut().insert(0, v);
4265                            },
4266                        }
4267                        true
4268                    });
4269                }
4270            },
4271            VVal::Map(map) => {
4272                for v in vals.iter() {
4273                    v.clone().with_value_or_iter_values(|v, k| {
4274                        match v {
4275                            VVal::Pair(_) => {
4276                                v.at(0).unwrap().with_s_ref(|k| {
4277                                    map.borrow_mut().insert(s2sym(k), v.at(1).unwrap())
4278                                });
4279                            },
4280                            VVal::Lst(_) => {
4281                                v.v_(0).with_s_ref(|k|
4282                                    map.borrow_mut().insert(s2sym(k), v.clone()));
4283                            },
4284                            VVal::Map(_) => {
4285                                for (vm, km) in v.iter() {
4286                                    if let Some(k) = km {
4287                                        k.with_s_ref(|ks|
4288                                            map.borrow_mut().insert(s2sym(ks), vm.clone()));
4289                                    }
4290                                }
4291                            },
4292                            _ => {
4293                                if let Some(k) = k {
4294                                    k.with_s_ref(|kv|
4295                                        map.borrow_mut().insert(s2sym(kv), v.clone()));
4296                                } else {
4297                                    v.with_s_ref(|kv|
4298                                        map.borrow_mut().insert(s2sym(kv), v.clone()));
4299                                }
4300                            },
4301                        }
4302                        true
4303                    })
4304                }
4305            },
4306            VVal::Str(_) => {
4307                let mut out = collection.with_s_ref(|s| s.to_string());
4308                for v in vals.iter() {
4309                    v.clone().with_value_or_iter_values(|v, _k| {
4310                        v.with_s_ref(|s| out.push_str(s));
4311                        true
4312                    });
4313                }
4314                collection = VVal::new_str_mv(out);
4315            },
4316            VVal::Byt(_) => {
4317                let mut out = collection.with_bv_ref(|b| b.to_vec());
4318                for v in vals.iter() {
4319                    v.clone().with_value_or_iter_values(|v, _k| {
4320                        v.with_bv_ref(|b| out.extend_from_slice(b));
4321                        true
4322                    })
4323                }
4324                collection = VVal::new_byt(out);
4325            },
4326            v => {
4327                return VVal::err_msg(
4328                    &format!("Can't add to non collection, got '{}' (type {})",
4329                             v.s(),
4330                             v.type_name()));
4331            },
4332        }
4333
4334        collection
4335//        let collection =
4336//            if (b.is_ref() && b.deref().is_vec() {
4337//               b.deref()
4338//            } else if !b.is_vec() {
4339//               VVal::vec1(b)
4340//            } else {
4341//                b
4342//            };
4343//
4344//        if !b.is_vec() {
4345//        }
4346//
4347//        match list_add {
4348//            CollectionAdd::Push => {
4349//                if let VVal::Iter(_) = a {
4350//                    a.for_each(|v| b.push(v));
4351//
4352//                } else if a.is_ref() {
4353//                    if let VVal::Iter(_) = a.deref() {
4354//                        a.deref().for_each(|v| b.push(v));
4355//                    } else {
4356//                        b.push(a);
4357//                    }
4358//                } else {
4359//                    b.push(a);
4360//                }
4361//            },
4362//            CollectionAdd::Unshift => {
4363//                if let VVal::Iter(_) = a {
4364//                    a.for_each(|v| b.unshift(v));
4365//
4366//                } else if a.is_ref() {
4367//                    if let VVal::Iter(_) = a.deref() {
4368//                        a.deref().for_each(|v| b.unshift(v));
4369//                    } else {
4370//                        b.unshift(a);
4371//                    }
4372//                } else {
4373//                    b.unshift(a);
4374//                }
4375//            },
4376//        }
4377//
4378//        self
4379    }
4380
4381    pub fn insert_at(&self, index: usize, val: VVal) {
4382        if let VVal::Lst(b) = &self {
4383            b.borrow_mut().insert(index, val);
4384        } else {
4385            self.with_deref(|v| v.insert_at(index, val), |_| ())
4386        }
4387    }
4388
4389    pub fn set(&self, index: usize, val: VVal) {
4390        if let VVal::Lst(b) = &self {
4391            if index >= b.borrow().len() {
4392                b.borrow_mut().resize(index + 1, VVal::None);
4393            }
4394            b.borrow_mut()[index] = val;
4395        }
4396    }
4397
4398    pub fn set_at(&self, index: usize, val: VVal) {
4399        if let VVal::Lst(b) = &self {
4400            b.borrow_mut()[index] = val;
4401        }
4402    }
4403
4404    pub fn at(&self, index: usize) -> Option<VVal> {
4405        match self {
4406            VVal::Byt(vval_bytes) => {
4407                if index as usize >= vval_bytes.len() {
4408                    None
4409                } else {
4410                    Some(VVal::new_byte(vval_bytes[index as usize]))
4411                }
4412            },
4413            VVal::Str(vval_str) => {
4414                vval_str.chars().nth(index as usize).map(VVal::new_char)
4415            },
4416            VVal::Pair(b) => {
4417                Some(if index % 2 == 0 { b.0.clone() } else { b.1.clone() })
4418            },
4419            VVal::Iter(i) => {
4420                let mut i = i.borrow_mut();
4421                for _ in 0..index { i.next(); }
4422                iter_next_value!(i, v, { Some(v) }, None)
4423            },
4424            VVal::Opt(ref b) => {
4425                if let Some(b) = b {
4426                    b.as_ref().at(index)
4427                } else {
4428                    None
4429                }
4430            },
4431            VVal::IVec(b) => {
4432                Some(match index {
4433                    0 => b.x(),
4434                    1 => b.y(),
4435                    2 => b.z().unwrap_or(VVal::None),
4436                    3 => b.w().unwrap_or(VVal::None),
4437                    _ => VVal::None
4438                })
4439            },
4440            VVal::FVec(b) => {
4441                Some(match index {
4442                    0 => b.x(),
4443                    1 => b.y(),
4444                    2 => b.z().unwrap_or(VVal::None),
4445                    3 => b.w().unwrap_or(VVal::None),
4446                    _ => VVal::None
4447                })
4448            },
4449            VVal::Lst(b) => {
4450                if b.borrow().len() > index {
4451                    Some(b.borrow()[index].clone())
4452                } else {
4453                    None
4454                }
4455            },
4456            v => v.with_deref(
4457                |v| v.at(index),
4458                |v| if let Some(v) = v { v.get_key(&format!("{}", index)) }
4459                    else { None }),
4460        }
4461    }
4462
4463    pub fn proto_data(&self) -> VVal {
4464        match self {
4465            VVal::Map(m) => m.borrow().get(&s2sym("_data")).cloned().unwrap_or(VVal::None),
4466            VVal::Lst(l) => {
4467                if l.borrow().len() > 1 {
4468                    l.borrow()[1].clone()
4469                } else {
4470                    VVal::None
4471                }
4472            },
4473            v => v.with_deref(
4474                |v| v.proto_data(),
4475                |_| VVal::None),
4476        }
4477    }
4478
4479    pub fn proto_lookup(&self, key: &str) -> Option<VVal> {
4480        match self {
4481            VVal::Map(m) => {
4482                if let Some(func) = m.borrow().get(&s2sym(key)) {
4483                    Some(func.clone())
4484                } else if let Some(proto) = m.borrow().get(&s2sym("_proto")) {
4485                    proto.proto_lookup(key)
4486                } else {
4487                    None
4488                }
4489            },
4490            VVal::Lst(l) => {
4491                let l = l.borrow();
4492                if l.is_empty() {
4493                    None
4494                } else {
4495                    l[0].proto_lookup(key)
4496                }
4497            },
4498            v => v.with_deref(|v| v.proto_lookup(key), |_| None),
4499        }
4500    }
4501
4502    pub fn get_key_sym(&self, key: &Symbol) -> Option<VVal> {
4503        match self {
4504            VVal::Map(m) => m.borrow().get(key).cloned(),
4505            _            => self.get_key(key.as_ref()),
4506        }
4507    }
4508
4509    pub fn get_key(&self, key: &str) -> Option<VVal> {
4510        match self {
4511            VVal::Map(m) => m.borrow().get(&s2sym(key)).cloned(),
4512            VVal::IVec(b) => {
4513                Some(match key {
4514                    "0" | "first"  | "x" | "r" | "h" => b.x(),
4515                    "1" | "second" | "y" | "g" | "s" => b.y(),
4516                    "2" | "third"  | "z" | "b" | "v" => b.z().unwrap_or(VVal::None),
4517                    "3" | "fourth" | "w" | "a" => b.w().unwrap_or(VVal::None),
4518                    _ =>
4519                        swizzle_i(
4520                            key,
4521                            b.x_raw(),
4522                            b.y_raw(),
4523                            b.z_raw().unwrap_or(0),
4524                            b.w_raw().unwrap_or(0)),
4525                })
4526            },
4527            VVal::FVec(b) => {
4528                Some(match key {
4529                    "0" | "first"  | "x" | "r" | "h" => b.x(),
4530                    "1" | "second" | "y" | "g" | "s" => b.y(),
4531                    "2" | "third"  | "z" | "b" | "v" => b.z().unwrap_or(VVal::None),
4532                    "3" | "fourth" | "w" | "a" => b.w().unwrap_or(VVal::None),
4533                    _ =>
4534                        swizzle_f(
4535                            key,
4536                            b.x_raw(),
4537                            b.y_raw(),
4538                            b.z_raw().unwrap_or(0.0),
4539                            b.w_raw().unwrap_or(0.0)),
4540                })
4541            },
4542            VVal::Pair(_) => {
4543                self.at(match key {
4544                    "0" | "value" | "v" | "car" | "head" | "first"  => 0,
4545                    "1" | "key"   | "k" | "cdr" | "tail" | "second" => 1,
4546                    _ => {
4547                        if !key.chars().all(|c| c.is_digit(10)) { return None; }
4548                        key.parse::<usize>().unwrap_or(0)
4549                    }
4550                })
4551            },
4552            VVal::Iter(i) => {
4553                if !key.chars().all(|c| c.is_digit(10)) { return None; }
4554
4555                let idx = key.parse::<usize>().unwrap_or(0);
4556                let mut i = i.borrow_mut();
4557                for _ in 0..idx { i.next(); }
4558                iter_next_value!(i, v, { Some(v) }, None)
4559            },
4560            VVal::Lst(l) => {
4561                if !key.chars().all(|c| c.is_digit(10)) { return None; }
4562
4563                let idx = key.parse::<usize>().unwrap_or(0);
4564                if idx < l.borrow().len() {
4565                    Some(l.borrow()[idx].clone())
4566                } else {
4567                    Some(VVal::None)
4568                }
4569            },
4570            VVal::Usr(u) => u.get_key(key),
4571            v => v.with_deref(|v| v.get_key(key), |_| None),
4572        }
4573    }
4574
4575    pub fn set_map_key_fun<T>(&self, key: &str, fun: T, min_args: Option<usize>, max_args: Option<usize>, err_arg_ok: bool)
4576        where T: 'static + Fn(&mut Env, usize) -> Result<VVal, StackAction> {
4577        self.set_key_sym(
4578                s2sym(key),
4579                VValFun::new_fun(fun, min_args, max_args, err_arg_ok))
4580            .expect("Map not borrowed when using set_map_key_fun");
4581    }
4582
4583    pub fn deref(&self) -> VVal {
4584        self.with_deref(
4585            |v| v.clone(),
4586            |v| v.map_or(VVal::None, |v| v.clone()))
4587    }
4588
4589    #[inline]
4590    pub fn with_deref<O, D, R>(&self, op: O, default: D) -> R
4591        where O: FnOnce(&VVal) -> R, D: FnOnce(Option<&VVal>) -> R
4592    {
4593        match self {
4594            VVal::Opt(Some(v))  => op(v.as_ref()),
4595            VVal::Opt(None)     => op(&VVal::None),
4596            VVal::Ref(l)        => op(&(*l).borrow()),
4597            VVal::HRef(l)       => op(&(*l).borrow()),
4598            VVal::WWRef(l)      => {
4599                match l.upgrade() {
4600                    Some(v) => op(&v.borrow()),
4601                    None    => default(None),
4602                }
4603            },
4604            _ => default(Some(self)),
4605        }
4606    }
4607
4608    pub fn list_operation<O, R>(&self, mut op: O) -> Result<R, StackAction>
4609        where O: FnMut(&mut std::cell::RefMut<std::vec::Vec<VVal>>) -> R
4610    {
4611        match self {
4612            VVal::Lst(l) => {
4613                match l.try_borrow_mut() {
4614                    Ok(mut v) => { Ok(op(&mut v)) },
4615                    Err(_) => Err(StackAction::panic_borrow(self)),
4616                }
4617            },
4618            v => v.with_deref(|v| {
4619                v.list_operation(op)
4620            }, |v| Err(StackAction::panic_msg(format!(
4621                    "Can't do list operation with non list value: {}",
4622                    v.map_or("".to_string(), |v| v.s())))))
4623        }
4624    }
4625
4626    pub fn delete_key(&self, key: &VVal) -> Result<VVal, StackAction> {
4627        match self {
4628            VVal::Map(m) => {
4629                let ks = key.to_sym();
4630                match m.try_borrow_mut() {
4631                    Ok(mut r)  => Ok(r.remove(&ks).unwrap_or(VVal::None)),
4632                    Err(_)     => Err(StackAction::panic_borrow(self)),
4633                }
4634            },
4635            VVal::Lst(l) => {
4636                let idx = key.i() as usize;
4637                match l.try_borrow_mut() {
4638                    Ok(mut v) => {
4639                        if idx < v.len() {
4640                            Ok(v.remove(idx))
4641                        } else {
4642                            Ok(VVal::None)
4643                        }
4644                    },
4645                    Err(_) => Err(StackAction::panic_borrow(self)),
4646                }
4647            },
4648            VVal::Usr(u) => u.delete_key(key),
4649            v => v.with_deref(
4650                |v| v.delete_key(key),
4651                |_| Ok(VVal::None)),
4652        }
4653    }
4654
4655    pub fn set_key_str(&self, key: &str, val: VVal) -> Result<(), StackAction> {
4656        self.set_key_sym(s2sym(key), val)
4657    }
4658
4659    pub fn set_key_sym(&self, key: Symbol, val: VVal) -> Result<(), StackAction> {
4660        match self {
4661            VVal::Map(m) => {
4662                match m.try_borrow_mut() {
4663                    Ok(mut r)  => { r.insert(key, val); Ok(()) },
4664                    Err(_)     => Err(StackAction::panic_borrow(self)),
4665                }
4666            },
4667            _ => self.set_key(&VVal::Sym(key), val),
4668        }
4669    }
4670
4671
4672
4673    pub fn set_key(&self, key: &VVal, val: VVal) -> Result<(), StackAction> {
4674        match self {
4675            VVal::Map(m) => {
4676                let ks = key.to_sym();
4677                match m.try_borrow_mut() {
4678                    Ok(mut r)  => { r.insert(ks, val); Ok(()) },
4679                    Err(_)     => Err(StackAction::panic_borrow(self)),
4680                }
4681            },
4682            VVal::Lst(l) => {
4683                let idx = key.i() as usize;
4684                match l.try_borrow_mut() {
4685                    Ok(mut v) => {
4686                        if v.len() <= idx {
4687                            v.resize(idx + 1, VVal::None);
4688                        }
4689                        v[idx] = val;
4690                        Ok(())
4691                    },
4692                    Err(_) => Err(StackAction::panic_borrow(self)),
4693                }
4694            },
4695            VVal::FVec(_) =>
4696                Err(StackAction::panic_msg(
4697                    "Can't mutate float vector".to_string())),
4698            VVal::IVec(_) =>
4699                Err(StackAction::panic_msg(
4700                    "Can't mutate integer vector".to_string())),
4701            VVal::Pair(_) =>
4702                Err(StackAction::panic_msg(
4703                    "Can't mutate pair".to_string())),
4704            VVal::Usr(u) => u.set_key(key, val),
4705            v => v.with_deref(
4706                |v| v.set_key(key, val),
4707                |_| Ok(())),
4708        }
4709    }
4710
4711    pub fn pop(&self) -> VVal {
4712        if let VVal::Lst(b) = &self {
4713            b.borrow_mut().pop().unwrap_or(VVal::None)
4714        } else {
4715            self.with_deref(|v| v.pop(), |_| VVal::None)
4716        }
4717    }
4718
4719    pub fn accum(&mut self, val: &VVal) {
4720        match self {
4721            VVal::Byt(ref mut b) => {
4722                match val {
4723                    VVal::Int(i) => { Rc::make_mut(b).push(*i as u8); },
4724                    VVal::Flt(f) => { Rc::make_mut(b).push(*f as u8); },
4725                    VVal::Str(s) => { Rc::make_mut(b).extend_from_slice(s.as_bytes()); },
4726                    VVal::Sym(s) => { Rc::make_mut(b).extend_from_slice(s.as_bytes()); },
4727                    VVal::Byt(s) => { Rc::make_mut(b).extend_from_slice(s.as_ref()); },
4728                    VVal::Bol(o) => { Rc::make_mut(b).push(*o as u8); },
4729                    _ => {
4730                        val.with_bv_ref(
4731                            |s: &[u8]| Rc::make_mut(b).extend_from_slice(s));
4732                    }
4733                }
4734            },
4735            VVal::Str(ref mut a) => {
4736                match val {
4737                    VVal::Str(s) => { Rc::make_mut(a).push_str(s.as_ref()); },
4738                    VVal::Sym(s) => { Rc::make_mut(a).push_str(&*s); },
4739                    VVal::Byt(s) => {
4740                        for b in s.as_ref().iter() {
4741                            let b = *b as char;
4742                            Rc::make_mut(a).push(b);
4743                        }
4744                    },
4745                    _ => {
4746                        val.with_s_ref(|s: &str|
4747                            Rc::make_mut(a).push_str(s));
4748                    }
4749                }
4750            },
4751            VVal::Int(i) => { *i += val.i(); },
4752            VVal::Flt(f) => { *f += val.f(); },
4753            VVal::Lst(v) => { v.borrow_mut().push(val.clone()); },
4754            _ => (),
4755        }
4756    }
4757
4758    pub fn push(&self, val: VVal) -> &VVal {
4759        //d// println!("FN PUSH {} v {}", self.s(), val.s());
4760        if let VVal::Lst(b) = &self {
4761            //d// println!("FN ! PUSH {} v {}", self.s(), val.s());
4762            b.borrow_mut().push(val);
4763        } else {
4764            self.with_deref(|v| { v.push(val); }, |_| ())
4765        }
4766        self
4767    }
4768
4769    pub fn is_empty(&self) -> bool { self.len() == 0 }
4770
4771    pub fn len(&self) -> usize {
4772        match self {
4773            VVal::Chr(_) => 1,
4774            VVal::Lst(l) => l.borrow().len(),
4775            VVal::Map(l) => l.borrow().len(),
4776            VVal::Byt(l) => l.len(),
4777            VVal::Str(l) => l.len(),
4778            VVal::Sym(l) => l.len(),
4779            v => v.with_deref(|v| v.len(), |_| 0),
4780        }
4781    }
4782
4783    pub fn s_len(&self) -> usize {
4784        match self {
4785            VVal::Chr(_)  => 1,
4786            VVal::Str(s)  => s.chars().count(),
4787            VVal::Sym(s)  => s.chars().count(),
4788            VVal::Usr(s)  => s.s_raw().chars().count(),
4789            VVal::Byt(b)  => b.len(),
4790            VVal::None    => 0,
4791            _             => self.s().chars().count(),
4792        }
4793    }
4794
4795    /// Returns the string data or converts the value to a string for displaying.
4796    /// The conversion format is not for reading the value in again via
4797    /// the WLambda parser, it's for accessing the data as pure as possible.
4798    ///
4799    /// Use this if you need the raw unescaped contents of VVal::Str, VVal::Sym,
4800    /// VVal::Byt and other VVals.
4801    ///
4802    /// As this is used usually for generating output a VVal::None is
4803    /// turned into an empty string
4804    ///
4805    /// **There is also `with_s_ref()` which allows you to work with a
4806    /// reference to the string, in case you don't need to own the copy!**
4807    ///
4808    /// ```
4809    /// use wlambda::VVal;
4810    ///
4811    /// assert_eq!(VVal::None.s_raw(), "");
4812    /// assert_eq!(VVal::new_str("Test").s_raw(), "Test");
4813    /// ```
4814    pub fn s_raw(&self) -> String {
4815        match self {
4816            VVal::Chr(c)  => {
4817                let mut buf = [0; 6];
4818                let chrstr = c.c().encode_utf8(&mut buf);
4819                chrstr.to_string()
4820            },
4821            VVal::Str(s)  => s.as_ref().clone(),
4822            VVal::Sym(s)  => String::from(s.as_ref()),
4823            VVal::Usr(s)  => s.s_raw(),
4824            VVal::Byt(s)  => s.iter().map(|b| *b as char).collect(),
4825            VVal::None    => String::from(""),
4826            v => v.with_deref(|v| {
4827                if v.is_none() { "".to_string() }
4828                else { v.s_raw() }
4829            }, |v| {
4830                v.map_or_else(
4831                    || "".to_string(),
4832                    |v| if v.is_none() { "".to_string() }
4833                        else { v.s() })
4834            }),
4835        }
4836    }
4837
4838    /// Like s_raw() but returns a reference to the string.
4839    ///
4840    /// Use this if you need the raw unescaped contents of VVal::Str, VVal::Sym,
4841    /// VVal::Byt and other VVals.
4842    ///
4843    /// As this is used usually for generating output a VVal::None is
4844    /// turned into an empty string
4845    ///
4846    /// ```
4847    /// use wlambda::VVal;
4848    ///
4849    /// VVal::None.with_s_ref(
4850    ///     |s: &str| assert_eq!(s, ""));
4851    ///
4852    /// VVal::new_str("Test").with_s_ref(
4853    ///     |s: &str| assert_eq!(s, "Test"));
4854    /// ```
4855    #[inline]
4856    pub fn with_s_ref<T, R>(&self, f: T) -> R
4857        where T: FnOnce(&str) -> R
4858    {
4859        match self {
4860            VVal::Chr(c)  => {
4861                let mut buf = [0; 6];
4862                let chrstr = c.c().encode_utf8(&mut buf);
4863                f(chrstr)
4864            },
4865            VVal::Str(s)  => f(s.as_ref()),
4866            VVal::Sym(s)  => f(&*s),
4867            VVal::Usr(s)  => f(&s.s_raw()),
4868            VVal::Byt(_)  => f(&self.s_raw()),
4869            VVal::None    => f(""),
4870            _             => f(&self.s_raw()),
4871        }
4872    }
4873
4874
4875    #[inline]
4876    pub fn with_bv_ref<T, R>(&self, f: T) -> R
4877        where T: FnOnce(&[u8]) -> R
4878    {
4879        match self {
4880            VVal::Chr(c) => f(&[c.byte()]),
4881            VVal::Byt(v) => f(&v.as_ref()[..]),
4882            VVal::Str(_) => {
4883                self.with_s_ref(|s| f(s.as_bytes()))
4884            },
4885            _ => {
4886                let vec = self.as_bytes();
4887                f(&vec[..])
4888            }
4889        }
4890    }
4891
4892    pub fn is_float(&self) -> bool {
4893        matches!(self, VVal::Flt(_))
4894    }
4895
4896    pub fn is_int(&self) -> bool {
4897        matches!(self, VVal::Int(_))
4898    }
4899
4900    pub fn is_char(&self) -> bool {
4901        matches!(self, VVal::Chr(VValChr::Char(_)))
4902    }
4903
4904    pub fn is_byte(&self) -> bool {
4905        matches!(self, VVal::Chr(VValChr::Byte(_)))
4906    }
4907
4908    pub fn is_sym(&self) -> bool {
4909        matches!(self, VVal::Sym(_))
4910    }
4911
4912    pub fn is_syn(&self) -> bool {
4913        matches!(self, VVal::Syn(_))
4914    }
4915
4916    pub fn get_syn_pos(&self) -> SynPos {
4917        if let VVal::Syn(s) = self {
4918            s.clone()
4919        } else {
4920            SynPos::empty()
4921        }
4922    }
4923
4924    pub fn syn(&self) -> Option<Syntax> {
4925        if let VVal::Syn(s) = self {
4926            Some(s.syn())
4927        } else {
4928            None
4929        }
4930    }
4931
4932    pub fn set_syn(&mut self, syn: Syntax) {
4933        if let VVal::Syn(s) = self {
4934            s.set_syn(syn);
4935        }
4936    }
4937
4938    pub fn set_syn_at(&self, idx: usize, syn: Syntax) {
4939        let mut v = self.v_(idx);
4940        v.set_syn(syn);
4941        self.set(idx, v);
4942    }
4943
4944    pub fn get_syn(&self) -> Syntax {
4945        if let VVal::Syn(s) = self {
4946            s.syn()
4947        } else {
4948            Syntax::Block
4949        }
4950    }
4951
4952    pub fn compile_err(&self, msg: String) -> CompileError {
4953        CompileError {
4954            msg,
4955            pos: self.at(0).unwrap_or(VVal::None).get_syn_pos(),
4956        }
4957    }
4958
4959    pub fn to_compile_err(&self, msg: String) -> Result<EvalNode, CompileError> {
4960        Err(self.compile_err(msg))
4961    }
4962
4963    pub fn is_pair(&self) -> bool {
4964        matches!(self, VVal::Pair(_))
4965    }
4966
4967    pub fn is_iter(&self) -> bool {
4968        matches!(self, VVal::Iter(_))
4969    }
4970
4971    pub fn is_optional(&self) -> bool {
4972        matches!(self, VVal::Opt(_))
4973    }
4974
4975    pub fn is_ref(&self) -> bool {
4976        matches!(self, VVal::Ref(_) | VVal::HRef(_) | VVal::WWRef(_))
4977    }
4978
4979    pub fn is_wref(&self) -> bool {
4980        matches!(self, VVal::WWRef(_))
4981    }
4982
4983    pub fn is_bool(&self) -> bool {
4984        matches!(self, VVal::Bol(_))
4985    }
4986
4987    pub fn is_bytes(&self) -> bool {
4988        matches!(self, VVal::Byt(_))
4989    }
4990
4991    pub fn is_str(&self) -> bool {
4992        matches!(self, VVal::Str(_))
4993    }
4994
4995    pub fn is_fun(&self) -> bool {
4996        matches!(self, VVal::Fun(_))
4997    }
4998
4999    pub fn is_vec(&self) -> bool {
5000        matches!(self, VVal::Lst(_))
5001    }
5002
5003    pub fn is_nvec(&self) -> bool {
5004        matches!(self, VVal::FVec(_) | VVal::IVec(_))
5005    }
5006
5007    pub fn is_ivec(&self) -> bool {
5008        matches!(self, VVal::IVec(_))
5009    }
5010
5011    pub fn is_fvec(&self) -> bool {
5012        matches!(self, VVal::FVec(_))
5013    }
5014
5015    pub fn nvec_len(&self) -> usize {
5016        match self {
5017            VVal::IVec(nv) => nv.dims().len(),
5018            VVal::FVec(nv) => nv.dims().len(),
5019            _ => 0,
5020        }
5021    }
5022
5023    pub fn is_map(&self) -> bool {
5024        matches!(self, VVal::Map(_))
5025    }
5026
5027    pub fn is_some(&self) -> bool {
5028        !matches!(self, VVal::Opt(None) | VVal::None)
5029    }
5030
5031    pub fn is_none(&self) -> bool {
5032        matches!(self, VVal::Opt(None) | VVal::None)
5033    }
5034
5035    pub fn is_err(&self) -> bool {
5036        matches!(self, VVal::Err(_))
5037    }
5038
5039    pub fn syntax_type(&self) -> &str {
5040        if let VVal::Syn(sp) = self {
5041            match sp.syn {
5042                Syntax::Var            => "Var",
5043                Syntax::Key            => "Key",
5044                Syntax::SetKey         => "SetKey",
5045                Syntax::GetKey         => "GetKey",
5046                Syntax::GetKey2        => "GetKey2",
5047                Syntax::GetKey3        => "GetKey3",
5048                Syntax::GetSym         => "GetSym",
5049                Syntax::GetSym2        => "GetSym2",
5050                Syntax::GetSym3        => "GetSym3",
5051                Syntax::GetIdx         => "GetIdx",
5052                Syntax::GetIdx2        => "GetIdx2",
5053                Syntax::GetIdx3        => "GetIdx3",
5054                Syntax::BinOpAdd       => "BinOpAdd",
5055                Syntax::BinOpSub       => "BinOpSub",
5056                Syntax::BinOpMul       => "BinOpMul",
5057                Syntax::BinOpDiv       => "BinOpDiv",
5058                Syntax::BinOpMod       => "BinOpMod",
5059                Syntax::BinOpLe        => "BinOpLe",
5060                Syntax::BinOpLt        => "BinOpLt",
5061                Syntax::BinOpGe        => "BinOpGe",
5062                Syntax::BinOpGt        => "BinOpGt",
5063                Syntax::BinOpEq        => "BinOpEq",
5064                Syntax::BinOpSomeOr    => "BinOpSomeOr",
5065                Syntax::BinOpExtSomeOr => "BinOpExtSomeOr",
5066                Syntax::BinOpNoneOr    => "BinOpNoneOr",
5067                Syntax::BinOpErrOr     => "BinOpErrOr",
5068                Syntax::BinOpOptOr     => "BinOpOptOr",
5069                Syntax::OpNewPair      => "OpNewPair",
5070                Syntax::OpCallLwR      => "OpCallLwR",
5071                Syntax::OpCallRwL      => "OpCallRwL",
5072                Syntax::OpCallApplyLwR => "OpCallApplyLwR",
5073                Syntax::OpCallApplyRwL => "OpCallApplyRwL",
5074                Syntax::OpColAddL      => "OpColAddL",
5075                Syntax::OpColAddR      => "OpColAddR",
5076                Syntax::Str            => "Str",
5077                Syntax::Lst            => "Lst",
5078                Syntax::IVec           => "IVec",
5079                Syntax::FVec           => "FVec",
5080                Syntax::Opt            => "Opt",
5081                Syntax::Iter           => "Iter",
5082                Syntax::Map            => "Map",
5083                Syntax::Expr           => "Expr",
5084                Syntax::Func           => "Func",
5085                Syntax::Block          => "Block",
5086                Syntax::Err            => "Err",
5087                Syntax::Call           => "Call",
5088                Syntax::Apply          => "Apply",
5089                Syntax::And            => "And",
5090                Syntax::Or             => "Or",
5091                Syntax::Assign         => "Assign",
5092                Syntax::Def            => "Def",
5093                Syntax::Ref            => "Ref",
5094                Syntax::HRef           => "HRef",
5095                Syntax::WRef           => "WRef",
5096                Syntax::Deref          => "Deref",
5097                Syntax::CaptureRef     => "CaptureRef",
5098                Syntax::AssignRef      => "AssignRef",
5099                Syntax::DefGlobRef     => "DefGlobRef",
5100                Syntax::DefConst       => "DefConst",
5101                Syntax::SelfObj        => "SelfObj",
5102                Syntax::SelfData       => "SelfData",
5103                Syntax::Import         => "Import",
5104                Syntax::Export         => "Export",
5105                Syntax::DumpStack      => "DumpStack",
5106                Syntax::DumpVM         => "DumpVM",
5107                Syntax::DebugPrint     => "DebugPrint",
5108                Syntax::MapSplice      => "MapSplice",
5109                Syntax::VecSplice      => "VecSplice",
5110                Syntax::Accum          => "Accum",
5111                Syntax::GlobVar        => "GlobVar",
5112                Syntax::Selector       => "Selector",
5113                Syntax::Pattern        => "Pattern",
5114                Syntax::StructPattern  => "StructPattern",
5115                Syntax::Formatter      => "Formatter",
5116            }
5117        } else {
5118            "VVal"
5119        }
5120    }
5121
5122    pub fn type_name(&self) -> &str {
5123        match self {
5124            VVal::Str(_)                 => "string",
5125            VVal::Byt(_)                 => "bytes",
5126            VVal::Chr(VValChr::Char(_))  => "char",
5127            VVal::Chr(VValChr::Byte(_))  => "byte",
5128            VVal::None                   => "none",
5129            VVal::Err(_)                 => "error",
5130            VVal::Bol(_)                 => "bool",
5131            VVal::Sym(_)                 => "symbol",
5132            VVal::Syn(_)                 => "syntax",
5133            VVal::Int(_)                 => "integer",
5134            VVal::Flt(_)                 => "float",
5135            VVal::Pair(_)                => "pair",
5136            VVal::Iter(_)                => "iter",
5137            VVal::Opt(_)                 => "optional",
5138            VVal::Lst(_)                 => "vector",
5139            VVal::Map(_)                 => "map",
5140            VVal::Usr(_)                 => "userdata",
5141            VVal::Fun(_)                 => "function",
5142            VVal::IVec(_)                => "integer_vector",
5143            VVal::FVec(_)                => "float_vector",
5144            VVal::DropFun(_)             => "drop_function",
5145            VVal::Ref(_)                 => "ref_strong",
5146            VVal::HRef(_)                => "ref_hidden",
5147            VVal::WWRef(_)               => "ref_weak",
5148        }
5149    }
5150
5151    /// Accesses the user data of type T directly.
5152    /// If the user data is not of that type it returns `None`.
5153    pub fn with_usr_ref<T: 'static, F, X>(&mut self, f: F) -> Option<X>
5154        where F: FnOnce(&mut T) -> X {
5155        if let VVal::Usr(bx) = self {
5156            bx.as_any().downcast_mut::<T>().map(f)
5157        } else {
5158            None
5159        }
5160    }
5161
5162    /// Quick access method for retrieving the VVal at index `idx`.
5163    /// Returns VVal::None if the VVal is not a VVal::Lst or no such index exists.
5164    /// See also the shorthands `v_i`, `v_f`, `v_s` and `v_s_raw`.
5165    ///
5166    ///```
5167    /// use wlambda::VVal;
5168    /// let v = VVal::vec();
5169    /// v.push(VVal::Int(10));
5170    /// v.push(VVal::Int(11));
5171    ///
5172    /// assert_eq!(v.v_(1).i(), 11);
5173    /// assert_eq!(v.v_i(1),    11);
5174    ///```
5175    pub fn v_(&self, idx: usize) -> VVal { self.at(idx).unwrap_or(VVal::None) }
5176
5177    /// Quick access method for retrieving the VVal at key `idx`.
5178    /// Returns VVal::None if the VVal is not a VVal::Map or no such index exists.
5179    /// See also the shorthands `v_ik`, `v_fk`, `v_sk`, `v_bk` and `v_s_rawk`.
5180    ///
5181    ///```
5182    /// use wlambda::VVal;
5183    /// let v = VVal::map();
5184    /// v.set_key_str("aaa", VVal::Int(12));
5185    /// v.set_key_str("abc", VVal::Int(13));
5186    /// v.set_key_str("zyy", VVal::Int(14));
5187    ///
5188    /// assert_eq!(v.v_k("abc").i(), 13);
5189    /// assert_eq!(v.v_ik("aaa"),    12);
5190    /// assert_eq!(v.v_ik("zyy"),    14);
5191    ///```
5192    pub fn v_k(&self, key: &str) -> VVal { self.get_key(key).unwrap_or(VVal::None) }
5193    /// Quick access of an integer at the given `idx`.
5194    /// See also `v_`.
5195    ///
5196    ///```
5197    /// let v = wlambda::VVal::vec();
5198    /// v.push(wlambda::VVal::Int(11));
5199    /// assert_eq!(v.v_i(0),    11);
5200    ///```
5201    pub fn v_i(&self, idx: usize)     -> i64 { self.v_(idx).i() }
5202    /// Quick access of the integer at the given `key`.
5203    /// See also `v_k`.
5204    ///
5205    ///```
5206    /// let v = wlambda::VVal::map();
5207    /// v.set_key_str("aaa", wlambda::VVal::new_str("10"));
5208    /// assert_eq!(v.v_ik("aaa"), 10);
5209    ///```
5210    pub fn v_ik(&self, key: &str)     -> i64 { self.v_k(key).i() }
5211    /// Quick access of an bool at the given `idx`.
5212    /// See also `v_`.
5213    ///
5214    ///```
5215    /// let v = wlambda::VVal::vec();
5216    /// v.push(wlambda::VVal::Bol(true));
5217    /// assert_eq!(v.v_b(0),    true);
5218    ///```
5219    pub fn v_b(&self, idx: usize)     -> bool { self.v_(idx).b() }
5220    /// Quick access of the integer at the given `key`.
5221    /// See also `v_k`.
5222    ///
5223    ///```
5224    /// let v = wlambda::VVal::map();
5225    /// v.set_key_str("aaa", wlambda::VVal::Bol(true));
5226    /// assert_eq!(v.v_bk("aaa"), true);
5227    ///```
5228    pub fn v_bk(&self, key: &str)     -> bool { self.v_k(key).b() }
5229    /// Quick access of a character at the given `idx`.
5230    /// See also `v_`.
5231    ///
5232    ///```
5233    /// let v = wlambda::VVal::vec();
5234    /// v.push(wlambda::VVal::Int(11));
5235    /// assert_eq!(v.v_c(0),    '\u{0b}');
5236    ///```
5237    pub fn v_c(&self, idx: usize)     -> char { self.v_(idx).c() }
5238    /// Quick access of the character at the given `key`.
5239    /// See also `v_k`.
5240    ///
5241    ///```
5242    /// let v = wlambda::VVal::map();
5243    /// v.set_key_str("aaa", wlambda::VVal::new_char('@'));
5244    /// assert_eq!(v.v_ck("aaa"), '@');
5245    ///```
5246    pub fn v_ck(&self, key: &str)     -> char { self.v_k(key).c() }
5247    /// Quick access of a byte at the given `idx`.
5248    /// See also `v_`.
5249    ///
5250    ///```
5251    /// let v = wlambda::VVal::vec();
5252    /// v.push(wlambda::VVal::Int(11));
5253    /// assert_eq!(v.v_byte(0), b'\x0b');
5254    ///```
5255    pub fn v_byte(&self, idx: usize)     -> u8 { self.v_(idx).byte() }
5256    /// Quick access of the byte at the given `key`.
5257    /// See also `v_k`.
5258    ///
5259    ///```
5260    /// let v = wlambda::VVal::map();
5261    /// v.set_key_str("aaa", wlambda::VVal::new_byte(b'@'));
5262    /// assert_eq!(v.v_bytek("aaa"), b'@');
5263    ///```
5264    pub fn v_bytek(&self, key: &str)     -> u8 { self.v_k(key).byte() }
5265    /// Quick access of a raw string at the given `idx`.
5266    /// See also `v_`.
5267    ///
5268    ///```
5269    /// let v = wlambda::VVal::vec();
5270    /// v.push(wlambda::VVal::Int(12));
5271    /// assert_eq!(v.v_s_raw(0), "12");
5272    ///```
5273    pub fn v_s_raw(&self, idx: usize) -> String { self.v_(idx).s_raw() }
5274    /// Quick access of a raw string as reference at the given `idx`.
5275    /// See also `v_`.
5276    ///
5277    ///```
5278    /// let v = wlambda::VVal::vec();
5279    /// v.push(wlambda::VVal::new_str("12"));
5280    /// assert_eq!(v.v_with_s_ref(0, |s: &str| s.chars().nth(0).unwrap()), '1');
5281    ///```
5282    pub fn v_with_s_ref<T, R>(&self, idx: usize, f: T) -> R
5283        where T: FnOnce(&str) -> R
5284    {
5285        self.v_(idx).with_s_ref(f)
5286    }
5287    /// Quick access of the string at the given `key`.
5288    /// See also `v_k`.
5289    ///
5290    ///```
5291    /// let v = wlambda::VVal::map();
5292    /// v.set_key_str("aaa", wlambda::VVal::new_str("XYX"));
5293    /// assert_eq!(v.v_s_rawk("aaa"), "XYX");
5294    ///```
5295    pub fn v_s_rawk(&self, key: &str) -> String { self.v_k(key).s_raw() }
5296    /// Quick access of the string as reference at the given `key`.
5297    /// See also `v_k`.
5298    ///
5299    ///```
5300    /// let v = wlambda::VVal::map();
5301    /// v.set_key_str("aaa", wlambda::VVal::new_str("XYX"));
5302    /// assert!(v.v_with_s_refk("aaa", |s: &str| s == "XYX"));
5303    ///```
5304    pub fn v_with_s_refk<T, R>(&self, key: &str, f: T) -> R
5305        where T: FnOnce(&str) -> R
5306    {
5307        self.v_k(key).with_s_ref(f)
5308    }
5309    /// Quick access of the string representation at the given `idx`.
5310    /// See also `v_`.
5311    ///
5312    ///```
5313    /// let v = wlambda::VVal::vec();
5314    /// v.push(wlambda::VVal::Int(13));
5315    /// assert_eq!(v.v_s(0), "13");
5316    ///```
5317    pub fn v_s(&self, idx: usize)     -> String { self.v_(idx).s() }
5318    /// Quick access of the string represenation at the given `key`.
5319    /// See also `v_k`.
5320    ///
5321    ///```
5322    /// let v = wlambda::VVal::map();
5323    /// v.set_key_str("aaa", wlambda::VVal::Flt(12.2));
5324    /// assert_eq!(v.v_sk("aaa"), "12.2");
5325    ///```
5326    pub fn v_sk(&self, key: &str)     -> String { self.v_k(key).s() }
5327    /// Quick access of the float at the given `idx`.
5328    /// See also `v_`.
5329    ///
5330    ///```
5331    /// let v = wlambda::VVal::vec();
5332    /// v.push(wlambda::VVal::Flt(13.2));
5333    /// assert_eq!(v.v_f(0), 13.2);
5334    ///```
5335    pub fn v_f(&self, idx: usize)     -> f64 { self.v_(idx).f() }
5336    /// Quick access of the float at the given `key`.
5337    /// See also `v_k`.
5338    ///
5339    ///```
5340    /// let v = wlambda::VVal::map();
5341    /// v.set_key_str("aaa", wlambda::VVal::Flt(12.2));
5342    /// assert_eq!(v.v_fk("aaa"), 12.2);
5343    ///```
5344    pub fn v_fk(&self, key: &str)     -> f64 { self.v_k(key).f() }
5345
5346    pub fn for_each<T>(&self, mut op: T)
5347        where T: FnMut(&VVal)
5348    {
5349        if let VVal::Lst(b) = &self {
5350            for i in b.borrow().iter() { op(i); }
5351        }
5352    }
5353
5354    pub fn for_eachk<T>(&self, mut op: T)
5355        where T: FnMut(&str, &VVal)
5356    {
5357        if let VVal::Map(b) = &self {
5358            for (k, v) in b.borrow().iter() { op(k, v); }
5359        }
5360    }
5361
5362    #[allow(clippy::cast_lossless)]
5363    pub fn f(&self) -> f64 {
5364        match self {
5365            VVal::Str(s)     => (*s).parse::<f64>().unwrap_or(0.0),
5366            VVal::Sym(s)     => (*s).parse::<f64>().unwrap_or(0.0),
5367            VVal::Byt(s)     => if s.len() > 0 { s[0] as f64 } else { 0.0 },
5368            VVal::Chr(c)     => c.c() as u32 as f64,
5369            VVal::None       => 0.0,
5370            VVal::Err(_)     => 0.0,
5371            VVal::Bol(b)     => if *b { 1.0 } else { 0.0 },
5372            VVal::Syn(s)     => (s.syn() as i64) as f64,
5373            VVal::Int(i)     => *i as f64,
5374            VVal::Flt(f)     => *f,
5375            VVal::Pair(b)    => b.0.f(),
5376            VVal::Lst(l)     => l.borrow().len() as f64,
5377            VVal::Map(l)     => l.borrow().len() as f64,
5378            VVal::Usr(u)     => u.f(),
5379            VVal::Fun(_)     => 1.0,
5380            VVal::IVec(iv)   => iv.x_raw() as f64,
5381            VVal::FVec(fv)   => fv.x_raw(),
5382            VVal::Iter(i)    => iter_next_value!(i.borrow_mut(), v, { v.f() }, 0.0),
5383            v => v.with_deref(|v| v.f(), |_| 0.0),
5384        }
5385    }
5386
5387    #[allow(clippy::cast_lossless)]
5388    pub fn i(&self) -> i64 {
5389        match self {
5390            VVal::Str(s)     => (*s).parse::<i64>().unwrap_or(0),
5391            VVal::Sym(s)     => (*s).parse::<i64>().unwrap_or(0),
5392            VVal::Chr(c)     => c.c() as u32 as i64,
5393            VVal::Byt(s)     => if s.len() > 0 { s[0] as i64 } else { 0 },
5394            VVal::None       => 0,
5395            VVal::Err(_)     => 0,
5396            VVal::Bol(b)     => if *b { 1 } else { 0 },
5397            VVal::Syn(s)     => s.syn() as i64,
5398            VVal::Int(i)     => *i,
5399            VVal::Flt(f)     => (*f as i64),
5400            VVal::Pair(b)    => b.0.i(),
5401            VVal::Lst(l)     => l.borrow().len() as i64,
5402            VVal::Map(l)     => l.borrow().len() as i64,
5403            VVal::Usr(u)     => u.i(),
5404            VVal::Fun(_)     => 1,
5405            VVal::IVec(iv)   => iv.x_raw(),
5406            VVal::FVec(fv)   => fv.x_raw() as i64,
5407            VVal::Iter(i)    => iter_next_value!(i.borrow_mut(), v, { v.i() }, 0),
5408            v => v.with_deref(|v| v.i(), |_| 0),
5409        }
5410    }
5411
5412    #[allow(clippy::cast_lossless)]
5413    pub fn byte(&self) -> u8 {
5414        match self {
5415            VVal::Str(s)     => { if (*s).len() > 0 { (*s).as_bytes()[0] } else { 0 } },
5416            VVal::Sym(s)     => { if (*s).len() > 0 { (*s).as_bytes()[0] } else { 0 } },
5417            VVal::Chr(c)     => c.byte(),
5418            VVal::Byt(s)     => if s.len() > 0 { s[0] } else { b'0' },
5419            VVal::None       => b'\0',
5420            VVal::Err(_)     => b'\0',
5421            VVal::Bol(b)     => if *b { b'\x01' } else { b'\0' },
5422            VVal::Syn(s)     => s.syn() as i64 as u32 as u8,
5423            VVal::Int(i)     => if *i <= 255 { *i as u8 } else { b'?' },
5424            VVal::Flt(f)     => if (*f as u32) <= 255 { *f as u8 } else { b'?' },
5425            VVal::Pair(b)    => b.0.byte(),
5426            VVal::Lst(l)     => l.borrow().len() as u8,
5427            VVal::Map(l)     => l.borrow().len() as u8,
5428            VVal::Usr(u)     => u.byte(),
5429            VVal::Fun(_)     => b'\x01',
5430            VVal::IVec(iv)   => iv.x_raw() as u8,
5431            VVal::FVec(fv)   => fv.x_raw() as u8,
5432            VVal::Iter(i)    => iter_next_value!(i.borrow_mut(), v, { v.byte() }, b'\0'),
5433            v => v.with_deref(|v| v.byte(), |_| b'\0'),
5434        }
5435    }
5436
5437
5438    #[allow(clippy::cast_lossless)]
5439    pub fn c(&self) -> char {
5440        match self {
5441            VVal::Str(s)     => (*s).chars().next().unwrap_or('\0'),
5442            VVal::Sym(s)     => (*s).chars().next().unwrap_or('\0'),
5443            VVal::Chr(c)     => c.c(),
5444            VVal::Byt(s)     => if s.len() > 0 { s[0] as char } else { '\0' },
5445            VVal::None       => '\0',
5446            VVal::Err(_)     => '\0',
5447            VVal::Bol(b)     => if *b { '\u{01}' } else { '\0' },
5448            VVal::Syn(s)     => std::char::from_u32(s.syn() as i64 as u32).unwrap_or('\0'),
5449            VVal::Int(i)     => std::char::from_u32(*i as u32).unwrap_or('\0'),
5450            VVal::Flt(f)     => std::char::from_u32(*f as u32).unwrap_or('\0'),
5451            VVal::Pair(b)    => b.0.c(),
5452            VVal::Lst(l)     => std::char::from_u32(l.borrow().len() as u32).unwrap_or('\0'),
5453            VVal::Map(l)     => std::char::from_u32(l.borrow().len() as u32).unwrap_or('\0'),
5454            VVal::Usr(u)     => u.c(),
5455            VVal::Fun(_)     => '\u{01}',
5456            VVal::IVec(iv)   => std::char::from_u32(iv.x_raw() as u32).unwrap_or('\0'),
5457            VVal::FVec(fv)   => std::char::from_u32(fv.x_raw() as u32).unwrap_or('\0'),
5458            VVal::Iter(i)    => iter_next_value!(i.borrow_mut(), v, { v.c() }, '\0'),
5459            v => v.with_deref(|v| v.c(), |_| '\0'),
5460        }
5461    }
5462
5463    #[allow(clippy::cast_lossless)]
5464    pub fn b(&self) -> bool {
5465        match self {
5466            VVal::Str(s)       => (*s).parse::<i64>().unwrap_or(0) != 0,
5467            VVal::Sym(s)       => (*s).parse::<i64>().unwrap_or(0) != 0,
5468            VVal::Chr(c)       => (c.c() as u32) > 0,
5469            VVal::Byt(s)       => (if s.len() > 0 { s[0] as i64 } else { 0 }) != 0,
5470            VVal::None         => false,
5471            VVal::Err(_)       => false,
5472            VVal::Bol(b)       => *b,
5473            VVal::Syn(s)       => (s.syn() as i64) != 0,
5474            VVal::Pair(b)      => b.0.b() || b.1.b(),
5475            VVal::Int(i)       => (*i) != 0,
5476            VVal::Flt(f)       => (*f as i64) != 0,
5477            VVal::Lst(l)       => (l.borrow().len() as i64) != 0,
5478            VVal::Map(l)       => (l.borrow().len() as i64) != 0,
5479            VVal::Usr(u)       => u.b(),
5480            VVal::Fun(_)       => true,
5481            VVal::Opt(None)    => false,
5482            VVal::Opt(Some(_)) => true,
5483            VVal::IVec(iv)     => iv.x().b(),
5484            VVal::FVec(fv)     => fv.x().b(),
5485            VVal::Iter(i)      => iter_next_value!(i.borrow_mut(), v, { v.b() }, false),
5486            v                  => v.with_deref(|v| v.b(), |_| false),
5487        }
5488    }
5489
5490    pub fn nvec<N: crate::nvec::NVecNum>(&self) -> NVec<N> {
5491        use NVec::*;
5492        match self {
5493            VVal::IVec(i) => N::from_ivec(**i),
5494            VVal::FVec(f) => N::from_fvec(**f),
5495            VVal::Map(map)  => {
5496                let m = map.borrow();
5497                let o = N::zero().into_vval();
5498                NVec::from_vval_tpl(
5499                    (m.get(&s2sym("x")).unwrap_or(&o),
5500                     m.get(&s2sym("y")).unwrap_or(&o),
5501                     m.get(&s2sym("z")),
5502                     m.get(&s2sym("w")))
5503                ).unwrap_or_else(|| {
5504                    // The only way from_vval_tpl can fail is if the fourth
5505                    // parameter is Some(_) but the third is None.
5506                    // That means that the following will always succeed
5507                    // (even if the above did not):
5508                    NVec::from_vval_tpl(
5509                        (m.get(&s2sym("x")).unwrap_or(&o),
5510                         m.get(&s2sym("y")).unwrap_or(&o),
5511                         Some(&o),
5512                         m.get(&s2sym("w")))
5513                    ).unwrap()
5514                })
5515            },
5516            VVal::Lst(lst) => {
5517                let list = lst.borrow();
5518                let mut lst = list.iter();
5519                let zero = N::zero().into_vval();
5520                let (x, y, z, w) = (lst.next(), lst.next(), lst.next(), lst.next());
5521                // The only way from_vval_tpl can fail is if the fourth
5522                // parameter is Some(_) but the third is None.
5523                // That means that the following will always succeed,
5524                // because lists can't have holes.
5525                NVec::from_vval_tpl(
5526                    (x.unwrap_or(&zero), y.unwrap_or(&zero), z, w))
5527                .unwrap()
5528            },
5529            VVal::Pair(p) => {
5530                NVec::from_vval_tpl((p.0.clone(), p.1.clone(), None, None)).unwrap()
5531            },
5532            VVal::Iter(i) => {
5533                iter_next_value!(
5534                    i.borrow_mut(), v, { v.nvec::<N>() },
5535                    NVec::from_vval_tpl(
5536                        (VVal::Int(0), VVal::Int(0), None, None)).unwrap())
5537            },
5538            _ => Vec2(N::from_vval(self), N::zero()),
5539        }
5540    }
5541
5542    fn s_cy(&self, c: &mut CycleCheck) -> String {
5543        let br = if let Some((do_continue, backref_str)) = c.backref(self) {
5544            if !do_continue { return backref_str; }
5545            backref_str
5546        } else {
5547            String::from("")
5548        };
5549        let s = match self {
5550            VVal::Str(_)     => self.with_s_ref(|s| format_vval_str(s, false)),
5551            VVal::Sym(s)     => VVal::dump_sym(&*s),
5552            VVal::Byt(s)     => format!("$b{}", format_vval_byt(s.as_ref())),
5553            VVal::None       => "$n".to_string(),
5554            VVal::Err(e)     =>
5555                if (*e).borrow().1.has_info() {
5556                    format!("$e {} [@ {}]", (*e).borrow().0.s_cy(c), (*e).borrow().1)
5557                } else {
5558                    format!("$e {}", (*e).borrow().0.s_cy(c))
5559                },
5560            VVal::Bol(b)     => if *b { "$true".to_string() } else { "$false".to_string() },
5561            VVal::Syn(s)     => format!("$%:{:?}", s.syn()),
5562            VVal::Chr(c)     => c.to_string(),
5563            VVal::Int(i)     => i.to_string(),
5564            VVal::Flt(f)     => f.to_string(),
5565            VVal::Pair(b)    => format!("$p({},{})", b.0.s_cy(c), b.1.s_cy(c)),
5566            VVal::Iter(_)    => "$iter(&)".to_string(),
5567            VVal::Opt(b)     =>
5568                if let Some(b) = b { format!("$o({})", b.s_cy(c)) }
5569                else { "$o()".to_string() },
5570            VVal::Lst(l)     => VVal::dump_vec_as_str(l, c),
5571            VVal::Map(l)     => VVal::dump_map_as_str(l, c), // VVal::dump_map_as_str(l),
5572            VVal::Usr(u)     => u.s(),
5573            VVal::Fun(f)     => {
5574                let min = if f.min_args.is_none() { "any".to_string() }
5575                          else { format!("{}", f.min_args.unwrap()) };
5576                let max = if f.max_args.is_none() { "any".to_string() }
5577                          else { format!("{}", f.max_args.unwrap()) };
5578                let upvalues : String =
5579                    f.upvalues
5580                     .iter()
5581                     .map(|v| v.s_cy(c))
5582                     .collect::<Vec<String>>()
5583                     .join(",");
5584                if let Some(ref sp) = f.syn_pos {
5585                    format!("&F{{@{},amin={},amax={},locals={},upvalues=$[{}]}}",
5586                            sp, min, max, f.local_size, upvalues)
5587                } else {
5588                    format!("&F{{@[0,0:?()],amin={},amax={},locals={},upvalues=$[{}]}}",
5589                            min, max, f.local_size, upvalues)
5590                }
5591            },
5592            VVal::DropFun(f) => format!("std:to_drop[{}]", f.fun.s_cy(c)),
5593            VVal::Ref(l)     => format!("$&&{}", (*l).borrow().s_cy(c)),
5594            VVal::HRef(l)    => format!("$&{}", (*l).borrow().s_cy(c)),
5595            VVal::FVec(nvec) => nvec.s(),
5596            VVal::IVec(nvec) => nvec.s(),
5597            VVal::WWRef(l)   => {
5598                match l.upgrade() {
5599                    Some(v) => format!("$w&{}", v.borrow().s_cy(c)),
5600                    None => "$n".to_string(),
5601                }
5602            },
5603        };
5604        format!("{}{}", br, s)
5605    }
5606
5607    pub fn as_bytes(&self) -> std::vec::Vec<u8> {
5608        match self {
5609            VVal::Chr(c) => vec![c.byte()],
5610            VVal::Byt(b) => b.as_ref().clone(),
5611            v => v.with_deref(
5612                |v| v.as_bytes(),
5613                |v| v.map_or_else(
5614                    Vec::new,
5615                    |v| v.with_s_ref(|s: &str| s.as_bytes().to_vec()))),
5616        }
5617    }
5618
5619    pub fn to_duration(&self) -> Result<std::time::Duration, VVal> {
5620        match self {
5621            VVal::Int(i) => Ok(std::time::Duration::from_millis(*i as u64)),
5622            VVal::Pair(b) => {
5623                let a = &b.0;
5624                let b = &b.1;
5625
5626                a.with_s_ref(|astr|
5627                    match astr {
5628                        "s"  => Ok(std::time::Duration::from_secs(b.i() as u64)),
5629                        "ms" => Ok(std::time::Duration::from_millis(b.i() as u64)),
5630                        "us" => Ok(std::time::Duration::from_micros(b.i() as u64)),
5631                        "ns" => Ok(std::time::Duration::from_nanos(b.i() as u64)),
5632                        _    => Err(VVal::err_msg(&format!("Bad duration: {}", self.s()))),
5633                    })
5634            },
5635            _ => Err(VVal::err_msg(&format!("Bad duration: {}", self.s()))),
5636        }
5637    }
5638
5639    /// Returns a string representation of the VVal data structure.
5640    /// It handles cyclic data structures fine.
5641    /// The purpose is to return an unambigous represenation of the data
5642    /// structure. That means strings are quoted and VVal::None becomes `$n`
5643    /// for instance.
5644    ///
5645    /// If you need strings in pure form, use the `s_raw()` method.
5646    ///
5647    /// ```
5648    /// use wlambda::VVal;
5649    ///
5650    /// let v = VVal::None;
5651    /// assert_eq!(v.s(), "$n");
5652    ///
5653    /// assert_eq!(VVal::new_str("Foo").s(), "\"Foo\"");
5654    /// ```
5655    pub fn s(&self) -> String {
5656        let mut cc = CycleCheck::new();
5657        cc.touch_walk(self);
5658        self.s_cy(&mut cc)
5659    }
5660
5661    /// Serializes the VVal (non cyclic) structure to a msgpack byte vector.
5662    #[cfg(feature="rmp-serde")]
5663    pub fn to_msgpack(&self) -> Result<Vec<u8>, String> {
5664        match rmp_serde::to_vec(self) {
5665            Ok(s) => Ok(s),
5666            Err(e) => Err(format!("to_msgpack failed: {}", e))
5667        }
5668    }
5669
5670    /// Creates a VVal structure from a msgpack byte vector.
5671    #[cfg(feature="rmp-serde")]
5672    pub fn from_msgpack(s: &[u8]) -> Result<VVal, String> {
5673        match rmp_serde::from_read_ref(&s) {
5674            Ok(v) => Ok(v),
5675            Err(e) => Err(format!("from_msgpack failed: {}", e)),
5676        }
5677    }
5678
5679    /// Serializes the VVal (non cyclic) structure to a JSON string.
5680    #[cfg(feature="serde_json")]
5681    pub fn to_json(&self, not_pretty: bool) -> Result<String, String> {
5682        if not_pretty {
5683            match serde_json::to_string(self) {
5684                Ok(s) => Ok(s),
5685                Err(e) => Err(format!("to_json failed: {}", e))
5686            }
5687        } else {
5688            match serde_json::to_string_pretty(self) {
5689                Ok(s) => Ok(s),
5690                Err(e) => Err(format!("to_json failed: {}", e))
5691            }
5692        }
5693    }
5694
5695    /// Creates a VVal structure from a JSON string.
5696    #[cfg(feature="serde_json")]
5697    pub fn from_json(s: &str) -> Result<VVal, String> {
5698        match serde_json::from_str(s) {
5699            Ok(v) => Ok(v),
5700            Err(e) => Err(format!("from_json failed: {}", e)),
5701        }
5702    }
5703}
5704
5705#[cfg(feature="serde")]
5706impl serde::ser::Serialize for VVal {
5707    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
5708        where S: serde::ser::Serializer {
5709        use serde::ser::{SerializeSeq, SerializeMap};
5710
5711        match self {
5712            VVal::Str(_)     => self.with_s_ref(|s: &str| serializer.serialize_str(s)),
5713            VVal::Sym(_)     => self.with_s_ref(|s: &str| serializer.serialize_str(s)),
5714            VVal::Byt(b)     => serializer.serialize_bytes(&b[..]),
5715            VVal::Chr(b)     =>
5716                match b {
5717                    VValChr::Char(c) => {
5718                        let mut buf = [0; 6];
5719                        serializer.serialize_str(c.encode_utf8(&mut buf))
5720                    },
5721                    VValChr::Byte(b) => { serializer.serialize_u8(*b) },
5722                },
5723            VVal::None       => serializer.serialize_none(),
5724            VVal::Iter(_)    => serializer.serialize_none(),
5725            VVal::Err(_)     => serializer.serialize_str(&self.s()),
5726            VVal::Bol(b)     => serializer.serialize_bool(*b),
5727            VVal::Syn(_)     => serializer.serialize_str(&self.s()),
5728            VVal::Int(i)     => serializer.serialize_i64(*i),
5729            VVal::Flt(f)     => serializer.serialize_f64(*f),
5730            VVal::Pair(b)    => {
5731                let mut seq = serializer.serialize_seq(Some(2))?;
5732                seq.serialize_element(&b.0)?;
5733                seq.serialize_element(&b.1)?;
5734                seq.end()
5735            },
5736            VVal::Opt(b)    => {
5737                if let Some(b) = b {
5738                    let mut seq = serializer.serialize_seq(Some(1))?;
5739                    seq.serialize_element(b.as_ref())?;
5740                    seq.end()
5741                } else {
5742                    let seq = serializer.serialize_seq(Some(0))?;
5743                    seq.end()
5744                }
5745            },
5746            VVal::Lst(l)     => {
5747                let mut seq = serializer.serialize_seq(Some(l.borrow().len()))?;
5748                for v in l.borrow().iter() {
5749                    seq.serialize_element(v)?;
5750                }
5751                seq.end()
5752            },
5753            VVal::Map(l) => {
5754                let hm = l.borrow();
5755
5756                let mut map = serializer.serialize_map(Some(l.borrow().len()))?;
5757                for (k, v) in hm.iter() {
5758                    map.serialize_entry(k.as_ref(), v)?;
5759                }
5760                map.end()
5761            },
5762            VVal::Usr(_)     => serializer.serialize_str(&self.s()),
5763            VVal::Fun(_)     => serializer.serialize_str(&self.s()),
5764            VVal::FVec(fv)   => {
5765                match fv.as_ref() {
5766                    NVec::Vec2(x, y) => {
5767                        let mut seq = serializer.serialize_seq(Some(2))?;
5768                        seq.serialize_element(x)?;
5769                        seq.serialize_element(y)?;
5770                        seq.end()
5771                    },
5772                    NVec::Vec3(x, y, z) => {
5773                        let mut seq = serializer.serialize_seq(Some(3))?;
5774                        seq.serialize_element(x)?;
5775                        seq.serialize_element(y)?;
5776                        seq.serialize_element(z)?;
5777                        seq.end()
5778                    },
5779                    NVec::Vec4(x, y, z, w) => {
5780                        let mut seq = serializer.serialize_seq(Some(4))?;
5781                        seq.serialize_element(x)?;
5782                        seq.serialize_element(y)?;
5783                        seq.serialize_element(z)?;
5784                        seq.serialize_element(w)?;
5785                        seq.end()
5786                    },
5787                }
5788            },
5789            VVal::IVec(iv)   => {
5790                match iv.as_ref() {
5791                    NVec::Vec2(x, y) => {
5792                        let mut seq = serializer.serialize_seq(Some(2))?;
5793                        seq.serialize_element(x)?;
5794                        seq.serialize_element(y)?;
5795                        seq.end()
5796                    },
5797                    NVec::Vec3(x, y, z) => {
5798                        let mut seq = serializer.serialize_seq(Some(3))?;
5799                        seq.serialize_element(x)?;
5800                        seq.serialize_element(y)?;
5801                        seq.serialize_element(z)?;
5802                        seq.end()
5803                    },
5804                    NVec::Vec4(x, y, z, w) => {
5805                        let mut seq = serializer.serialize_seq(Some(4))?;
5806                        seq.serialize_element(x)?;
5807                        seq.serialize_element(y)?;
5808                        seq.serialize_element(z)?;
5809                        seq.serialize_element(w)?;
5810                        seq.end()
5811                    },
5812                }
5813            },
5814            VVal::DropFun(_) => serializer.serialize_str(&self.s()),
5815            VVal::Ref(_)     => self.deref().serialize(serializer),
5816            VVal::HRef(_)    => self.deref().serialize(serializer),
5817            VVal::WWRef(_)   => self.deref().serialize(serializer),
5818        }
5819    }
5820}
5821
5822#[cfg(feature="serde")]
5823struct VValVisitor;
5824
5825#[cfg(feature="serde")]
5826impl<'de> serde::de::Visitor<'de> for VValVisitor {
5827    type Value = VVal;
5828
5829    fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
5830        formatter.write_str("a VVal")
5831    }
5832
5833    fn visit_i128<E>(self, value: i128) -> Result<Self::Value, E>
5834        where E: serde::de::Error { Ok(VVal::Int(value as i64)) }
5835    fn visit_i64<E>(self, value: i64) -> Result<Self::Value, E>
5836        where E: serde::de::Error { Ok(VVal::Int(value)) }
5837    fn visit_i32<E>(self, value: i32) -> Result<Self::Value, E>
5838        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5839    fn visit_i16<E>(self, value: i16) -> Result<Self::Value, E>
5840        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5841    fn visit_i8<E>(self, value: i8) -> Result<Self::Value, E>
5842        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5843    fn visit_u128<E>(self, value: u128) -> Result<Self::Value, E>
5844        where E: serde::de::Error { Ok(VVal::Int(value as i64)) }
5845    fn visit_u64<E>(self, value: u64) -> Result<Self::Value, E>
5846        where E: serde::de::Error { Ok(VVal::Int(value as i64)) }
5847    fn visit_u32<E>(self, value: u32) -> Result<Self::Value, E>
5848        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5849    fn visit_u16<E>(self, value: u16) -> Result<Self::Value, E>
5850        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5851    fn visit_u8<E>(self, value: u8) -> Result<Self::Value, E>
5852        where E: serde::de::Error { Ok(VVal::Int(i64::from(value))) }
5853
5854    fn visit_f64<E>(self, value: f64) -> Result<Self::Value, E>
5855        where E: serde::de::Error { Ok(VVal::Flt(value)) }
5856    fn visit_f32<E>(self, value: f32) -> Result<Self::Value, E>
5857        where E: serde::de::Error { Ok(VVal::Flt(f64::from(value))) }
5858
5859    fn visit_bool<E>(self, value: bool) -> Result<Self::Value, E>
5860        where E: serde::de::Error { Ok(VVal::Bol(value)) }
5861
5862    fn visit_str<E>(self, value: &str) -> Result<Self::Value, E>
5863        where E: serde::de::Error { Ok(VVal::new_str(value)) }
5864
5865    fn visit_bytes<E>(self, value: &[u8]) -> Result<Self::Value, E>
5866        where E: serde::de::Error { Ok(VVal::new_byt(value.to_vec())) }
5867
5868    fn visit_none<E>(self) -> Result<Self::Value, E>
5869        where E: serde::de::Error { Ok(VVal::None) }
5870    fn visit_unit<E>(self) -> Result<Self::Value, E>
5871        where E: serde::de::Error { Ok(VVal::None) }
5872
5873    fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
5874        where A: serde::de::SeqAccess<'de> {
5875
5876        let v = VVal::vec();
5877
5878        while let Some(ve) = seq.next_element()? {
5879            v.push(ve);
5880        }
5881
5882        Ok(v)
5883    }
5884
5885    fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error>
5886        where A: serde::de::MapAccess<'de> {
5887
5888        let v = VVal::map();
5889
5890        while let Some((ke, ve)) = map.next_entry()? {
5891            let k : VVal = ke;
5892            v.set_key(&k, ve)
5893             .expect("Deserialized map not used more than once");
5894        }
5895
5896        Ok(v)
5897    }
5898}
5899
5900#[cfg(feature="serde")]
5901impl<'de> serde::de::Deserialize<'de> for VVal {
5902    fn deserialize<D>(deserializer: D) -> Result<VVal, D::Error>
5903        where D: serde::de::Deserializer<'de>,
5904    {
5905        deserializer.deserialize_any(VValVisitor)
5906    }
5907}