Annotation of uae/newcpu.c, revision 1.1.1.2

1.1       root        1:  /* 
                      2:   * UAE - The Un*x Amiga Emulator
                      3:   * 
                      4:   * MC68000 emulation
                      5:   *
                      6:   * (c) 1995 Bernd Schmidt
                      7:   */
1.1.1.2 ! root        8: 
        !             9: #include "sysconfig.h"
        !            10: #include "sysdeps.h"
1.1       root       11: 
                     12: #include "config.h"
                     13: #include "options.h"
                     14: #include "events.h"
1.1.1.2 ! root       15: #include "gui.h"
1.1       root       16: #include "memory.h"
                     17: #include "custom.h"
                     18: #include "newcpu.h"
                     19: #include "ersatz.h"
1.1.1.2 ! root       20: #include "readcpu.h"
        !            21: 
        !            22: int areg_byteinc[] = { 1,1,1,1,1,1,1,2 };
        !            23: int imm8_table[] = { 8,1,2,3,4,5,6,7 };
1.1       root       24: 
1.1.1.2 ! root       25: cpuop_func *cpufunctbl[65536];
1.1       root       26: 
                     27: #ifdef COUNT_INSTRS
                     28: static unsigned long int instrcount[65536];
                     29: static UWORD opcodenums[65536];
                     30: 
                     31: int compfn(const void *el1, const void *el2)
                     32: {
                     33:     return instrcount[*(const UWORD *)el1] < instrcount[*(const UWORD *)el2];
                     34: }
                     35: 
                     36: void dump_counts(void)
                     37: {
                     38:     FILE *f = fopen("insncount", "w");
                     39:     unsigned long int total = 0;
                     40:     int i;
                     41:     
                     42:     for(i=0; i < 65536; i++) {
                     43:        opcodenums[i] = i;
                     44:        total += instrcount[i];
                     45:     }
                     46:     qsort(opcodenums, 65536, sizeof(UWORD), compfn);
                     47:     
                     48:     fprintf(f, "Total: %ld\n", total);
                     49:     for(i=0; i < 65536; i++) {
                     50:        unsigned long int cnt = instrcount[opcodenums[i]];
                     51:        if (!cnt)
                     52:            break;
                     53:        fprintf(f, "%04x: %ld\n", opcodenums[i], cnt);
                     54:     }
                     55:     fclose(f);
                     56: }
                     57: #endif
                     58: 
1.1.1.2 ! root       59: int broken_in;
1.1       root       60: 
1.1.1.2 ! root       61: #ifdef INTEL_FLAG_OPT
        !            62: union flagu intel_flag_lookup[256];
1.1       root       63: #endif
                     64: 
1.1.1.2 ! root       65: void init_m68k (void)
1.1       root       66: {
1.1.1.2 ! root       67:     long int opcode;
1.1       root       68:     int i;
1.1.1.2 ! root       69:     
        !            70: #ifdef COUNT_INSTRS
        !            71:     memset(instrcount, 0, sizeof instrcount);
1.1       root       72: #endif
1.1.1.2 ! root       73: #ifdef INTEL_FLAG_OPT
        !            74:     for (i = 0; i < 256; i++) {
        !            75:        intel_flag_lookup[i].flags.c = !!(i & 1);
        !            76:        intel_flag_lookup[i].flags.z = !!(i & 64);
        !            77:        intel_flag_lookup[i].flags.n = !!(i & 128);
        !            78:        intel_flag_lookup[i].flags.v = 0;
1.1       root       79:     }
1.1.1.2 ! root       80: #endif
        !            81:     printf("Building CPU table...\n");
        !            82:     read_table68k ();
        !            83:     do_merges ();
        !            84:     for (opcode = 0; opcode < 65536; opcode++)
        !            85:        cpufunctbl[opcode] = op_illg;
        !            86:     for (i = 0; smallcputbl[i].handler != NULL; i++) {
        !            87:        if (!smallcputbl[i].specific)
        !            88:            cpufunctbl[smallcputbl[i].opcode] = smallcputbl[i].handler;
1.1       root       89:     }
1.1.1.2 ! root       90:     for (opcode = 0; opcode < 65536; opcode++) {
        !            91:        cpuop_func *f;
        !            92:        
        !            93:        if (table68k[opcode].mnemo == i_ILLG)
        !            94:            continue;
        !            95:        
        !            96:        if (table68k[opcode].handler != -1) {
        !            97:            f = cpufunctbl[table68k[opcode].handler];
        !            98:            if (f == op_illg)
        !            99:                abort();
        !           100:            cpufunctbl[opcode] = f;
        !           101:        }
        !           102:     }  
        !           103:     for (i = 0; smallcputbl[i].handler != NULL; i++) {
        !           104:        if (smallcputbl[i].specific)
        !           105:            cpufunctbl[smallcputbl[i].opcode] = smallcputbl[i].handler;
1.1       root      106:     }
                    107: }
                    108: 
