qemu-devel
[Top][All Lists]
Advanced

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

Re: [Qemu-devel] [PATCH 06/24] target-arm: A64: Implement store-exclusiv


From: Hu Tao
Subject: Re: [Qemu-devel] [PATCH 06/24] target-arm: A64: Implement store-exclusive for system mode
Date: Wed, 22 Jan 2014 10:19:44 +0800
User-agent: Mutt/1.5.21 (2010-09-15)

On Tue, Jan 21, 2014 at 08:12:12PM +0000, Peter Maydell wrote:
> System mode store-exclusive use a different code path to usermode ones;
> implement this missing code, in a similar way to the 32 bit version.
> 
> Signed-off-by: Peter Maydell <address@hidden>
> ---
>  target-arm/translate-a64.c | 68 
> ++++++++++++++++++++++++++++++++++++++++++----
>  1 file changed, 62 insertions(+), 6 deletions(-)
> 
> diff --git a/target-arm/translate-a64.c b/target-arm/translate-a64.c
> index e0f6765..5aa1f17 100644
> --- a/target-arm/translate-a64.c
> +++ b/target-arm/translate-a64.c
> @@ -1422,12 +1422,68 @@ static void gen_store_exclusive(DisasContext *s, int 
> rd, int rt, int rt2,
>  }
>  #else
>  static void gen_store_exclusive(DisasContext *s, int rd, int rt, int rt2,
> -                                TCGv_i64 addr, int size, int is_pair)
> -{
> -    qemu_log_mask(LOG_UNIMP,
> -                  "%s:%d: system mode store_exclusive unsupported "
> -                  "at pc=%016" PRIx64 "\n",
> -                  __FILE__, __LINE__, s->pc - 4);
> +                                TCGv_i64 inaddr, int size, int is_pair)
> +{
> +    /* if (env->exclusive_addr == addr && env->exclusive_val == [addr]
> +     *     && (!is_pair || env->exclusive_high == [addr + datasize])) {
> +     *     [addr] = {Rt};
> +     *     if (is_pair) {
> +     *         [addr + datasize] = {Rt2};
> +     *     }
> +     *     {Rd} = 0;
> +     * } else {
> +     *     {Rd} = 1;
> +     * }
> +     * env->exclusive_addr = -1;
> +     */
> +    int fail_label = gen_new_label();
> +    int done_label = gen_new_label();
> +    TCGv_i64 addr = tcg_temp_local_new_i64();
> +    TCGv_i64 tmp;
> +
> +    /* Copy input into a local temp so it is not trashed when the
> +     * basic block ends at the branch insn.
> +     */
> +    tcg_gen_mov_i64(addr, inaddr);
> +    tcg_gen_brcond_i64(TCG_COND_NE, addr, cpu_exclusive_addr, fail_label);
> +
> +    tmp = tcg_temp_new_i64();
> +    tcg_gen_qemu_ld_i64(tmp, addr, get_mem_index(s), MO_TE + size);
> +    tcg_gen_brcond_i64(TCG_COND_NE, tmp, cpu_exclusive_val, fail_label);
> +    tcg_temp_free_i64(tmp);
> +
> +    if (is_pair) {
> +        TCGv_i64 addrhi = tcg_temp_new_i64();
> +        TCGv_i64 tmphi = tcg_temp_new_i64();
> +
> +        tcg_gen_addi_i64(addrhi, addr, 1 << size);
> +        tcg_gen_qemu_ld_i64(tmphi, addrhi, get_mem_index(s), MO_TE + size);
> +        tcg_gen_brcond_i64(TCG_COND_NE, tmp, cpu_exclusive_high, fail_label);

s/tmp/tmphi/

> +
> +        tcg_temp_free_i64(tmphi);
> +        tcg_temp_free_i64(addrhi);

Can addrhi be saved and free after doing store?

> +    }
> +
> +    /* We seem to still have the exclusive monitor, so do the store */
> +    tcg_gen_qemu_st_i64(cpu_reg(s, rt), addr, get_mem_index(s), MO_TE + 
> size);
> +    if (is_pair) {
> +        TCGv_i64 addrhi = tcg_temp_new_i64();
> +
> +        tcg_gen_addi_i64(addrhi, addr, 1 << size);
> +        tcg_gen_qemu_st_i64(cpu_reg(s, rt2), addrhi,
> +                            get_mem_index(s), MO_TE + size);
> +        tcg_temp_free_i64(addrhi);
> +    }
> +
> +    tcg_temp_free_i64(addr);
> +
> +    tcg_gen_movi_i64(cpu_reg(s, rd), 0);
> +    tcg_gen_br(done_label);
> +    gen_set_label(fail_label);
> +    tcg_gen_movi_i64(cpu_reg(s, rd), 1);
> +    gen_set_label(done_label);
> +    tcg_gen_movi_i64(cpu_exclusive_addr, -1);
> +
>  }
>  #endif
>  
> -- 
> 1.8.5
> 
> _______________________________________________
> kvmarm mailing list
> address@hidden
> https://lists.cs.columbia.edu/cucslists/listinfo/kvmarm



reply via email to

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