/*
 * Copyright (C) 2018-2020 Western Digital Corporation or its affiliates
 * Copyright (C) 2017-2018 Wearable, Inc.
 * Copyright (C) 2000-2012 leJOS Contributors
 * Copyright (C) 2000 Jose H. Solorzano and TinyVM Contributors
 *
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at https://mozilla.org/MPL/2.0/.
 * 
 * This Source Code Form is “Incompatible With Secondary Licenses”,
 * as defined by the Mozilla Public License, v. 2.0.
 */

#ifndef INTERPRETER_H
#define INTERPRETER_H

#include "types.h"
#include "constants.h"
#include "classes.h"
#include "state.h"

#define REQUEST_TICK          0
#define REQUEST_SWITCH_THREAD 1
#define REQUEST_EXIT          2

// Allow external control of VM
#define VM_DEFAULT 0
#define VM_TYPECHECKS 1
#define VM_ASSERTS 2
#define VM_MEMCOMPACT 4
#define type_checks_enabled(state) (state->vm_options & VM_TYPECHECKS)

#define getPc(state) (state->program_counter + state->program_offset)

#if FAST_DISPATCH
#define FORCE_EVENT_CHECK(state) ((state)->dispatch_table = (state)->dispatch_check_event)
#define SCHEDULER_REQUESTED(state) ((state)->dispatch_table == (state)->dispatch_check_event)
#else
#define FORCE_EVENT_CHECK(state) ((state)->scheduler_make_request = true)
#define SCHEDULER_REQUESTED(state) ((state)->scheduler_make_request)
#endif

static inline void schedule_request (nvm_state_t* pState, const byte aCode)
{
  FORCE_EVENT_CHECK(pState);
  pState->scheduler_request_code = aCode;
}

void engine(nvm_state_t*);

#endif