1.1.1.2 ! root      109: struct regstruct regs;
        !           110: union flagu regflags;
        !           111: static void ShowEA(int reg, amodes mode, wordsizes size)
1.1       root      112: {
                    113:     UWORD dp;
                    114:     BYTE disp8;
                    115:     WORD disp16;
                    116:     int r;
                    117:     ULONG dispreg;
1.1.1.2 ! root      118:     CPTR addr;
1.1       root      119:     
1.1.1.2 ! root      120:     switch(mode){
1.1       root      121:      case Dreg:
1.1.1.2 ! root      122:        printf("D%d", reg);
1.1       root      123:        break;
                    124:      case Areg:
1.1.1.2 ! root      125:        printf("A%d", reg);
1.1       root      126:        break;
                    127:      case Aind:
1.1.1.2 ! root      128:        printf("(A%d)", reg);
1.1       root      129:        break;
                    130:      case Aipi:
1.1.1.2 ! root      131:        printf("(A%d)+", reg);
1.1       root      132:        break;
                    133:      case Apdi:
1.1.1.2 ! root      134:        printf("-(A%d)", reg);
1.1       root      135:        break;
                    136:      case Ad16:
                    137:        disp16 = nextiword();
1.1.1.2 ! root      138:        addr = regs.a[reg] + (WORD)disp16;
        !           139:        printf("(A%d,$%04lx) == $%08lx", reg, disp16, (long unsigned int)addr);
1.1       root      140:        break;
                    141:      case Ad8r:
                    142:        dp = nextiword();
                    143:        disp8 = dp & 0xFF;
                    144:        r = (dp & 0x7000) >> 12;
1.1.1.2 ! root      145:        dispreg = dp & 0x8000 ? regs.a[r] : regs.d[r];  
        !           146:        if (!(dp & 0x800)) dispreg = (LONG)(WORD)(dispreg);
1.1       root      147:        
1.1.1.2 ! root      148:        addr = regs.a[reg] + disp8 + dispreg;
        !           149:        printf("(A%d, %c%d.%c, $%02x) == $%08lx", reg, 
1.1       root      150:               dp & 0x8000 ? 'A' : 'D', (int)r, dp & 0x800 ? 'L' : 'W', disp8,
1.1.1.2 ! root      151:               (long unsigned int)addr);
1.1       root      152:        break;
                    153:      case PC16:
1.1.1.2 ! root      154:        addr = m68k_getpc();
1.1       root      155:        disp16 = nextiword();
1.1.1.2 ! root      156:        addr += (WORD)disp16;
        !           157:        printf("(PC,$%08lx) == $%08lx", disp16, (long unsigned int)addr);
1.1       root      158:        break;
                    159:      case PC8r:
1.1.1.2 ! root      160:        addr = m68k_getpc();
1.1       root      161:        dp = nextiword();
                    162:        disp8 = dp & 0xFF;
                    163:        r = (dp & 0x7000) >> 12;
                    164:        dispreg = dp & 0x8000 ? regs.a[r] : regs.d[r];
                    165:        
1.1.1.2 ! root      166:        if (!(dp & 0x800)) dispreg = (LONG)(WORD)(dispreg);
        !           167:        addr += disp8 + dispreg;
1.1       root      168:        printf("(PC, %c%d.%c, $%02x) == $%08lx", dp & 0x8000 ? 'A' : 'D', 
1.1.1.2 ! root      169:               (int)r, dp & 0x800 ? 'L' : 'W', disp8, (long unsigned int)addr);
1.1       root      170:        break;
                    171:      case absw:
1.1.1.2 ! root      172:        printf("$%08lx", (LONG)(WORD)nextiword());
1.1       root      173:        break;
                    174:      case absl:
1.1.1.2 ! root      175:        printf("$%08lx", nextilong());
1.1       root      176:        break;
                    177:      case imm:
1.1.1.2 ! root      178:        switch(size){
        !           179:         case sz_byte:
        !           180:            printf("#$%02x", nextiword() & 0xff); break;
        !           181:         case sz_word:
        !           182:            printf("#$%04x", nextiword()); break;
        !           183:         case sz_long:
        !           184:            printf("#$%08lx", nextilong()); break;
        !           185:         default:
        !           186:            abort();
1.1       root      187:        }
                    188:        break;
1.1.1.2 ! root      189:      case imm0:
        !           190:        printf("#$%02lx", nextiword() & 0xff);
        !           191:        break;
        !           192:      case imm1:
        !           193:        printf("#$%04lx", nextiword());
        !           194:        break;
        !           195:      case imm2:
        !           196:        printf("#$%08lx", nextilong());
        !           197:        break;
        !           198:      case immi:
        !           199:        printf("#$%04lx", reg);
1.1       root      200:        break;
                    201:      default:
                    202:        abort();
                    203:     }
                    204: }
                    205: 
