inline bool set_local_depth(STATE, CallFrame* call_frame, intptr_t depth, intptr_t index) {
      if(depth == 0) {
        Exception::internal_error(state, "illegal set_local_depth usage");
        return false;
      } else {
        VariableScope* scope = call_frame->scope->parent();

        if(!scope || scope->nil_p()) {
          Exception::internal_error(state, "illegal set_local_depth usage, no parent");
          return false;
        }

        for(int j = 1; j < depth; j++) {
          scope = scope->parent();
          if(!scope || scope->nil_p()) {
            Exception::internal_error(state, "illegal set_local_depth usage, no parent");
            return false;
          }
        }

        if(index >= scope->number_of_locals()) {
          Exception::internal_error(state, "illegal set_local_depth usage, bad index");
          return false;
        }
        Object* val = stack_pop();
        scope->set_local(state, index, val);
        stack_push(val);
        return true;
      }
    }
Beispiel #2
0
  void VariableScope::Info::mark(Object* obj, ObjectMark& mark) {
    auto_mark(obj, mark);

    VariableScope* vs = as<VariableScope>(obj);

    vs->fixup();


    Object* tmp;

    size_t locals = vs->number_of_locals();
    for(size_t i = 0; i < locals; i++) {
      tmp = mark.call(vs->get_local(i));
      if(tmp) vs->set_local(mark.state(), i, tmp);
    }
  }
Beispiel #3
0
  VariableScope* StackVariables::create_heap_alias(STATE, CallFrame* call_frame,
                                                   bool full)
  {
    if(on_heap_) return on_heap_;

    MachineCode* mcode = call_frame->compiled_code->machine_code();
    VariableScope* scope =
      state->memory()->new_object<VariableScope>(state, G(variable_scope));

    if(parent_) {
      scope->parent(state, parent_);
    } else {
      scope->parent(state, nil<VariableScope>());
    }

    scope->self(state, self_);
    scope->block(state, block_);
    scope->module(state, module_);
    scope->method(state, call_frame->compiled_code);
    scope->heap_locals(state, nil<Tuple>());
    scope->last_match(state, last_match_);
    scope->fiber(state, state->vm()->thread()->current_fiber());

    scope->number_of_locals(mcode->number_of_locals);
    scope->isolated(0);
    scope->flags(call_frame->flags);
    scope->_lock_.init();

    if(!full) {
      scope->isolated(1);
      scope->heap_locals(state, Tuple::create(state, mcode->number_of_locals));
      for(int i = 0; i < scope->number_of_locals(); i++) {
        scope->set_local(state, i, locals_[i]);
      }
    }

    scope->locals(locals_);
    scope->dynamic_locals(state, nil<LookupTable>());

    on_heap_ = scope;

    return scope;
  }
Beispiel #4
0
  VariableScope* VariableScope::promote(STATE) {
    VariableScope* scope = state->new_struct<VariableScope>(
        G(variable_scope), number_of_locals_ * sizeof(Object*));

    scope->block(state, block_);
    scope->method(state, method_);
    scope->module(state, module_);
    if(parent_) {
      scope->parent(state, parent_);
    } else {
      scope->parent(state, (VariableScope*)Qnil);
    }
    scope->self(state, self_);

    scope->number_of_locals_ = number_of_locals_;

    for(int i = 0; i < number_of_locals_; i++) {
      scope->set_local(state, i, locals_[i]);
    }

    return scope;
  }