void nofunc( void ) { uint8 n = ins_ptr[-1]; printf( "\afunction %s (%02x) not implemented\n", iname[n], (int)n ); rdch(); } /* nofunc() */
void readfile( void ) { VMRef v; Symbol * s; word op = 0; /* * Quick Test. * Determine if the first byte in the input file is a GHOF * directive. If not then do not bother to parse the rest * of the file. */ op = getc( infd ); if (op >= 0x40) { #if defined __ARM && (defined RS6000 || defined __SUN4) /* only support AOF -> GHOF conversion when cross linking */ if (op == 0xC3 || op == 0xC5) { s_aof * pAOF; uword iCodeSize; char * pTempFileName; trace( "Assuming file is in AOF format" ); pTempFileName = malloc( strlen( infile_duplicate ) + 5 /* strlen( ".ghof" ) */ + 1 ); if (pTempFileName == NULL) { error( "Out of memory allocating temporary file name" ); return; } strcpy( pTempFileName, infile_duplicate ); strcat( pTempFileName, ".ghof" ); file_trace( "creating GHOF copy of AOF file '%s'", infile_duplicate ); pAOF = open_aof( infile_duplicate ); if (pAOF == NULL) { error( "Failed to reopen file in AOF mode" ); return; } (void)convert_aof( pAOF, pTempFileName, bSharedLib, bTinyModel, bDeviceDriver ); /* Open the temporary file again */ file_trace( "opening GHOF copy '%s'", pTempFileName ); infd = freopen( pTempFileName, "rb", infd ); if (infd == NULL) { error( "Unable to reopen temporary file %s", pTempFileName ); return; } else file_trace( "copy opened" ); free( pTempFileName ); /* drop throiugh into normal readfile() code */ } else #endif /* __ARM and (RS6000 or __SUN4) */ { error( "Input file is not in GHOF format" ); return; } } else { ungetc( (char)op, infd ); } do { op = rdint(); trace("OP = %x, curloc = %x, codepos = %x",op,curloc, codepos); switch( op ) { default: error( "Illegal linker directive '%x'", op ); break; case EOF: return; case OBJCODE: { word size = rdint(); if (size < 0) error( "Negative sized code directive encountered (%x)", size ); trace("CODE %d",size); while( size-- ) genbyte(rdch()); break; } case OBJBSS: { word size = rdint(); if (size < 0) error("Negative sized bss defined"); trace("BSS %d",size); while( size-- ) genbyte(0L); break; } case OBJWORD: genpatch( OBJWORD ); break; case OBJSHORT: genpatch( OBJSHORT ); break; case OBJBYTE: genpatch( OBJBYTE ); break; case OBJINIT: geninit(); break; case OBJMODULE: genmodule(rdint()); break; case OBJBYTESEX: if( bytesex != 0 ) error("bytesex already set"); bytesex = rdint(); trace("BYTESEX %d",bytesex); break; case OBJREF: v = rdsymb(); movesym(v); /* XXX - all REF symbols are implicitly global */ refsymbol_nondef(v); break; case OBJGLOBAL: v = rdsymb(); s = VMAddr(Symbol,v); movesym(v); if (s->referenced) { refsymbol_def(v); } break; case OBJLABEL: v = rdsymb(); s = VMAddr(Symbol,v); trace("LABEL %s",s->name); if( s->type != S_UNBOUND ) { if (!inlib) warn( "Duplicate definition of symbol '%s' defined in file '%s'", s->name, s->file_name ); } else { if (s->AOFassumedData) { error( "(AOF) Symbol '%s' has been assumed to be data in file '%s'", s->name, s->file_name ); s->AOFassumedData = FALSE; } copycode(); s->type = S_CODESYMB; s->value.v = codeptr(); s->module = curmod; s->file_name = infile_duplicate; if (s->referenced) refsymbol_def(v); { int len = strlen( s->name ); /* hack to insert correct name for resident libraries */ VMlock( v ); if (len > 8 && strcmp( s->name + len - 8, ".library" ) == 0 && VMAddr( asm_Module, curmod )->id != -1 ) { VMAddr( asm_Module, curmod )->file_name = s->name; } VMunlock( v ); } } break; case OBJDATA: case OBJCOMMON: { word size = rdint(); if (size < 0) error("Negative sized data/common directive encountered"); v = rdsymb(); s = VMAddr(Symbol,v); trace("%s %d %s",op== OBJDATA ? "DATA" : "COMMON",size,s->name); if( s->type != S_UNBOUND ) { if( s->type != S_COMMSYMB) { if (!inlib) warn("Duplicate data definition of symbol '%s' defined in file '%s'",s->name, s->file_name); } else { if( s->value.w < size ) s->value.w = size; } } else { s->type = op== OBJDATA ? S_DATASYMB : S_COMMSYMB; s->value.w = size; s->module = curmod; s->file_name = infile_duplicate; if(s->referenced) refsymbol_def(v); } (void)newcode(op,0,0,curloc,v); break; } case OBJCODETABLE: { if (!smtopt) error("CODETABLE directive encountered without split module table mode set"); v = rdsymb(); s = VMAddr(Symbol,v); #if 0 /* problems for .MaxCodeP */ movesym(v); /* implicit global directive */ #endif trace("%s %s","CODETABLE",s->name); if ( s->type != S_UNBOUND ) { if (!inlib) warn("Duplicate definition of symbol '%s' defined in file '%s'", s->name, s->file_name); } else { if (s->AOFassumedData) { error( "(AOF) Symbol '%s' has been assumed to be data in file '%s'", s->name, s->file_name ); s->AOFassumedData = FALSE; } s->type = S_FUNCSYMB; s->value.w = 4; s->module = curmod; s->file_name = infile_duplicate; if(s->referenced) refsymbol_def(v); } (void)newcode(op,0,0,curloc,v); break; } } } while( op != EOF ); return; }
static int interpret() { fetch: Cyclecount++; W = M[C++]; if ((W & DBIT) == 0) D = W & ABITS; else D = M[C++]; if ((W & PBIT) != 0) D += P; if ((W & GBIT) != 0) D += G; if ((W & IBIT) != 0) D = M[D]; switch (W >> FSHIFT) { error: default: printf("\nINTCODE ERROR AT C = %d\n", C - 1); return -1; case 0: B = A; A = D; goto fetch; case 1: M[D] = A; goto fetch; case 2: A = A + D; goto fetch; case 3: C = D; goto fetch; case 4: A = !A; case 5: if (!A) C = D; goto fetch; case 6: D += P; M[D] = P; M[D + 1] = C; P = D; C = A; goto fetch; case 7: switch (D) { default: goto error; case 1: A = M[A]; goto fetch; case 2: A = -A; goto fetch; case 3: A = ~A; goto fetch; case 4: C = M[P + 1]; P = M[P]; goto fetch; case 5: A = B * A; goto fetch; case 6: A = B / A; goto fetch; case 7: A = B % A; goto fetch; case 8: A = B + A; goto fetch; case 9: A = B - A; goto fetch; case 10: A = B == A ? ~0 : 0; goto fetch; case 11: A = B != A ? ~0 : 0; goto fetch; case 12: A = B < A ? ~0 : 0; goto fetch; case 13: A = B >= A ? ~0 : 0; goto fetch; case 14: A = B > A ? ~0 : 0; goto fetch; case 15: A = B <= A ? ~0 : 0; goto fetch; case 16: A = B << A; goto fetch; case 17: A = B >> A; goto fetch; case 18: A = B & A; goto fetch; case 19: A = B | A; goto fetch; case 20: A = B ^ A; goto fetch; case 21: A = B ^ ~A; goto fetch; case 22: return 0; case 23: B = M[C]; D = M[C + 1]; while (B != 0) { B--; C += 2; if (A == M[C]) { D = M[C + 1]; break; } } C = D; goto fetch; case 24: selectinput(A); goto fetch; case 25: selectoutput(A); goto fetch; case 26: A = rdch(); goto fetch; case 27: wrch(A); goto fetch; case 28: A = findinput(A); goto fetch; case 29: A = findoutput(A); goto fetch; case 30: return A; case 31: A = M[P]; goto fetch; case 32: P = A; C = B; goto fetch; case 33: endread(); goto fetch; case 34: endwrite(); goto fetch; case 35: D = P + B + 1; M[D] = M[P]; M[D + 1] = M[P + 1]; M[D + 2] = P; M[D + 3] = B; P = D; C = A; goto fetch; case 36: A = getbyte(A, B); goto fetch; case 37: putbyte(A, B, M[P + 4]); goto fetch; case 38: A = input(); goto fetch; case 39: A = output(); goto fetch; } } }
void ibug( void ) { char ch; static int i0; int i1; int depth; int32 *sp; char s[32]; char s0[32]; char s1[32]; BOOL loop_flag = FALSE; static INSTRUCTION *ip0; INSTRUCTION *ip1; static char brk_ins[12]; ip1 = ilist( ins_ptr ); if( ((*go_adr_str == '\0') || (strcmp(go_adr_str, prg_str) == 0)) && ((ip1 > go_adr) && (ins_ptr <= go_adr)) ) { printf( "reached go address\n" ); go_flag = FALSE; } /* if */ if( match( iname[*ins_ptr], brk_ins ) ) { printf( "reached break instruction %s at adr %d\n", iname[*ins_ptr], (int)(ins_ptr - prg_start) ); go_flag = FALSE; } /* if */ if( go_flag ) return; while( !loop_flag ) { ch = rdch(); putchar( '\b' ); switch( ch ) { case '?': printf( "\ng adr\t go til address\n" "$\tshow stack elements\n" "?\thelp\n" "b instruction\tbreak \n" "l [start][,end]\tlist from start..end\n" "space\tstep\n" ); break; case 'b': printf( "\nb " ); fgets( brk_ins, sizeof(brk_ins), stdin ); break; case '$': depth = stack_ptr - stack_Base; printf( "\n$ stack[%d]: ", depth ); sp = stack_ptr - 1; i1 = depth>10 ? 10 : depth; while( i1>0 ) { printf( " -> %ld", *sp ); sp--; i1--; } /* for */ printf( "\n" ); break; case 'l': printf( "\nl " ); fflush( stdout ); fgets( s, sizeof(s), stdin ); switch( sscanf( s, "%d, %d", &i0, &i1 ) ) { default: if( prev_ch != 'l' ) { ip0 = ins_ptr; } /* if */ ip1 = ip0+10; break; case 1: ip0 = prg_start+i0; ip1 = ip0+10; break; case 2: ip0 = prg_start+i0; ip1 = prg_start+i1; } /* switch */ while( ip0<=ip1 ) { ip0 = ilist( ip0 ); printf( "\n "); } /* for */ break; /* case 'l' */ case 'g': printf( "\ng " ); fflush( stdout ); fgets( s, sizeof(s), stdin ); switch( sscanf( s, "%s.%d", s0, s1 ) ) { case 1: go_adr = prg_start + atoi( s0 ); *go_adr_str = '\0'; break; case 2: go_adr = prg_start + atoi( s1 ); strcpy( go_adr_str, s0); break; } /* switch */ go_flag = TRUE; loop_flag = TRUE; break; default: loop_flag = TRUE; } /* switch */ prev_ch = ch; } /* while */ } /* ibug() */