1.1.1.2 ! root      206: #if CPU_LEVEL > 1
        !           207: ULONG get_disp_ea (ULONG base, UWORD dp)
1.1       root      208: {
1.1.1.2 ! root      209:     int reg = (dp >> 12) & 7;
        !           210:     LONG regd;
        !           211:     if (dp & 0x8000)
        !           212:        regd = regs.a[reg];
        !           213:     else
        !           214:        regd = regs.d[reg];
        !           215:     if (!(dp & 0x800))
        !           216:        regd = (LONG)(WORD)regd;
        !           217:     if (dp & 0x100) {
        !           218:        LONG extraind = 0;
        !           219:        printf("020\n");
        !           220:        regd <<= (dp >> 9) & 3;
        !           221:        if (dp & 0x80)
        !           222:            base = 0;
        !           223:        if (dp & 0x40)
        !           224:            regd = 0;
        !           225:        if ((dp & 0x30) == 0x20)
        !           226:            base += (LONG)(WORD)nextiword();
        !           227:        if ((dp & 0x30) == 0x30)
        !           228:            base += nextilong();
        !           229:        
        !           230:        if ((dp & 0x3) == 0x2)
        !           231:            extraind = (LONG)(WORD)nextiword();
        !           232:        if ((dp & 0x3) == 0x3)
        !           233:            extraind = nextilong();
        !           234:        
        !           235:        if (!(dp & 4))
        !           236:            base += regd;
        !           237:        if (dp & 3)
        !           238:            base = get_long (base);
        !           239:        if (dp & 4)
        !           240:            base += regd;
        !           241:        
        !           242:        return base + extraind;
        !           243:        /* Yikes, that's complicated */
        !           244:     } else {
        !           245:        return base + (BYTE)(dp) + regd;
1.1       root      246:     }
                    247: }
