#ifndef INTERPRET_H #define INTERPRET_H struct shared; struct regexp; union storage_union { float fnum; int number; struct shared *string; struct object *ob; struct vector *vec; struct lvalue *lvalue; struct regexp *regexp; int *ref; }; /* * The value stack element. * If it is a string, then the way that the string has been allocated differ, * wich will affect how it should be freed. */ struct svalue { unsigned short type; unsigned short subtype; union storage_union u; }; /* 0 must be without need to be freed */ #define T_POINTER 0 #define T_OBJECT 1 #define T_MAPPING 2 #define T_LIST 3 #define T_ALIST_PART 4 #define T_FUNCTION 5 #define T_REGEXP 6 #define T_STRING 7 #define T_FLOAT 8 #define T_LVALUE 9 #define T_NUMBER 10 #define T_NOTHING 254 #define T_ANY 255 #ifdef STRALLOC_GC #define MAX_REF_TYPE T_REGEXP #else #define MAX_REF_TYPE T_STRING #endif #define T_INT T_NUMBER #define BT_LVALUE (1<<T_LVALUE) #define BT_NUMBER (1<<T_NUMBER) #define BT_STRING (1<<T_STRING) #define BT_POINTER (1<<T_POINTER) #define BT_OBJECT (1<<T_OBJECT) #define BT_MAPPING (1<<T_MAPPING) #define BT_LIST (1<<T_LIST) #define BT_ALIST_PART (1<<T_ALIST_PART) #define BT_FUNCTION (1<<T_FUNCTION) #define BT_FLOAT (1<<T_FLOAT) #define BT_REGEXP (1<<T_REGEXP) #define BT_INT (1<<T_INT) #define BT_ANY 0xffff /* these types uses the .u.vec */ #define BT_VECTOR (BT_ALIST_PART | BT_POINTER | BT_MAPPING | BT_LIST) #define IS_TYPE(X,Y) ((1<<(X).type) & (Y)) /* different types of zeros */ #define NUMBER_NUMBER 0 /* normal number */ #define NUMBER_UNDEFINED 1 /* value not present */ #define NUMBER_DESTRUCTED_OBJECT 2 /* a destructed object */ #define NUMBER_DESTRUCTED_FUNCTION 3 /* a function in a destructed object */ #define LVALUE_INDEX 0 #define LVALUE_RANGE 1 #define LVALUE_LOCAL 2 #define LVALUE_GLOBAL 3 #define LVALUE_SHORT_GLOBAL 4 #define LVALUES 800 struct lvalue { short type; short rttype; union ptr { struct svalue *sval; union storage_union *uval; } ptr; struct svalue ind; }; struct lnode_def; void free_vector PROT((struct vector *)); void free_all_values(); /* * Control stack element. * 'prog' is usually same as 'ob->prog' (current_object), except when * when the current function is defined by inheritance. * The pointer, csp, will point to the values that will be used at return. */ struct control_stack { struct object *comgiver; /* Always save the command giver... */ struct object *ob; /* Current object */ struct program *prog; /* Current program */ int num_local_variables; /* Local + arguments */ int num_of_arguments; /* Local + arguments */ char *pc; struct svalue *fp; struct function *funp; /* Only used for tracebacks */ int func; /* funp==prog->funcions[func] */ int function_index_offset; /* Used when executing functions in inherited programs */ int variable_index_offset; /* Same */ struct vector *va_args; /* remaining arguments */ }; #define IS_ZERO(x) (!(x) || (((x)->type == T_NUMBER) && ((x)->u.number == 0))) #define SET_TO_ZERO(x) ((x).type=T_NUMBER,(x).subtype=NUMBER_NUMBER,(x).u.number=0) #define SET_TO_ONE(x) ((x).type=T_NUMBER,(x).subtype=NUMBER_NUMBER,(x).u.number=1) #define SET_TO_UNDEFINED(x) ((x).type=T_NUMBER,(x).subtype=NUMBER_UNDEFINED,(x).u.number=0) #define SET_STR(X,Y) ((X)->type=T_STRING,(X)->u.string=BASE(Y)) struct svalue *apply_lfun(int fun,struct object *ob,int num_arg,int ignorestatic); struct svalue *apply PROT((char *, struct object *, int,int)); struct svalue *apply_shared PROT((char *, struct object *, int,int)); int apply_lambda_low(struct object *,int,int,int); struct svalue *apply_lambda(struct svalue *,int,int); struct svalue *apply_master_ob PROT((char *fun, int num_arg)); struct svalue *safe_apply (char *fun,struct object * ob,int num_arg); struct svalue *safe_apply_lambda(struct svalue *lambda,int num_arg); struct svalue *apply_numbered_fun(struct object *o,int fun,int num_arg,int ignorestatic); void push_string PROT((char *)); void push_number PROT((int)); void push_object PROT((struct object *)); int inter_sscanf PROT((int)); void assert_master_ob_loaded(); void check_eval_cost(); char *function_exists PROT((char *, struct object *)); char *function_exists_in_prog(char *fun,struct program *prog); int get_line_number_if_any PROT((void)); void check_a_lot_ref_counts PROT((struct program *)); void clear_state PROT((void)); void reset_machine PROT((int)); void push_svalue PROT((struct svalue *)); void push_new_shared_string(char *p); void call_function PROT((struct program *, struct function *)); int find_function(char *fun,struct program *prog); int find_shared_string_function(char *fun,struct program *prog); void pop_stack(); void push_zero(); void push_shared_string(char *); void push_malloced_string(char *); void pop_n_elems(int); void bad_arg(int arg,int instruction) ATTRIBUTE((noreturn)); void push_vector(struct vector *v); void push_one(); struct svalue *find_value(int num); void eval_instruction(char *p); INLINE void push_mapping(struct vector *v); void assign_svalue PROT((struct svalue *, struct svalue *)); void move_svalue PROT((struct svalue *, struct svalue *)); INLINE void assign_svalue_no_free PROT((struct svalue *to, struct svalue *from)); #ifdef DEBUG void assign_svalue_raw PROT((struct svalue *to, struct svalue *from)); #else #define assign_svalue_raw(TO,FROM) \ { struct svalue t; *(TO)=t=*(FROM); if(t.type<=MAX_REF_TYPE) t.u.ref[0]++; } #endif INLINE void free_svalue PROT((struct svalue *)); INLINE void free_svalues PROT((struct svalue *,int)); INLINE void free_lvalue PROT((struct lvalue *)); INLINE void push_control_stack(struct function *funp); void pop_control_stack(); void push_pop_error_context (int push); INLINE void push_conditional(int f); INLINE void copy_svalue(struct svalue *dest,struct svalue *src); void copy_svalues_no_free(struct svalue *to,struct svalue *from,int num); void copy_svalues(struct svalue *,struct svalue *,int); void copy_svalues_raw(struct svalue *,struct svalue *,int); INLINE void push_list(struct vector *v); INLINE void assign_short_svalue_no_free(union storage_union *to, struct svalue *from, unsigned short type); INLINE void assign_short_svalue(union storage_union *to, struct svalue *from, unsigned short type); INLINE void free_short_svalue(union storage_union *u, unsigned short type); INLINE void assign_svalue_from_short_no_free(struct svalue *to, union storage_union *from, unsigned short type); #define APPLY_MASTER_OB(RET,FUN,ARGS) \ { \ static int fun_,master_cnt=0; \ extern struct object *master_ob; \ assert_master_ob_loaded(); \ if(master_cnt!=master_ob->prog->id) \ { \ fun_=find_function(FUN,master_ob->prog); \ master_cnt=master_ob->prog->id; \ } \ RET apply_numbered_fun(master_ob,fun_,ARGS,1); \ } extern struct svalue const_empty_string; #endif