qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Qemu-devel] [PATCH] linux-user: Handle new ARM breakpoint instructi


From: Hunter Laux
Subject: Re: [Qemu-devel] [PATCH] linux-user: Handle new ARM breakpoint instruction
Date: Wed, 25 Jun 2014 09:11:56 -0700

Isn't the instruction decoder really the wrong place to do that since that exception is handled differently in user space and kernel space. It's my understanding that the instruction decoder is also shared by machine emulation. If you're doing machine emulation you'll still want to throw EXCP_UDEF because that's what Linux is expecting.

http://lxr.free-electrons.com/source/arch/avr32/kernel/traps.c#L212

It fixed by signal 4 problem during my SBCL build, but there might be a better way to fix this. I think they use every trick in the book to get that thing working.

-Hunter Laux

On Jun 25, 2014 2:18 AM, "Peter Maydell" <address@hidden> wrote:
On 25 June 2014 05:08, Hunter Laux <address@hidden> wrote:
> This instruction space is guaranteed to be undefined.
> ARM:   xxxx 0111 1111 xxxx xxxx xxxx 1111 xxxx
> Thumb: 1101 1110 xxxx xxxx
>
> The breakpoint instructions were selected from this instruction space.
> Linux traps the illegal instruction and sends a SIGTRAP if it is a breakpoint.
>
> Here is the Linux implementation:
> http://lxr.free-electrons.com/source/arch/arm/kernel/ptrace.c#L221
>
> Signed-off-by: Hunter Laux <address@hidden>
> ---
>  linux-user/main.c | 18 ++++++++++++++++++
>  1 file changed, 18 insertions(+)
>
> diff --git a/linux-user/main.c b/linux-user/main.c
> index 900a17f..91f2681 100644
> --- a/linux-user/main.c
> +++ b/linux-user/main.c
> @@ -688,11 +688,29 @@ void cpu_loop(CPUARMState *env)
>                  uint32_t opcode;
>                  int rc;
>
> +                const uint32_t arm_bkpt_mask        = 0x0FFFFFFF;
> +                const uint32_t arm_bkpt             = 0x07F001F0;
> +                const uint32_t arm_bkpt_thumb_mask  = 0x0000FFFF;
> +                const uint32_t arm_bkpt_thumb       = 0x0000DE01;
> +                const uint32_t arm_bkpt_thumb2_mask = 0xFFFFFFFF;
> +                const uint32_t arm_bkpt_thumb2      = 0xF7F0A000;
> +
>                  /* we handle the FPU emulation here, as Linux */
>                  /* we get the opcode */
>                  /* FIXME - what to do if get_user() fails? */
>                  get_user_code_u32(opcode, env->regs[15], env->bswap_code);
>
> +                if (env->thumb) {
> +                    if ((opcode & arm_bkpt_thumb_mask) == arm_bkpt_thumb
> +                        || (opcode & arm_bkpt_thumb2_mask) == arm_bkpt_thumb2) {
> +                        goto excp_debug;
> +                    }
> +                } else {
> +                    if ((opcode & arm_bkpt_mask) == arm_bkpt) {
> +                        goto excp_debug;
> +                    }
> +                }
> +
>                  rc = EmulateAll(opcode, &ts->fpa, env);
>                  if (rc == 0) { /* illegal instruction */
>                      info.si_signo = SIGILL;

This shouldn't be necessary, because our instruction decoder
causes the BKPT instructions to generate an EXCP_BKPT
(see target-arm/translate.c). So we should never go through
this code path for these instructions...

thanks
-- PMM

reply via email to

[Prev in Thread] Current Thread [Next in Thread]