fn pre_bind_call(load_fn: CellRef, args: CellRef, bindings: SymbolBindings) -> (SymbolBindings, CellRef) {
    let mut bindings = bindings;

    // Start by pushing the function value onto the stack (we'll pop it later on to call the function)
    let mut actions = vec![load_fn];

    // Push the arguments
    let mut next_arg    = args;
    let mut hanging_cdr = false;

    loop {
        match &*next_arg {
            SafasCell::List(car, cdr) => {
                // Evaluate car and push it onto the stack
                let (next_bindings, next_action) = pre_bind_statement(Arc::clone(car), bindings);

                actions.push(next_action);

                bindings    = next_bindings;

                // cdr contains the next argument
                next_arg    = Arc::clone(cdr);
            }

            SafasCell::Nil => {
                // Got a complete list
                break;
            }

            _other => {
                // Incomplete list: evaluate the CDR value
                let (next_bindings, next_action) = pre_bind_statement(next_arg, bindings);
                actions.push(next_action);

                bindings    = next_bindings;
                hanging_cdr = true;
                break;
            }
        }
    }

    // If there was a 'hanging' CDR, then generate a result with the same format, otherwise generate a well-formed list
    if hanging_cdr {
        let cdr = actions.pop();
        (bindings, SafasCell::list_with_cells_and_cdr(actions, cdr.unwrap()).into())
    } else {
        (bindings, SafasCell::list_with_cells(actions).into())
    }
}
///
/// Pre-binds a call operation given the value that will evaluate to the function
///
Pre-binds a call operation given the value that will evaluate to the function
Pre - binds a call operation given the value that will evaluate to the function
fn pre_bind_call(load_fn: CellRef, args: CellRef, bindings: SymbolBindings) -> (SymbolBindings, CellRef) {
    let mut bindings = bindings;
    // Start by pushing the function value onto the stack (we'll pop it later on to call the function)
    let mut actions = vec![load_fn];
    // Push the arguments
    let mut next_arg    = args;
    let mut hanging_cdr = false;
    loop {
        match &*next_arg {
            SafasCell::List(car, cdr) => {
                // Evaluate car and push it onto the stack
                let (next_bindings, next_action) = pre_bind_statement(Arc::clone(car), bindings);
                actions.push(next_action);
                bindings    = next_bindings;
                // cdr contains the next argument
                next_arg    = Arc::clone(cdr);
            }
            SafasCell::Nil => {
                // Got a complete list
                break;
            }
            _other => {
                // Incomplete list: evaluate the CDR value
                let (next_bindings, next_action) = pre_bind_statement(next_arg, bindings);
                actions.push(next_action);
                bindings    = next_bindings;
                hanging_cdr = true;
                break;
            }
        }
    }
    // If there was a 'hanging' CDR, then generate a result with the same format, otherwise generate a well-formed list
    if hanging_cdr {
        let cdr = actions.pop();
        (bindings, SafasCell::list_with_cells_and_cdr(actions, cdr.unwrap()).into())
    } else {
        (bindings, SafasCell::list_with_cells(actions).into())
    }
}
fn pre_bind_call ( load_fn : CellRef , args : CellRef , bindings : SymbolBindings ) -> ( SymbolBindings , CellRef ) { let mut bindings = bindings ; // Start by pushing the function value onto the stack (we'll pop it later on to call the function) let mut actions = vec ! [ load_fn ] ; // Push the arguments let mut next_arg = args ; let mut hanging_cdr = false ; loop { match & * next_arg { SafasCell :: List ( car , cdr ) => { // Evaluate car and push it onto the stack let ( next_bindings , next_action ) = pre_bind_statement ( Arc :: clone ( car ) , bindings ) ; actions . push ( next_action ) ; bindings = next_bindings ; // cdr contains the next argument next_arg = Arc :: clone ( cdr ) ; } SafasCell :: Nil => { // Got a complete list break ; } _other => { // Incomplete list: evaluate the CDR value let ( next_bindings , next_action ) = pre_bind_statement ( next_arg , bindings ) ; actions . push ( next_action ) ; bindings = next_bindings ; hanging_cdr = true ; break ; } } } // If there was a 'hanging' CDR, then generate a result with the same format, otherwise generate a well-formed list if hanging_cdr { let cdr = actions . pop ( ) ; ( bindings , SafasCell :: list_with_cells_and_cdr ( actions , cdr . unwrap ( ) ) . into ( ) ) } else { ( bindings , SafasCell :: list_with_cells ( actions ) . into ( ) ) } }
Pre-binds a call operation given the value that will evaluate to the function
Pre - binds a call operation given the value that will evaluate to the function
load_fn
CellRef
args
CellRef
bindings
SymbolBindings
load_fn
CellRef
args
CellRef
bindings
SymbolBindings