/* parrotinterpreter.pmc
 *  Copyright: 2001-2003 The Perl Foundation.  All Rights Reserved.
 *  CVS Info
 *     $Id: parrotinterpreter.pmc,v 1.5 2003/08/28 13:17:01 leo Exp $
 *  Overview:
 *     These are the vtable functions for the ParrotInterpreter base class
 *  Data Structure and Algorithms:
 *  History:
 *  Notes:
 *     getinterp P0
 *     set P1, P0[.IGLOBALS_*]	# access interpreter globals
 *     set I0, P0[x]		# interpinfo I0, x
 *     set I0, P0[-1]		# get interpreter flags
 *     set P0[-1], x		# set flags on interpreter
 *  References:
 */

#include "parrot/parrot.h"

pmclass ParrotInterpreter need_ext {

    void init () {
	struct Parrot_Interp *new_interp;
	new_interp = make_interpreter(0);
	new_interp->parent_interpreter = interpreter;
	PMC_data(SELF) = new_interp;
    }
    void set_integer_native (INTVAL value) {
	SELF->cache.int_val = value;
    }

    void* invoke (void* next) {
	struct Parrot_Interp * new_interp =
	    (struct Parrot_Interp *)PMC_data(SELF);
	Interp_flags_SET(new_interp, PARROT_EXTERN_CODE_FLAG);
	new_interp->code = interpreter->code;
	/* this is obviously the wrong offset */
	runops(new_interp, (opcode_t *)SELF->cache.int_val - (opcode_t *)next);
	return next;
    }

    PMC* get_pmc_keyed_int(INTVAL key) {
	struct Parrot_Interp * new_interp =
	    (struct Parrot_Interp *)PMC_data(SELF);
	if (key >= 0 && key < IGLOBALS_SIZE)
	    return VTABLE_get_pmc_keyed_int(new_interp,
		    new_interp->iglobals, key);
	return NULL;
    }
    INTVAL get_integer_keyed_int(INTVAL key) {
	struct Parrot_Interp * new_interp =
	    (struct Parrot_Interp *)PMC_data(SELF);
	switch (key) {
	    case -1:
		return (INTVAL) new_interp->flags;
	    default:
		return interpinfo(new_interp, key);
	}
    }

    void set_integer_keyed_int(INTVAL key, INTVAL val) {
	struct Parrot_Interp * new_interp =
	    (struct Parrot_Interp *)PMC_data(SELF);
	INTVAL allowed;

	switch (key) {
	    case -1:	/* set interpreter flags */
		allowed =
		    PARROT_DEBUG_FLAG |
		    PARROT_TRACE_FLAG |
		    PARROT_BOUNDS_FLAG |
		    PARROT_PROFILE_FLAG |
		    PARROT_PREDEREF_FLAG |
		    PARROT_JIT_FLAG   |
		    PARROT_CGOTO_FLAG  |
		    PARROT_GC_DEBUG_FLAG |
		    PARROT_SWITCH_FLAG;
		Interp_flags_CLEAR(new_interp, allowed);
		Interp_flags_SET(new_interp, val & allowed);
		break;
	}
    }
}
