| /* NEXT and NEXT1 are split into several parts to help scheduling */ |
/* NEXT and NEXT1 are split into several parts to help scheduling */ |
| #ifdef DIRECT_THREADED |
#ifdef DIRECT_THREADED |
| # define NEXT1_P1 |
# define NEXT1_P1 |
| |
# ifdef i386 |
| |
# define NEXT1_P2 ({cfa=*ip++; goto *cfa;}) |
| |
# else |
| # define NEXT1_P2 ({goto *cfa;}) |
# define NEXT1_P2 ({goto *cfa;}) |
| |
# endif |
| # define DEF_CA |
# define DEF_CA |
| #else |
#else |
| # define NEXT1_P1 ({ca = *cfa;}) |
# define NEXT1_P1 ({ca = *cfa;}) |
| # define NEXT1_P2 ({goto *ca;}) |
# define NEXT1_P2 ({goto *ca;}) |
| # define DEF_CA Label ca; |
# define DEF_CA Label ca; |
| #endif |
#endif |
| |
#if defined(i386) && defined(DIRECT_THREADED) |
| |
# define NEXT_P1 |
| |
# define NEXT1 ({goto *cfa;}) |
| |
#else |
| #define NEXT_P1 ({cfa = *ip++; NEXT1_P1;}) |
#define NEXT_P1 ({cfa = *ip++; NEXT1_P1;}) |
| |
|
| #define NEXT1 ({DEF_CA NEXT1_P1; NEXT1_P2;}) |
#define NEXT1 ({DEF_CA NEXT1_P1; NEXT1_P2;}) |
| |
#endif |
| |
|
| #define NEXT ({DEF_CA NEXT_P1; NEXT1_P2;}) |
#define NEXT ({DEF_CA NEXT_P1; NEXT1_P2;}) |
| |
|
| #ifdef USE_TOS |
#ifdef USE_TOS |
| int emitcounter; |
int emitcounter; |
| #define NULLC '\0' |
#define NULLC '\0' |
| |
|
| |
#ifdef copycstr |
| #define cstr(to,from,size)\ |
#define cstr(to,from,size)\ |
| { memcpy(to,from,size);\ |
{ memcpy(to,from,size);\ |
| to[size]=NULLC;} |
to[size]=NULLC;} |
| |
#else |
| |
char scratch[1024]; |
| |
int soffset; |
| |
# define cstr(from,size) \ |
| |
({ char * to = scratch; \ |
| |
memcpy(to,from,size); \ |
| |
to[size] = NULLC; \ |
| |
soffset = size+1; \ |
| |
to; \ |
| |
}) |
| |
# define cstr1(from,size) \ |
| |
({ char * to = scratch+soffset; \ |
| |
memcpy(to,from,size); \ |
| |
to[size] = NULLC; \ |
| |
soffset += size+1; \ |
| |
to; \ |
| |
}) |
| |
#endif |
| |
|
| #define NEWLINE '\n' |
#define NEWLINE '\n' |
| |
|
| |
|
| static char* fileattr[6]={"r","rb","r+","r+b","w+","w+b"}; |
static char* fileattr[6]={"r","rb","r+","r+b","w+","w+b"}; |
| |
|
| static Address up0=NULL; |
static Address up0=NULL; |
| |
|
| |
#if defined(i386) && defined(FORCE_REG) |
| |
# define REG(reg) __asm__(reg) |
| |
|
| |
Label *engine(Xt *ip0, Cell *sp0, Cell *rp, Float *fp, Address lp) |
| |
{ |
| |
register Xt *ip REG("%esi")=ip0; |
| |
register Cell *sp REG("%edi")=sp0; |
| |
|
| |
#else |
| |
# define REG(reg) |
| |
|
| Label *engine(Xt *ip, Cell *sp, Cell *rp, Float *fp, Address lp) |
Label *engine(Xt *ip, Cell *sp, Cell *rp, Float *fp, Address lp) |
| |
{ |
| |
#endif |
| /* executes code at ip, if ip!=NULL |
/* executes code at ip, if ip!=NULL |
| returns array of machine code labels (for use in a loader), if ip==NULL |
returns array of machine code labels (for use in a loader), if ip==NULL |
| */ |
*/ |
| { |
register Xt cfa |
| Xt cfa; |
#ifdef i386 |
| |
# ifdef USE_TOS |
| |
REG("%ecx") |
| |
# else |
| |
REG("%edx") |
| |
# endif |
| |
#endif |
| |
; |
| Address up=up0; |
Address up=up0; |
| static Label symbols[]= { |
static Label symbols[]= { |
| &&docol, |
&&docol, |
| #ifdef DEBUG |
#ifdef DEBUG |
| printf("%08x: col: %08x\n",(Cell)ip,(Cell)PFA1(cfa)); |
printf("%08x: col: %08x\n",(Cell)ip,(Cell)PFA1(cfa)); |
| #endif |
#endif |
| #ifdef undefined |
#ifdef i386 |
| /* this is the simple version */ |
/* this is the simple version */ |
| *--rp = (Cell)ip; |
*--rp = (Cell)ip; |
| ip = (Xt *)PFA1(cfa); |
ip = (Xt *)PFA1(cfa); |
| #endif |
#endif |
| *--rp = (Cell)ip; |
*--rp = (Cell)ip; |
| /* PFA1 might collide with DOES_CODE1 here, so we use PFA */ |
/* PFA1 might collide with DOES_CODE1 here, so we use PFA */ |
| |
ip = DOES_CODE1(cfa); |
| #ifdef USE_TOS |
#ifdef USE_TOS |
| *sp-- = TOS; |
*sp-- = TOS; |
| TOS = (Cell)PFA(cfa); |
TOS = (Cell)PFA(cfa); |
| #else |
#else |
| *--sp = (Cell)PFA(cfa); |
*--sp = (Cell)PFA(cfa); |
| #endif |
#endif |
| ip = DOES_CODE1(cfa); |
|
| NEXT; |
NEXT; |
| |
|
| #include "primitives.i" |
#include "primitives.i" |