1.1.1.2 ! root      248: #endif
1.1       root      249: 
                    250: void MakeSR(void)
                    251: {
1.1.1.2 ! root      252: #if 0
        !           253:     assert((NFLG & 1) == NFLG);
1.1       root      254:     assert((regs.s & 1) == regs.s);
                    255:     assert((regs.x & 1) == regs.x);
1.1.1.2 ! root      256:     assert((CFLG & 1) == CFLG);
        !           257:     assert((VFLG & 1) == VFLG);
        !           258:     assert((ZFLG & 1) == ZFLG);
        !           259: #endif
1.1       root      260:     regs.sr = ((regs.t << 15) | (regs.s << 13) | (regs.intmask << 8)
1.1.1.2 ! root      261:               | (regs.x << 4) | (NFLG << 3) | (ZFLG << 2) | (VFLG << 1) 
        !           262:               |  CFLG);
1.1       root      263: }
                    264: 
                    265: void MakeFromSR(void)
                    266: {
                    267:     int olds = regs.s;
                    268: 
                    269:     regs.t = (regs.sr >> 15) & 1;
                    270:     regs.s = (regs.sr >> 13) & 1;
                    271:     regs.intmask = (regs.sr >> 8) & 7;
                    272:     regs.x = (regs.sr >> 4) & 1;
1.1.1.2 ! root      273:     NFLG = (regs.sr >> 3) & 1;
        !           274:     ZFLG = (regs.sr >> 2) & 1;
        !           275:     VFLG = (regs.sr >> 1) & 1;
        !           276:     CFLG = regs.sr & 1;
1.1       root      277:     if (olds != regs.s) {
1.1.1.2 ! root      278:        CPTR temp = regs.usp;
        !           279:        regs.usp = regs.a[7];
        !           280:        regs.a[7] = temp;
1.1       root      281:     }
                    282:     specialflags |= SPCFLAG_INT;
                    283:     if (regs.t)
                    284:        specialflags |= SPCFLAG_TRACE;
                    285:     else
                    286:        specialflags &= ~(SPCFLAG_TRACE | SPCFLAG_DOTRACE);
                    287: }
                    288: 
                    289: void Exception(int nr)
                    290: {
                    291:     MakeSR();
1.1.1.2 ! root      292:     if (!regs.s) {
        !           293:        CPTR temp = regs.usp;
        !           294:        regs.usp = regs.a[7];
        !           295:        regs.a[7] = temp;
        !           296:        regs.s = 1;
        !           297:     }
        !           298:     if (CPU_LEVEL > 0) {
        !           299:        regs.a[7] -= 2;
        !           300:        put_word (regs.a[7], nr * 4);
        !           301:     }
        !           302:     regs.a[7] -= 4;
        !           303:     put_long (regs.a[7], m68k_getpc ());
        !           304:     regs.a[7] -= 2;
        !           305:     put_word (regs.a[7], regs.sr);
        !           306:     m68k_setpc(get_long(regs.vbr + 4*nr));
1.1       root      307:     regs.t = 0;
                    308:     specialflags &= ~(SPCFLAG_TRACE | SPCFLAG_DOTRACE);
                    309: }
                    310: 
                    311: static void Interrupt(int nr)
                    312: {
                    313:     assert(nr < 8 && nr >= 0);
                    314:     Exception(nr+24);
                    315:     
                    316:     regs.intmask = nr;
                    317:     specialflags |= SPCFLAG_INT;
                    318: }
                    319: 
1.1.1.2 ! root      320: static int caar, cacr;
1.1       root      321: 
1.1.1.2 ! root      322: void m68k_move2c (int regno, ULONG *regp)
1.1       root      323: {
1.1.1.2 ! root      324:     if (CPU_LEVEL == 1 && (regno & 0x7FF) > 1)
        !           325:        op_illg (0x4E7B);
        !           326:     else
        !           327:        switch (regno) {
        !           328:         case 0: regs.sfc = *regp; break;
        !           329:         case 1: regs.dfc = *regp; break;
        !           330:         case 2: cacr = *regp & 0xFF; break;
        !           331:         case 0x800: regs.usp = *regp; break;
        !           332:         case 0x801: regs.vbr = *regp; break;
        !           333:         case 0x802: caar = *regp & 0xFF; break;
        !           334:         default:
        !           335:            op_illg (0x4E7B);
        !           336:            break;
1.1       root      337:        }
                    338: }
                    339: 
1.1.1.2 ! root      340: void m68k_movec2 (int regno, ULONG *regp)
1.1       root      341: {
1.1.1.2 ! root      342:     if (CPU_LEVEL == 1 && (regno & 0x7FF) > 1)
        !           343:        op_illg (0x4E7A);
        !           344:     else
        !           345:        switch (regno) {
        !           346:         case 0: *regp = regs.sfc; break;
        !           347:         case 1: *regp = regs.dfc; break;
        !           348:         case 2: *regp = cacr; break;
        !           349:         case 0x800: *regp = regs.usp; break;
        !           350:         case 0x801: *regp = regs.vbr; break;
        !           351:         case 0x802: *regp = caar; break;
        !           352:         default:
        !           353:            op_illg (0x4E7A);
        !           354:            break;
1.1       root      355:        }
                    356: }
                    357: 
