summaryrefslogtreecommitdiff
path: root/linux-user/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'linux-user/main.c')
-rw-r--r--linux-user/main.c154
1 files changed, 81 insertions, 73 deletions
diff --git a/linux-user/main.c b/linux-user/main.c
index 5c14c1e874..fdee981351 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -130,7 +130,7 @@ void fork_end(int child)
pthread_cond_init(&exclusive_cond, NULL);
pthread_cond_init(&exclusive_resume, NULL);
pthread_mutex_init(&tcg_ctx.tb_ctx.tb_lock, NULL);
- gdbserver_fork((CPUArchState *)thread_cpu->env_ptr);
+ gdbserver_fork(thread_cpu);
} else {
pthread_mutex_unlock(&exclusive_lock);
pthread_mutex_unlock(&tcg_ctx.tb_ctx.tb_lock);
@@ -169,7 +169,7 @@ static inline void start_exclusive(void)
}
/* Finish an exclusive operation. */
-static inline void end_exclusive(void)
+static inline void __attribute__((unused)) end_exclusive(void)
{
pending_cpus = 0;
pthread_cond_broadcast(&exclusive_resume);
@@ -215,10 +215,6 @@ void cpu_list_unlock(void)
/***********************************************************/
/* CPUX86 core interface */
-void cpu_smm_update(CPUX86State *env)
-{
-}
-
uint64_t cpu_get_tsc(CPUX86State *env)
{
return cpu_get_real_ticks();
@@ -283,7 +279,9 @@ void cpu_loop(CPUX86State *env)
target_siginfo_t info;
for(;;) {
- trapnr = cpu_x86_exec(env);
+ cpu_exec_start(cs);
+ trapnr = cpu_x86_exec(cs);
+ cpu_exec_end(cs);
switch(trapnr) {
case 0x80:
/* linux syscall from int $0x80 */
@@ -313,7 +311,7 @@ void cpu_loop(CPUX86State *env)
#endif
case EXCP0B_NOSEG:
case EXCP0C_STACK:
- info.si_signo = SIGBUS;
+ info.si_signo = TARGET_SIGBUS;
info.si_errno = 0;
info.si_code = TARGET_SI_KERNEL;
info._sifields._sigfault._addr = 0;
@@ -327,7 +325,7 @@ void cpu_loop(CPUX86State *env)
} else
#endif
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
info.si_code = TARGET_SI_KERNEL;
info._sifields._sigfault._addr = 0;
@@ -335,7 +333,7 @@ void cpu_loop(CPUX86State *env)
}
break;
case EXCP0E_PAGE:
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
if (!(env->error_code & 1))
info.si_code = TARGET_SEGV_MAPERR;
@@ -352,7 +350,7 @@ void cpu_loop(CPUX86State *env)
#endif
{
/* division by zero */
- info.si_signo = SIGFPE;
+ info.si_signo = TARGET_SIGFPE;
info.si_errno = 0;
info.si_code = TARGET_FPE_INTDIV;
info._sifields._sigfault._addr = env->eip;
@@ -367,7 +365,7 @@ void cpu_loop(CPUX86State *env)
} else
#endif
{
- info.si_signo = SIGTRAP;
+ info.si_signo = TARGET_SIGTRAP;
info.si_errno = 0;
if (trapnr == EXCP01_DB) {
info.si_code = TARGET_TRAP_BRKPT;
@@ -387,7 +385,7 @@ void cpu_loop(CPUX86State *env)
} else
#endif
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
info.si_code = TARGET_SI_KERNEL;
info._sifields._sigfault._addr = 0;
@@ -395,7 +393,7 @@ void cpu_loop(CPUX86State *env)
}
break;
case EXCP06_ILLOP:
- info.si_signo = SIGILL;
+ info.si_signo = TARGET_SIGILL;
info.si_errno = 0;
info.si_code = TARGET_ILL_ILLOPN;
info._sifields._sigfault._addr = env->eip;
@@ -517,14 +515,12 @@ segv:
end_exclusive();
/* We get the PC of the entry address - which is as good as anything,
on a real kernel what you get depends on which mode it uses. */
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
info._sifields._sigfault._addr = env->exception.vaddress;
queue_signal(env, info.si_signo, &info);
-
- end_exclusive();
}
/* Handle a jump to the kernel code page. */
@@ -564,7 +560,7 @@ do_kernel_trap(CPUARMState *env)
end_exclusive();
break;
case 0xffff0fe0: /* __kernel_get_tls */
- env->regs[0] = env->cp15.tpidrro_el0;
+ env->regs[0] = cpu_get_tls(env);
break;
case 0xffff0f60: /* __kernel_cmpxchg64 */
arm_kernel_cmpxchg64_helper(env);
@@ -678,7 +674,7 @@ void cpu_loop(CPUARMState *env)
for(;;) {
cpu_exec_start(cs);
- trapnr = cpu_arm_exec(env);
+ trapnr = cpu_arm_exec(cs);
cpu_exec_end(cs);
switch(trapnr) {
case EXCP_UDEF:
@@ -694,7 +690,7 @@ void cpu_loop(CPUARMState *env)
rc = EmulateAll(opcode, &ts->fpa, env);
if (rc == 0) { /* illegal instruction */
- info.si_signo = SIGILL;
+ info.si_signo = TARGET_SIGILL;
info.si_errno = 0;
info.si_code = TARGET_ILL_ILLOPN;
info._sifields._sigfault._addr = env->regs[15];
@@ -718,7 +714,7 @@ void cpu_loop(CPUARMState *env)
//printf("fpsr 0x%x, arm_fpe 0x%x\n",fpsr,arm_fpe);
if (fpsr & (arm_fpe << 16)) { /* exception enabled? */
- info.si_signo = SIGFPE;
+ info.si_signo = TARGET_SIGFPE;
info.si_errno = 0;
/* ordered by priority, least first */
@@ -842,7 +838,7 @@ void cpu_loop(CPUARMState *env)
case EXCP_DATA_ABORT:
addr = env->exception.vaddress;
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -1009,7 +1005,7 @@ void cpu_loop(CPUARMState *env)
for (;;) {
cpu_exec_start(cs);
- trapnr = cpu_arm_exec(env);
+ trapnr = cpu_arm_exec(cs);
cpu_exec_end(cs);
switch (trapnr) {
@@ -1028,7 +1024,7 @@ void cpu_loop(CPUARMState *env)
/* just indicate that signals should be handled asap */
break;
case EXCP_UDEF:
- info.si_signo = SIGILL;
+ info.si_signo = TARGET_SIGILL;
info.si_errno = 0;
info.si_code = TARGET_ILL_ILLOPN;
info._sifields._sigfault._addr = env->pc;
@@ -1041,7 +1037,7 @@ void cpu_loop(CPUARMState *env)
/* fall through for segv */
case EXCP_PREFETCH_ABORT:
case EXCP_DATA_ABORT:
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -1088,7 +1084,7 @@ void cpu_loop(CPUUniCore32State *env)
for (;;) {
cpu_exec_start(cs);
- trapnr = uc32_cpu_exec(env);
+ trapnr = uc32_cpu_exec(cs);
cpu_exec_end(cs);
switch (trapnr) {
case UC32_EXCP_PRIV:
@@ -1121,7 +1117,7 @@ void cpu_loop(CPUUniCore32State *env)
break;
case UC32_EXCP_DTRAP:
case UC32_EXCP_ITRAP:
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -1288,7 +1284,9 @@ void cpu_loop (CPUSPARCState *env)
target_siginfo_t info;
while (1) {
- trapnr = cpu_sparc_exec (env);
+ cpu_exec_start(cs);
+ trapnr = cpu_sparc_exec(cs);
+ cpu_exec_end(cs);
/* Compute PSR before exposing state. */
if (env->cc_op != CC_OP_FLAGS) {
@@ -1426,8 +1424,7 @@ void cpu_loop (CPUSPARCState *env)
#ifdef TARGET_PPC
static inline uint64_t cpu_ppc_get_tb(CPUPPCState *env)
{
- /* TO FIX */
- return 0;
+ return cpu_get_real_ticks();
}
uint64_t cpu_ppc_load_tbl(CPUPPCState *env)
@@ -1568,7 +1565,7 @@ void cpu_loop(CPUPPCState *env)
for(;;) {
cpu_exec_start(cs);
- trapnr = cpu_ppc_exec(env);
+ trapnr = cpu_ppc_exec(cs);
cpu_exec_end(cs);
switch(trapnr) {
case POWERPC_EXCP_NONE:
@@ -2420,7 +2417,7 @@ void cpu_loop(CPUMIPSState *env)
for(;;) {
cpu_exec_start(cs);
- trapnr = cpu_mips_exec(env);
+ trapnr = cpu_mips_exec(cs);
cpu_exec_end(cs);
switch(trapnr) {
case EXCP_SYSCALL:
@@ -2580,7 +2577,7 @@ done_syscall:
code = (trap_instr >> 6) & 0x3f;
}
} else {
- ret = get_user_ual(trap_instr, env->active_tc.PC);
+ ret = get_user_u32(trap_instr, env->active_tc.PC);
if (ret != 0) {
goto error;
}
@@ -2614,7 +2611,7 @@ done_syscall:
trap_instr = (instr[0] << 16) | instr[1];
} else {
- ret = get_user_ual(trap_instr, env->active_tc.PC);
+ ret = get_user_u32(trap_instr, env->active_tc.PC);
}
if (ret != 0) {
@@ -2656,7 +2653,9 @@ void cpu_loop(CPUOpenRISCState *env)
int trapnr, gdbsig;
for (;;) {
- trapnr = cpu_exec(env);
+ cpu_exec_start(cs);
+ trapnr = cpu_openrisc_exec(cs);
+ cpu_exec_end(cs);
gdbsig = 0;
switch (trapnr) {
@@ -2666,7 +2665,7 @@ void cpu_loop(CPUOpenRISCState *env)
break;
case EXCP_BUSERR:
qemu_log("\nBus error, exit, pc is %#x\n", env->pc);
- gdbsig = SIGBUS;
+ gdbsig = TARGET_SIGBUS;
break;
case EXCP_DPF:
case EXCP_IPF:
@@ -2678,11 +2677,11 @@ void cpu_loop(CPUOpenRISCState *env)
break;
case EXCP_ALIGN:
qemu_log("\nAlignment pc is %#x\n", env->pc);
- gdbsig = SIGBUS;
+ gdbsig = TARGET_SIGBUS;
break;
case EXCP_ILLEGAL:
qemu_log("\nIllegal instructionpc is %#x\n", env->pc);
- gdbsig = SIGILL;
+ gdbsig = TARGET_SIGILL;
break;
case EXCP_INT:
qemu_log("\nExternal interruptpc is %#x\n", env->pc);
@@ -2693,7 +2692,7 @@ void cpu_loop(CPUOpenRISCState *env)
break;
case EXCP_RANGE:
qemu_log("\nRange\n");
- gdbsig = SIGSEGV;
+ gdbsig = TARGET_SIGSEGV;
break;
case EXCP_SYSCALL:
env->pc += 4; /* 0xc00; */
@@ -2711,7 +2710,7 @@ void cpu_loop(CPUOpenRISCState *env)
break;
case EXCP_TRAP:
qemu_log("\nTrap\n");
- gdbsig = SIGTRAP;
+ gdbsig = TARGET_SIGTRAP;
break;
case EXCP_NR:
qemu_log("\nNR\n");
@@ -2744,7 +2743,9 @@ void cpu_loop(CPUSH4State *env)
target_siginfo_t info;
while (1) {
- trapnr = cpu_sh4_exec (env);
+ cpu_exec_start(cs);
+ trapnr = cpu_sh4_exec(cs);
+ cpu_exec_end(cs);
switch (trapnr) {
case 0x160:
@@ -2779,7 +2780,7 @@ void cpu_loop(CPUSH4State *env)
break;
case 0xa0:
case 0xc0:
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
info.si_code = TARGET_SEGV_MAPERR;
info._sifields._sigfault._addr = env->tea;
@@ -2804,11 +2805,13 @@ void cpu_loop(CPUCRISState *env)
target_siginfo_t info;
while (1) {
- trapnr = cpu_cris_exec (env);
+ cpu_exec_start(cs);
+ trapnr = cpu_cris_exec(cs);
+ cpu_exec_end(cs);
switch (trapnr) {
case 0xaa:
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -2863,11 +2866,13 @@ void cpu_loop(CPUMBState *env)
target_siginfo_t info;
while (1) {
- trapnr = cpu_mb_exec (env);
+ cpu_exec_start(cs);
+ trapnr = cpu_mb_exec(cs);
+ cpu_exec_end(cs);
switch (trapnr) {
case 0xaa:
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -2905,14 +2910,14 @@ void cpu_loop(CPUMBState *env)
switch (env->sregs[SR_ESR] & 31) {
case ESR_EC_DIVZERO:
- info.si_signo = SIGFPE;
+ info.si_signo = TARGET_SIGFPE;
info.si_errno = 0;
info.si_code = TARGET_FPE_FLTDIV;
info._sifields._sigfault._addr = 0;
queue_signal(env, info.si_signo, &info);
break;
case ESR_EC_FPU:
- info.si_signo = SIGFPE;
+ info.si_signo = TARGET_SIGFPE;
info.si_errno = 0;
if (env->sregs[SR_FSR] & FSR_IO) {
info.si_code = TARGET_FPE_FLTINV;
@@ -2966,13 +2971,15 @@ void cpu_loop(CPUM68KState *env)
TaskState *ts = cs->opaque;
for(;;) {
- trapnr = cpu_m68k_exec(env);
+ cpu_exec_start(cs);
+ trapnr = cpu_m68k_exec(cs);
+ cpu_exec_end(cs);
switch(trapnr) {
case EXCP_ILLEGAL:
{
if (ts->sim_syscalls) {
uint16_t nr;
- nr = lduw(env->pc + 2);
+ get_user_u16(nr, env->pc + 2);
env->pc += 4;
do_m68k_simcall(env, nr);
} else {
@@ -2989,7 +2996,7 @@ void cpu_loop(CPUM68KState *env)
case EXCP_LINEF:
case EXCP_UNSUPPORTED:
do_sigill:
- info.si_signo = SIGILL;
+ info.si_signo = TARGET_SIGILL;
info.si_errno = 0;
info.si_code = TARGET_ILL_ILLOPN;
info._sifields._sigfault._addr = env->pc;
@@ -3016,7 +3023,7 @@ void cpu_loop(CPUM68KState *env)
break;
case EXCP_ACCESS:
{
- info.si_signo = SIGSEGV;
+ info.si_signo = TARGET_SIGSEGV;
info.si_errno = 0;
/* XXX: check env->error_code */
info.si_code = TARGET_SEGV_MAPERR;
@@ -3103,7 +3110,9 @@ void cpu_loop(CPUAlphaState *env)
abi_long sysret;
while (1) {
- trapnr = cpu_alpha_exec (env);
+ cpu_exec_start(cs);
+ trapnr = cpu_alpha_exec(cs);
+ cpu_exec_end(cs);
/* All of the traps imply a transition through PALcode, which
implies an REI instruction has been executed. Which means
@@ -3289,7 +3298,9 @@ void cpu_loop(CPUS390XState *env)
target_ulong addr;
while (1) {
- trapnr = cpu_s390x_exec(env);
+ cpu_exec_start(cs);
+ trapnr = cpu_s390x_exec(cs);
+ cpu_exec_end(cs);
switch (trapnr) {
case EXCP_INTERRUPT:
/* Just indicate that signals should be handled asap. */
@@ -3319,12 +3330,12 @@ void cpu_loop(CPUS390XState *env)
switch (n) {
case PGM_OPERATION:
case PGM_PRIVILEGED:
- sig = SIGILL;
+ sig = TARGET_SIGILL;
n = TARGET_ILL_ILLOPC;
goto do_signal_pc;
case PGM_PROTECTION:
case PGM_ADDRESSING:
- sig = SIGSEGV;
+ sig = TARGET_SIGSEGV;
/* XXX: check env->error_code */
n = TARGET_SEGV_MAPERR;
addr = env->__excp_addr;
@@ -3334,16 +3345,16 @@ void cpu_loop(CPUS390XState *env)
case PGM_SPECIAL_OP:
case PGM_OPERAND:
do_sigill_opn:
- sig = SIGILL;
+ sig = TARGET_SIGILL;
n = TARGET_ILL_ILLOPN;
goto do_signal_pc;
case PGM_FIXPT_OVERFLOW:
- sig = SIGFPE;
+ sig = TARGET_SIGFPE;
n = TARGET_FPE_INTOVF;
goto do_signal_pc;
case PGM_FIXPT_DIVIDE:
- sig = SIGFPE;
+ sig = TARGET_SIGFPE;
n = TARGET_FPE_INTDIV;
goto do_signal_pc;
@@ -3368,7 +3379,7 @@ void cpu_loop(CPUS390XState *env)
/* ??? Quantum exception; BFP, DFP error. */
goto do_sigill_opn;
}
- sig = SIGFPE;
+ sig = TARGET_SIGFPE;
goto do_signal_pc;
}
@@ -3434,12 +3445,10 @@ void init_task_state(TaskState *ts)
CPUArchState *cpu_copy(CPUArchState *env)
{
CPUState *cpu = ENV_GET_CPU(env);
- CPUArchState *new_env = cpu_init(cpu_model);
- CPUState *new_cpu = ENV_GET_CPU(new_env);
-#if defined(TARGET_HAS_ICE)
+ CPUState *new_cpu = cpu_init(cpu_model);
+ CPUArchState *new_env = new_cpu->env_ptr;
CPUBreakpoint *bp;
CPUWatchpoint *wp;
-#endif
/* Reset non arch specific state */
cpu_reset(new_cpu);
@@ -3449,16 +3458,14 @@ CPUArchState *cpu_copy(CPUArchState *env)
/* Clone all break/watchpoints.
Note: Once we support ptrace with hw-debug register access, make sure
BP_CPU break/watchpoints are handled correctly on clone. */
- QTAILQ_INIT(&cpu->breakpoints);
- QTAILQ_INIT(&cpu->watchpoints);
-#if defined(TARGET_HAS_ICE)
+ QTAILQ_INIT(&new_cpu->breakpoints);
+ QTAILQ_INIT(&new_cpu->watchpoints);
QTAILQ_FOREACH(bp, &cpu->breakpoints, entry) {
cpu_breakpoint_insert(new_cpu, bp->pc, bp->flags, NULL);
}
QTAILQ_FOREACH(wp, &cpu->watchpoints, entry) {
cpu_watchpoint_insert(new_cpu, wp->vaddr, wp->len, wp->flags, NULL);
}
-#endif
return new_env;
}
@@ -3905,7 +3912,7 @@ int main(int argc, char **argv, char **envp)
#endif
#elif defined(TARGET_MIPS)
#if defined(TARGET_ABI_MIPSN32) || defined(TARGET_ABI_MIPSN64)
- cpu_model = "20Kc";
+ cpu_model = "5KEf";
#else
cpu_model = "24Kf";
#endif
@@ -3917,20 +3924,21 @@ int main(int argc, char **argv, char **envp)
# else
cpu_model = "750";
# endif
+#elif defined TARGET_SH4
+ cpu_model = TYPE_SH7785_CPU;
#else
cpu_model = "any";
#endif
}
tcg_exec_init(0);
- cpu_exec_init_all();
/* NOTE: we need to init the CPU at this stage to get
qemu_host_page_size */
- env = cpu_init(cpu_model);
- if (!env) {
+ cpu = cpu_init(cpu_model);
+ if (!cpu) {
fprintf(stderr, "Unable to find CPU definition\n");
exit(1);
}
- cpu = ENV_GET_CPU(env);
+ env = cpu->env_ptr;
cpu_reset(cpu);
thread_cpu = cpu;