# HG changeset patch # User Mike Pavone # Date 1374299040 25200 # Node ID 1e828ed04a7c9b77bdf253c3ac0161b782afb7ff # Parent 80a9527c812c13d534fc826c2a4f99f1542b6ade Implement 68K stop instruction diff -r 80a9527c812c -r 1e828ed04a7c blastem.c --- a/blastem.c Thu Jul 18 09:59:39 2013 -0700 +++ b/blastem.c Fri Jul 19 22:44:00 2013 -0700 @@ -258,6 +258,12 @@ context->int_ack = 0; } adjust_int_cycle(context, v_context); + if (context->current_cycle <= context->sync_cycle) { + context->sync_cycle = context->current_cycle + 4; + if (context->sync_cycle < context->int_cycle) { + context->target_cycle = context->sync_cycle; + } + } if (break_on_sync && address) { break_on_sync = 0; debugger(context, address); diff -r 80a9527c812c -r 1e828ed04a7c m68k_to_x86.c --- a/m68k_to_x86.c Thu Jul 18 09:59:39 2013 -0700 +++ b/m68k_to_x86.c Fri Jul 19 22:44:00 2013 -0700 @@ -3781,8 +3781,30 @@ } dst = m68k_save_result(inst, dst, opts); break; - /*case M68K_STOP: - break;*/ + case M68K_STOP: { + //TODO: Trap if not in system mode + //manual says 4 cycles, but it has to be at least 8 since it's a 2-word instruction + //possibly even 12 since that's how long MOVE to SR takes + dst = cycles(dst, BUS*2); + dst = mov_ir(dst, src_op.disp & 0x1, FLAG_C, SZ_B); + dst = mov_ir(dst, (src_op.disp >> 1) & 0x1, FLAG_V, SZ_B); + dst = mov_ir(dst, (src_op.disp >> 2) & 0x1, FLAG_Z, SZ_B); + dst = mov_ir(dst, (src_op.disp >> 3) & 0x1, FLAG_N, SZ_B); + dst = mov_irind(dst, (src_op.disp >> 4) & 0x1, CONTEXT, SZ_B); + dst = mov_irdisp8(dst, (src_op.disp >> 8), CONTEXT, offsetof(m68k_context, status), SZ_B); + if (!((inst->src.params.immed >> 8) & (1 << BIT_SUPERVISOR))) { + //leave supervisor mode + dst = mov_rr(dst, opts->aregs[7], SCRATCH1, SZ_D); + dst = mov_rdisp8r(dst, CONTEXT, offsetof(m68k_context, aregs) + sizeof(uint32_t) * 8, opts->aregs[7], SZ_D); + dst = mov_rrdisp8(dst, SCRATCH1, CONTEXT, offsetof(m68k_context, aregs) + sizeof(uint32_t) * 8, SZ_D); + } + uint8_t * loop_top = dst; + dst = call(dst, (uint8_t *)do_sync); + dst = mov_rr(dst, LIMIT, CYCLES, SZ_D); + dst = cmp_rdisp8r(dst, CONTEXT, offsetof(m68k_context, int_cycle), CYCLES, SZ_D); + dst = jcc(dst, CC_C, loop_top); + break; + } case M68K_SUB: size = inst->dst.addr_mode == MODE_AREG ? OPSIZE_LONG : inst->extra.size; dst = cycles(dst, BUS);