1.1.1.2 ! root      358: extern void m68k_divl (UWORD opcode, ULONG src, UWORD extra)
1.1       root      359: {
1.1.1.2 ! root      360:     if (src == 0)
        !           361:        return;
        !           362: #ifdef INT_64BIT
        !           363:     if (extra & 0x800) {
        !           364:        /* signed variant */
        !           365:        INT_64BIT a = regs.d[(extra >> 12) & 7];
        !           366:        INT_64BIT quot, rem;
        !           367:        
        !           368:        if (extra & 0x400)
        !           369:            a |= (INT_64BIT)regs.d[extra & 7] << 32;
        !           370:        rem = a % src;
        !           371:        quot = a / src;
        !           372:        if ((extra & 0x400) && (extra & 7) != ((extra >> 12) & 7))
        !           373:            regs.d[extra & 7] = rem;
        !           374:        regs.d[(extra >> 12) & 7] = quot;
1.1       root      375:     } else {
1.1.1.2 ! root      376:        /* unsigned */
        !           377:        unsigned INT_64BIT a = regs.d[(extra >> 12) & 7];
        !           378:        unsigned INT_64BIT quot, rem;
        !           379:        
        !           380:        if (extra & 0x400)
        !           381:            a |= (INT_64BIT)regs.d[extra & 7] << 32;
        !           382:        rem = a % src;
        !           383:        quot = a / src;
        !           384:        if ((extra & 0x400) && (extra & 7) != ((extra >> 12) & 7))
        !           385:            regs.d[extra & 7] = rem;
        !           386:        regs.d[(extra >> 12) & 7] = quot;
1.1       root      387:     }
1.1.1.2 ! root      388: #endif
1.1       root      389: }
                    390: 
1.1.1.2 ! root      391: extern void m68k_mull (UWORD opcode, ULONG src, UWORD extra)
1.1       root      392: {
1.1.1.2 ! root      393: #ifdef INT_64BIT
        !           394:     if (extra & 0x800) {
        !           395:        /* signed variant */
        !           396:        INT_64BIT a = (LONG)regs.d[(extra >> 12) & 7];
        !           397: 
        !           398:        a *= (LONG)src;
        !           399:        if ((extra & 0x400) && (extra & 7) != ((extra >> 12) & 7))
        !           400:            regs.d[extra & 7] = a >> 32;
        !           401:        regs.d[(extra >> 12) & 7] = (ULONG)a;
1.1       root      402:     } else {
1.1.1.2 ! root      403:        /* unsigned */
        !           404:        unsigned INT_64BIT a = (ULONG)regs.d[(extra >> 12) & 7];
        !           405:        unsigned INT_64BIT quot, rem;
        !           406:        
        !           407:        a *= src;
        !           408:        if ((extra & 0x400) && (extra & 7) != ((extra >> 12) & 7))
        !           409:            regs.d[extra & 7] = a >> 32;
        !           410:        regs.d[(extra >> 12) & 7] = (ULONG)a;
1.1       root      411:     }
1.1.1.2 ! root      412: #endif
1.1       root      413: }
                    414: 
                    415: static char* ccnames[] =
                    416: { "T ","F ","HI","LS","CC","CS","NE","EQ",
                    417:   "VC","VS","PL","MI","GE","LT","GT","LE" };
                    418: 
                    419: void MC68000_reset(void)
                    420: {
                    421:     regs.a[7] = get_long(0x00f80000);
                    422:     m68k_setpc(get_long(0x00f80004));
                    423:     regs.s = 1;
                    424:     regs.stopped = 0;
                    425:     regs.t = 0;
                    426:     specialflags = 0;
                    427:     regs.intmask = 7;
1.1.1.2 ! root      428:     regs.vbr = regs.sfc = regs.dfc = 0;
        !           429:     customreset();
1.1       root      430: }
                    431: 
