X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=target-m68k%2Fop_helper.c;h=bbbfd7f130c14d1e093053cf92192fd29c6a285d;hb=30c367ed446b6ea53245589a5cf373578ac075d7;hp=c198e855404daa210e915e83cca1a8879b433760;hpb=1d6198c3b01619151f3227c6461b3d53eeb711e5;p=qemu.git diff --git a/target-m68k/op_helper.c b/target-m68k/op_helper.c index c198e8554..bbbfd7f13 100644 --- a/target-m68k/op_helper.c +++ b/target-m68k/op_helper.c @@ -14,85 +14,80 @@ * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * License along with this library; if not, see . */ -#include "exec.h" -#include "helpers.h" +#include "cpu.h" +#include "helper.h" #if defined(CONFIG_USER_ONLY) -void do_interrupt(int is_hw) +void m68k_cpu_do_interrupt(CPUState *cs) { + M68kCPU *cpu = M68K_CPU(cs); + CPUM68KState *env = &cpu->env; + env->exception_index = -1; } +void do_interrupt_m68k_hardirq(CPUM68KState *env) +{ +} + #else extern int semihosting_enabled; +#include "exec/softmmu_exec.h" + #define MMUSUFFIX _mmu #define SHIFT 0 -#include "softmmu_template.h" +#include "exec/softmmu_template.h" #define SHIFT 1 -#include "softmmu_template.h" +#include "exec/softmmu_template.h" #define SHIFT 2 -#include "softmmu_template.h" +#include "exec/softmmu_template.h" #define SHIFT 3 -#include "softmmu_template.h" +#include "exec/softmmu_template.h" /* Try to fill the TLB and return an exception if error. If retaddr is NULL, it means that the function was called in C code (i.e. not from generated code or from helper.c) */ -/* XXX: fix it to restore all registers */ -void tlb_fill (target_ulong addr, int is_write, int mmu_idx, void *retaddr) +void tlb_fill(CPUM68KState *env, target_ulong addr, int is_write, int mmu_idx, + uintptr_t retaddr) { - TranslationBlock *tb; - CPUState *saved_env; - unsigned long pc; int ret; - /* XXX: hack to restore env in all cases, even if not called from - generated code */ - saved_env = env; - env = cpu_single_env; - ret = cpu_m68k_handle_mmu_fault(env, addr, is_write, mmu_idx, 1); + ret = cpu_m68k_handle_mmu_fault(env, addr, is_write, mmu_idx); if (unlikely(ret)) { if (retaddr) { /* now we have a real cpu fault */ - pc = (unsigned long)retaddr; - tb = tb_find_pc(pc); - if (tb) { - /* the PC is inside the translated code. It means that we have - a virtual CPU fault */ - cpu_restore_state(tb, env, pc, NULL); - } + cpu_restore_state(env, retaddr); } - cpu_loop_exit(); + cpu_loop_exit(env); } - env = saved_env; } -static void do_rte(void) +static void do_rte(CPUM68KState *env) { uint32_t sp; uint32_t fmt; sp = env->aregs[7]; - fmt = ldl_kernel(sp); - env->pc = ldl_kernel(sp + 4); + fmt = cpu_ldl_kernel(env, sp); + env->pc = cpu_ldl_kernel(env, sp + 4); sp |= (fmt >> 28) & 3; env->sr = fmt & 0xffff; m68k_switch_sp(env); env->aregs[7] = sp + 8; } -void do_interrupt(int is_hw) +static void do_interrupt_all(CPUM68KState *env, int is_hw) { + CPUState *cs; uint32_t sp; uint32_t fmt; uint32_t retaddr; @@ -105,21 +100,22 @@ void do_interrupt(int is_hw) switch (env->exception_index) { case EXCP_RTE: /* Return from an exception. */ - do_rte(); + do_rte(env); return; case EXCP_HALT_INSN: if (semihosting_enabled && (env->sr & SR_S) != 0 && (env->pc & 3) == 0 - && lduw_code(env->pc - 4) == 0x4e71 - && ldl_code(env->pc) == 0x4e7bf000) { + && cpu_lduw_code(env, env->pc - 4) == 0x4e71 + && cpu_ldl_code(env, env->pc) == 0x4e7bf000) { env->pc += 4; do_m68k_semihosting(env, env->dregs[0]); return; } - env->halted = 1; + cs = CPU(m68k_env_get_cpu(env)); + cs->halted = 1; env->exception_index = EXCP_HLT; - cpu_loop_exit(); + cpu_loop_exit(env); return; } if (env->exception_index >= EXCP_TRAP0 @@ -148,28 +144,40 @@ void do_interrupt(int is_hw) /* ??? This could cause MMU faults. */ sp &= ~3; sp -= 4; - stl_kernel(sp, retaddr); + cpu_stl_kernel(env, sp, retaddr); sp -= 4; - stl_kernel(sp, fmt); + cpu_stl_kernel(env, sp, fmt); env->aregs[7] = sp; /* Jump to vector. */ - env->pc = ldl_kernel(env->vbr + vector); + env->pc = cpu_ldl_kernel(env, env->vbr + vector); +} + +void m68k_cpu_do_interrupt(CPUState *cs) +{ + M68kCPU *cpu = M68K_CPU(cs); + CPUM68KState *env = &cpu->env; + + do_interrupt_all(env, 0); } +void do_interrupt_m68k_hardirq(CPUM68KState *env) +{ + do_interrupt_all(env, 1); +} #endif -static void raise_exception(int tt) +static void raise_exception(CPUM68KState *env, int tt) { env->exception_index = tt; - cpu_loop_exit(); + cpu_loop_exit(env); } -void HELPER(raise_exception)(uint32_t tt) +void HELPER(raise_exception)(CPUM68KState *env, uint32_t tt) { - raise_exception(tt); + raise_exception(env, tt); } -void HELPER(divu)(CPUState *env, uint32_t word) +void HELPER(divu)(CPUM68KState *env, uint32_t word) { uint32_t num; uint32_t den; @@ -180,14 +188,12 @@ void HELPER(divu)(CPUState *env, uint32_t word) num = env->div1; den = env->div2; /* ??? This needs to make sure the throwing location is accurate. */ - if (den == 0) - raise_exception(EXCP_DIV0); + if (den == 0) { + raise_exception(env, EXCP_DIV0); + } quot = num / den; rem = num % den; flags = 0; - /* Avoid using a PARAM1 of zero. This breaks dyngen because it uses - the address of a symbol, and gcc knows symbols can't have address - zero. */ if (word && quot > 0xffff) flags |= CCF_V; if (quot == 0) @@ -199,7 +205,7 @@ void HELPER(divu)(CPUState *env, uint32_t word) env->cc_dest = flags; } -void HELPER(divs)(CPUState *env, uint32_t word) +void HELPER(divs)(CPUM68KState *env, uint32_t word) { int32_t num; int32_t den; @@ -209,8 +215,9 @@ void HELPER(divs)(CPUState *env, uint32_t word) num = env->div1; den = env->div2; - if (den == 0) - raise_exception(EXCP_DIV0); + if (den == 0) { + raise_exception(env, EXCP_DIV0); + } quot = num / den; rem = num % den; flags = 0;