Bits CPU_Core_Full_Run(void) { FullData inst; while (CPU_Cycles-->0) { #if C_DEBUG cycle_count++; #if C_HEAVY_DEBUG if (DEBUG_HeavyIsBreakpoint()) { FillFlags(); return debugCallback; }; #endif #endif LoadIP(); inst.entry=cpu.code.big*0x200; inst.prefix=cpu.code.big; restartopcode: inst.entry=(inst.entry & 0xffffff00) | Fetchb(); inst.code=OpCodeTable[inst.entry]; #include "core_full/load.h" #include "core_full/op.h" #include "core_full/save.h" nextopcode:; SaveIP(); continue; illegalopcode: LOG(LOG_CPU,LOG_NORMAL)("Illegal opcode"); CPU_Exception(0x6,0); } FillFlags(); return CBRET_NONE; }
Bits CPU_Core_Normal_Run(void) { while (CPU_Cycles-- > 0) { LOADIP; core.opcode_index = cpu.code.big*0x200; core.prefixes = cpu.code.big; core.ea_table = &EATable[cpu.code.big*256]; BaseDS = SegBase(ds); BaseSS = SegBase(ss); core.base_val_ds = ds; restart_opcode: // lastOpcode = core.opcode_index+Fetchb(); // switch (lastOpcode) switch (core.opcode_index+Fetchb()) { #include "core_normal/prefix_none.h" #include "core_normal/prefix_0f.h" #include "core_normal/prefix_66.h" #include "core_normal/prefix_66_0f.h" default: illegal_opcode: CPU_Exception(6, 0); continue; } SAVEIP; } FillFlags(); return CBRET_NONE; decode_end: SAVEIP; FillFlags(); return CBRET_NONE; }
Bits CPU_Core_Simple_Run(void) { while (CPU_Cycles-->0) { LOADIP; core.opcode_index=cpu.code.big*0x200; core.prefixes=cpu.code.big; core.ea_table=&EATable[cpu.code.big*256]; BaseDS=SegBase(ds); BaseSS=SegBase(ss); core.base_val_ds=ds; #if C_DEBUG #if C_HEAVY_DEBUG if (DEBUG_HeavyIsBreakpoint()) { FillFlags(); return debugCallback; }; #endif #endif cycle_count++; restart_opcode: switch (core.opcode_index+Fetchb()) { #include "core_normal/prefix_none.h" #include "core_normal/prefix_0f.h" #include "core_normal/prefix_66.h" #include "core_normal/prefix_66_0f.h" default: illegal_opcode: #if C_DEBUG { Bitu len=(GETIP-reg_eip); LOADIP; if (len>16) len=16; char tempcode[16*2+1];char * writecode=tempcode; for (;len>0;len--) { // sprintf(writecode,"%X",mem_readb(core.cseip++)); writecode+=2; } LOG(LOG_CPU,LOG_NORMAL)("Illegal/Unhandled opcode %s",tempcode); } #endif CPU_Exception(6,0); continue; } SAVEIP; } FillFlags(); return CBRET_NONE; decode_end: SAVEIP; FillFlags(); return CBRET_NONE; }
Bits CPU_Core_Prefetch_Run(void) { bool invalidate_pq=false; while (CPU_Cycles-->0) { if (invalidate_pq) { pq_valid=false; invalidate_pq=false; } LOADIP; core.opcode_index=cpu.code.big*0x200; core.prefixes=cpu.code.big; core.ea_table=&EATable[cpu.code.big*256]; BaseDS=SegBase(ds); BaseSS=SegBase(ss); core.base_val_ds=ds; #if C_DEBUG #if C_HEAVY_DEBUG if (DEBUG_HeavyIsBreakpoint()) { FillFlags(); return debugCallback; }; #endif cycle_count++; #endif restart_opcode: Bit8u next_opcode=Fetchb(); invalidate_pq=false; if (core.opcode_index&OPCODE_0F) invalidate_pq=true; else switch (next_opcode) { case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: // jcc case 0x9a: // call case 0xc2: case 0xc3: // retn case 0xc8: // enter case 0xc9: // leave case 0xca: case 0xcb: // retf case 0xcc: // int3 case 0xcd: // int case 0xce: // into case 0xcf: // iret case 0xe0: // loopnz case 0xe1: // loopz case 0xe2: // loop case 0xe3: // jcxz case 0xe8: // call case 0xe9: case 0xea: case 0xeb: // jmp case 0xff: invalidate_pq=true; break; default: break; } switch (core.opcode_index+next_opcode) { #include "core_normal/prefix_none.h" #include "core_normal/prefix_0f.h" #include "core_normal/prefix_66.h" #include "core_normal/prefix_66_0f.h" default: illegal_opcode: #if C_DEBUG { bool ignore=false; Bitu len=(GETIP-reg_eip); LOADIP; if (len>16) len=16; char tempcode[16*2+1];char * writecode=tempcode; if (ignore_opcode_63 && mem_readb(core.cseip) == 0x63) ignore = true; for (;len>0;len--) { sprintf(writecode,"%02X",mem_readb(core.cseip++)); writecode+=2; } if (!ignore) LOG(LOG_CPU,LOG_NORMAL)("Illegal/Unhandled opcode %s",tempcode); } #endif CPU_Exception(6,0); invalidate_pq=true; continue; } SAVEIP; } FillFlags(); return CBRET_NONE; decode_end: SAVEIP; FillFlags(); return CBRET_NONE; }
Bits CPU_Core286_Normal_Run(void) { if (CPU_Cycles <= 0) return CBRET_NONE; while (CPU_Cycles-->0) { LOADIP; core.prefixes=0; core.opcode_index=0; core.ea_table=&EATable[0]; BaseDS=SegBase(ds); BaseSS=SegBase(ss); core.base_val_ds=ds; #if C_DEBUG #if C_HEAVY_DEBUG if (DEBUG_HeavyIsBreakpoint()) { FillFlags(); return (Bits)debugCallback; }; #endif #endif cycle_count++; restart_opcode: switch (core.opcode_index+Fetchb()) { #include "core_normal/prefix_none.h" #include "core_normal/prefix_0f.h" default: illegal_opcode: #if C_DEBUG { bool ignore=false; Bitu len=(GETIP-reg_eip); LOADIP; if (len>16) len=16; char tempcode[16*2+1];char * writecode=tempcode; if (ignore_opcode_63 && mem_readb(core.cseip) == 0x63) ignore = true; for (;len>0;len--) { sprintf(writecode,"%02X",mem_readb(core.cseip++)); writecode+=2; } if (!ignore) LOG(LOG_CPU,LOG_NORMAL)("Illegal/Unhandled opcode %s",tempcode); } #endif CPU_Exception(6,0); continue; gp_fault: CPU_Exception(EXCEPTION_GP,0); continue; } SAVEIP; } FillFlags(); return CBRET_NONE; /* 8086/286 multiple prefix interrupt bug emulation. * If an instruction is interrupted, only the last prefix is restarted. * See also [https://www.pcjs.org/pubs/pc/reference/intel/8086/] and [https://www.youtube.com/watch?v=6FC-tcwMBnU] */ prefix_out: SAVEIP_PREFIX; FillFlags(); return CBRET_NONE; decode_end: SAVEIP; FillFlags(); return CBRET_NONE; }
Bits CPU_Core_Normal_Run(void) { while (CPU_Cycles-->0) { LOADIP; dosbox_check_nonrecursive_pf_cs = SegValue(cs); dosbox_check_nonrecursive_pf_eip = reg_eip; core.opcode_index=cpu.code.big*0x200; core.prefixes=cpu.code.big; core.ea_table=&EATable[cpu.code.big*256]; BaseDS=SegBase(ds); BaseSS=SegBase(ss); core.base_val_ds=ds; #if C_DEBUG #if C_HEAVY_DEBUG if (DEBUG_HeavyIsBreakpoint()) { FillFlags(); return debugCallback; }; #endif #endif cycle_count++; restart_opcode: switch (core.opcode_index+Fetchb()) { #include "core_normal/prefix_none.h" #include "core_normal/prefix_0f.h" #include "core_normal/prefix_66.h" #include "core_normal/prefix_66_0f.h" default: illegal_opcode: #if C_DEBUG { bool ignore=false; Bitu len=(GETIP-reg_eip); LOADIP; if (len>16) len=16; char tempcode[16*2+1];char * writecode=tempcode; if (ignore_opcode_63 && mem_readb(core.cseip) == 0x63) ignore = true; for (;len>0;len--) { sprintf(writecode,"%02X",mem_readb(core.cseip++)); writecode+=2; } if (!ignore) LOG(LOG_CPU,LOG_NORMAL)("Illegal/Unhandled opcode %s",tempcode); } #endif CPU_Exception(6,0); continue; gp_fault: LOG_MSG("Segment limit violation"); CPU_Exception(EXCEPTION_GP,0); continue; } SAVEIP; } FillFlags(); return CBRET_NONE; decode_end: SAVEIP; FillFlags(); return CBRET_NONE; }