1.1.1.2 ! root      432: void op_illg(ULONG opcode)
1.1       root      433: {
1.1.1.2 ! root      434:     if (opcode == 0x4E7B && get_long(0x10) == 0 
        !           435:        && (m68k_getpc() & 0xF80000) == 0xF80000) 
        !           436:     {
        !           437:        fprintf(stderr, "Your Kickstart requires a 68020 CPU. Giving up.\n");
        !           438:        broken_in = 1; 
        !           439:        specialflags |= SPCFLAG_BRK;
        !           440:        quit_program = 1;
        !           441:     }
1.1       root      442:     if (opcode == 0xF00D && ((m68k_getpc() & 0xF80000) == 0xF80000)) {
                    443:        /* This is from the dummy Kickstart replacement */
                    444:        ersatz_perform (nextiword ());
                    445:        return;
                    446:     }
                    447:     regs.pc_p--;
1.1.1.2 ! root      448:     if ((opcode & 0xF000) == 0xF000) {
        !           449:        if ((opcode & 0xE00) == 0x200)
        !           450:            Exception(0xB);
        !           451:        else 
        !           452:            switch (opcode & 0x1FF) {
        !           453:             case 0x17:
        !           454:                regs.pc_p+=2;
        !           455:                break;
        !           456:             default:
        !           457:                regs.pc_p++;
        !           458:            }
1.1       root      459:        return;
                    460:     }
                    461:     if ((opcode & 0xF000) == 0xA000) {
                    462:        Exception(0xA);
                    463:        return;
                    464:     }
                    465:     fprintf(stderr, "Illegal instruction: %04x\n", opcode);
                    466:     Exception(4);
                    467: }
                    468: 
                    469: static int n_insns=0, n_spcinsns=0;
                    470: 
                    471: static __inline__ void do_hardware(void)
                    472: {
                    473:     if (specialflags & SPCFLAG_BLIT) {
                    474:        do_blitter();
                    475: #ifdef NO_FAST_BLITTER
                    476:        do_blitter();
                    477:        do_blitter();
                    478:        do_blitter();
                    479: #endif
                    480:     }
                    481:     if (specialflags & SPCFLAG_DISK) {
                    482:        do_disk(); /* This is not critical. Four calls make disk */
                    483:        do_disk(); /* loading quite fast. */
                    484:        do_disk();
                    485:        do_disk();
                    486:     }
                    487: }
                    488: 
                    489: void MC68000_run(void)
                    490: {
                    491:     for(;;) {
                    492:        UWORD opcode;
                    493:        /* assert (!regs.stopped && !(specialflags & SPCFLAG_STOP)); */
                    494:        opcode = nextiword();
                    495: #ifdef COUNT_INSTRS
                    496:        instrcount[opcode]++;
                    497: #endif
                    498:        (*cpufunctbl[opcode])(opcode);
                    499: #ifndef NO_EXCEPTION_3
                    500:        if (buserr) {
                    501:            Exception(3);
1.1.1.2 ! root      502:            buserr = 0;
1.1       root      503:        }
                    504: #endif
                    505:        /*n_insns++;*/
                    506:        do_cycles();    
                    507:        if (specialflags) {
                    508:            /*n_spcinsns++;*/
1.1.1.2 ! root      509:            while (specialflags & SPCFLAG_BLTNASTY) {
        !           510:                do_cycles();
        !           511:                do_hardware();
        !           512:            }
        !           513:            if (specialflags & SPCFLAG_DOTRACE) {
        !           514:                Exception(9);
        !           515:            }
1.1       root      516:            while (specialflags & SPCFLAG_STOP) {
                    517:                do_cycles();
                    518:                do_hardware();
                    519:                if (specialflags & (SPCFLAG_INT | SPCFLAG_DOINT)){
                    520:                    int intr = intlev();
                    521:                    specialflags &= ~(SPCFLAG_INT | SPCFLAG_DOINT);
                    522:                    specialflags &= ~(SPCFLAG_INT | SPCFLAG_DOINT);
                    523:                    if (intr != -1 && intr > regs.intmask) {
                    524:                        Interrupt(intr);
                    525:                        regs.stopped = 0;
                    526:                        specialflags &= ~SPCFLAG_STOP;
                    527:                    }       
                    528:                }               
                    529:            }
                    530:            if (specialflags & SPCFLAG_TRACE) {
                    531:                specialflags &= ~SPCFLAG_TRACE;
                    532:                specialflags |= SPCFLAG_DOTRACE;
                    533:            }
                    534: #ifdef WANT_SLOW_MULTIPLY
                    535:            /* Kludge for Hardwired demo. The guys who wrote it should be
                    536:             * mutilated. */
                    537:            if (specialflags & SPCFLAG_EXTRA_CYCLES) {
                    538:                do_cycles ();
                    539:                do_cycles ();
                    540:                do_cycles ();
                    541:                do_cycles ();
                    542:                specialflags &= ~SPCFLAG_EXTRA_CYCLES;
                    543:            }
                    544: #endif
                    545:            do_hardware();
                    546:            
                    547:            if (specialflags & SPCFLAG_DOINT) {
                    548:                int intr = intlev();
                    549:                specialflags &= ~(SPCFLAG_INT | SPCFLAG_DOINT);
                    550:                if (intr != -1 && intr > regs.intmask) {
                    551:                    Interrupt(intr);
                    552:                    regs.stopped = 0;
                    553:                }           
                    554:            }
                    555:            if (specialflags & SPCFLAG_INT) {
                    556:                specialflags &= ~SPCFLAG_INT;
                    557:                specialflags |= SPCFLAG_DOINT;
                    558:            }
                    559:            if (specialflags & SPCFLAG_BRK) {           
                    560:                specialflags &= ~SPCFLAG_BRK;
                    561:                return;         
                    562:            }
                    563:        }
                    564:     }
                    565: }
                    566: 
                    567: void MC68000_step(void)
                    568: {
                    569:     specialflags |= SPCFLAG_BRK;
                    570:     MC68000_run();
                    571: }
                    572: 
                    573: void MC68000_skip(CPTR nextpc)
                    574: {
1.1.1.2 ! root      575:     broken_in = 0;
1.1       root      576:     specialflags |= SPCFLAG_BRK;
                    577:     do {
                    578:        MC68000_step();
                    579:     } while (nextpc != m68k_getpc() && !broken_in);
                    580: }
                    581: 
                    582: void MC68000_disasm(CPTR addr, CPTR *nextpc, int cnt)
                    583: {
                    584:     CPTR pc = m68k_getpc();
                    585:     m68k_setpc(addr);
                    586:     for (;cnt--;){
                    587:        char instrname[20],*ccpt;
                    588:        int opwords;
                    589:        UWORD opcode;
                    590:        UWORD special = 0;
1.1.1.2 ! root      591:        struct mnemolookup *lookup;
        !           592:        struct instr *dp;
1.1       root      593:        printf("%08lx: ", m68k_getpc());
                    594:        for(opwords = 0; opwords < 5; opwords++){
                    595:            printf("%04x ", get_word(m68k_getpc() + opwords*2));
                    596:        }
                    597:        
                    598:        opcode = nextiword();
                    599:        if (cpufunctbl[opcode] == op_illg) {
                    600:            opcode = 0x4AFC;
                    601:        }
1.1.1.2 ! root      602:        dp = table68k + opcode;
        !           603:        for (lookup = lookuptab;lookup->mnemo != dp->mnemo; lookup++)
1.1       root      604:            ;
                    605:        
1.1.1.2 ! root      606:        strcpy(instrname,lookup->name);
1.1       root      607:        ccpt = strstr(instrname,"cc");
                    608:        if (ccpt != 0) {
1.1.1.2 ! root      609:            strncpy(ccpt,ccnames[dp->cc],2);
1.1       root      610:        }
                    611:        printf("%s", instrname);
1.1.1.2 ! root      612:        switch(dp->size){
        !           613:         case sz_byte: printf(".B "); break;
        !           614:         case sz_word: printf(".W "); break;
        !           615:         case sz_long: printf(".L "); break;
        !           616:         default: break;
1.1       root      617:        }
                    618: 
1.1.1.2 ! root      619:        if (dp->suse) {
        !           620:            ShowEA(dp->sreg, dp->smode, dp->size);
        !           621:        }
        !           622:        if (dp->suse && dp->duse)
        !           623:            printf(",");
        !           624:        if (dp->duse) {
        !           625:            ShowEA(dp->dreg, dp->dmode, dp->size);
1.1       root      626:        }
                    627:        if (ccpt != 0) {
1.1.1.2 ! root      628:            if (cctrue(dp->cc))
1.1       root      629:                printf(" (TRUE)");
                    630:            else 
                    631:                printf(" (FALSE)");
                    632:        }
                    633:        printf("\n");
                    634:     }
                    635:     *nextpc = m68k_getpc();
                    636:     m68k_setpc(pc);
                    637: }
                    638: 
                    639: void MC68000_dumpstate(CPTR *nextpc)
                    640: {
                    641:     int i;
                    642:     for(i = 0; i < 8; i++){
                    643:        printf("D%d: %08lx ", i, regs.d[i]);
                    644:        if ((i & 3) == 3) printf("\n");
                    645:     }
                    646:     for(i=0;i<8;i++){
                    647:        printf("A%d: %08lx ", i, regs.a[i]);
                    648:        if ((i & 3) == 3) printf("\n");
                    649:     }
                    650:     printf ("T=%d S=%d X=%d N=%d Z=%d V=%d C=%d IMASK=%d\n", regs.t, regs.s, 
1.1.1.2 ! root      651:            regs.x, NFLG, ZFLG, VFLG, CFLG, regs.intmask);
1.1       root      652:     MC68000_disasm(m68k_getpc(), nextpc, 1);
                    653:     printf("next PC: %08lx\n", *nextpc);
                    654: }
                    655: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.