Commit 105a0601 authored by Peter Maydell's avatar Peter Maydell
Browse files

Merge remote-tracking branch 'remotes/pmaydell/tags/pull-target-arm-20140220' into staging



target-arm queue:
 * Fix a bug causing an assertion in the NVIC on ARMv7M models
 * More A64 Neon instructions
 * Refactor cpreg API to separate out access check functions, as
   groundwork for AArch64 system mode
 * Fix bug in linux-user A64 store-exclusive of XZR

# gpg: Signature made Thu 20 Feb 2014 11:12:57 GMT using RSA key ID 14360CDE
# gpg: Good signature from "Peter Maydell <peter.maydell@linaro.org>"

* remotes/pmaydell/tags/pull-target-arm-20140220: (30 commits)
  linux-user: AArch64: Fix exclusive store of the zero register
  target-arm: A64: Implement unprivileged load/store
  target-arm: A64: Implement narrowing three-reg-diff operations
  target-arm: A64: Implement the wide 3-reg-different operations
  target-arm: A64: Add most remaining three-reg-diff widening ops
  target-arm: A64: Add opcode comments to disas_simd_three_reg_diff
  target-arm: A64: Implement store-exclusive for system mode
  target-arm: Fix incorrect type for value argument to write_raw_cp_reg
  target-arm: Remove failure status return from read/write_raw_cp_reg
  target-arm: Remove unnecessary code now read/write fns can't fail
  target-arm: Drop success/fail return from cpreg read and write functions
  target-arm: Convert miscellaneous reginfo structs to accessfn
  target-arm: Convert generic timer reginfo to accessfn
  target-arm: Convert performance monitor reginfo to accessfn
  target-arm: Split cpreg access checks out from read/write functions
  target-arm: Stop underdecoding ARM946 PRBS registers
  target-arm: Log bad system register accesses with LOG_UNIMP
  target-arm: Remove unused ARMCPUState sr substruct
  target-arm: Restrict check_ap() use of S and R bits to v6 and earlier
  target-arm: Define names for SCTLR bits
  ...

Signed-off-by: default avatarPeter Maydell <peter.maydell@linaro.org>
parents 3e890c77 2ea5a2ca
Loading
Loading
Loading
Loading
+38 −0
Original line number Diff line number Diff line
@@ -2372,6 +2372,17 @@ float32 float32_muladd(float32 a, float32 b, float32 c, int flags STATUS_PARAM)
            }
        }
        /* Zero plus something non-zero : just return the something */
        if (flags & float_muladd_halve_result) {
            if (cExp == 0) {
                normalizeFloat32Subnormal(cSig, &cExp, &cSig);
            }
            /* Subtract one to halve, and one again because roundAndPackFloat32
             * wants one less than the true exponent.
             */
            cExp -= 2;
            cSig = (cSig | 0x00800000) << 7;
            return roundAndPackFloat32(cSign ^ signflip, cExp, cSig STATUS_VAR);
        }
        return packFloat32(cSign ^ signflip, cExp, cSig);
    }

@@ -2408,6 +2419,9 @@ float32 float32_muladd(float32 a, float32 b, float32 c, int flags STATUS_PARAM)
            /* Throw out the special case of c being an exact zero now */
            shift64RightJamming(pSig64, 32, &pSig64);
            pSig = pSig64;
            if (flags & float_muladd_halve_result) {
                pExp--;
            }
            return roundAndPackFloat32(zSign, pExp - 1,
                                       pSig STATUS_VAR);
        }
@@ -2472,6 +2486,10 @@ float32 float32_muladd(float32 a, float32 b, float32 c, int flags STATUS_PARAM)
        zSig64 <<= shiftcount;
        zExp -= shiftcount;
    }
    if (flags & float_muladd_halve_result) {
        zExp--;
    }

    shift64RightJamming(zSig64, 32, &zSig64);
    return roundAndPackFloat32(zSign, zExp, zSig64 STATUS_VAR);
}
@@ -4088,6 +4106,17 @@ float64 float64_muladd(float64 a, float64 b, float64 c, int flags STATUS_PARAM)
            }
        }
        /* Zero plus something non-zero : just return the something */
        if (flags & float_muladd_halve_result) {
            if (cExp == 0) {
                normalizeFloat64Subnormal(cSig, &cExp, &cSig);
            }
            /* Subtract one to halve, and one again because roundAndPackFloat64
             * wants one less than the true exponent.
             */
            cExp -= 2;
            cSig = (cSig | 0x0010000000000000ULL) << 10;
            return roundAndPackFloat64(cSign ^ signflip, cExp, cSig STATUS_VAR);
        }
        return packFloat64(cSign ^ signflip, cExp, cSig);
    }

@@ -4123,6 +4152,9 @@ float64 float64_muladd(float64 a, float64 b, float64 c, int flags STATUS_PARAM)
        if (!cSig) {
            /* Throw out the special case of c being an exact zero now */
            shift128RightJamming(pSig0, pSig1, 64, &pSig0, &pSig1);
            if (flags & float_muladd_halve_result) {
                pExp--;
            }
            return roundAndPackFloat64(zSign, pExp - 1,
                                       pSig1 STATUS_VAR);
        }
@@ -4159,6 +4191,9 @@ float64 float64_muladd(float64 a, float64 b, float64 c, int flags STATUS_PARAM)
            zExp--;
        }
        shift128RightJamming(zSig0, zSig1, 64, &zSig0, &zSig1);
        if (flags & float_muladd_halve_result) {
            zExp--;
        }
        return roundAndPackFloat64(zSign, zExp, zSig1 STATUS_VAR);
    } else {
        /* Subtraction */
@@ -4209,6 +4244,9 @@ float64 float64_muladd(float64 a, float64 b, float64 c, int flags STATUS_PARAM)
                zExp -= (shiftcount + 64);
            }
        }
        if (flags & float_muladd_halve_result) {
            zExp--;
        }
        return roundAndPackFloat64(zSign, zExp, zSig0 STATUS_VAR);
    }
}
+13 −23
Original line number Diff line number Diff line
@@ -224,15 +224,13 @@ static const VMStateDescription vmstate_pxa2xx_cm = {
    }
};

static int pxa2xx_clkcfg_read(CPUARMState *env, const ARMCPRegInfo *ri,
                              uint64_t *value)
static uint64_t pxa2xx_clkcfg_read(CPUARMState *env, const ARMCPRegInfo *ri)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
    *value = s->clkcfg;
    return 0;
    return s->clkcfg;
}

static int pxa2xx_clkcfg_write(CPUARMState *env, const ARMCPRegInfo *ri,
static void pxa2xx_clkcfg_write(CPUARMState *env, const ARMCPRegInfo *ri,
                                uint64_t value)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
@@ -240,10 +238,9 @@ static int pxa2xx_clkcfg_write(CPUARMState *env, const ARMCPRegInfo *ri,
    if (value & 2) {
        printf("%s: CPU frequency change attempt\n", __func__);
    }
    return 0;
}

static int pxa2xx_pwrmode_write(CPUARMState *env, const ARMCPRegInfo *ri,
static void pxa2xx_pwrmode_write(CPUARMState *env, const ARMCPRegInfo *ri,
                                 uint64_t value)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
@@ -310,37 +307,30 @@ static int pxa2xx_pwrmode_write(CPUARMState *env, const ARMCPRegInfo *ri,
        printf("%s: machine entered %s mode\n", __func__,
               pwrmode[value & 7]);
    }

    return 0;
}

static int pxa2xx_cppmnc_read(CPUARMState *env, const ARMCPRegInfo *ri,
                              uint64_t *value)
static uint64_t pxa2xx_cppmnc_read(CPUARMState *env, const ARMCPRegInfo *ri)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
    *value = s->pmnc;
    return 0;
    return s->pmnc;
}

static int pxa2xx_cppmnc_write(CPUARMState *env, const ARMCPRegInfo *ri,
static void pxa2xx_cppmnc_write(CPUARMState *env, const ARMCPRegInfo *ri,
                                uint64_t value)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
    s->pmnc = value;
    return 0;
}

static int pxa2xx_cpccnt_read(CPUARMState *env, const ARMCPRegInfo *ri,
                              uint64_t *value)
static uint64_t pxa2xx_cpccnt_read(CPUARMState *env, const ARMCPRegInfo *ri)
{
    PXA2xxState *s = (PXA2xxState *)ri->opaque;
    if (s->pmnc & 1) {
        *value = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
        return qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
    } else {
        *value = 0;
    }
        return 0;
    }
}

static const ARMCPRegInfo pxa_cp_reginfo[] = {
    /* cp14 crm==1: perf registers */
+4 −7
Original line number Diff line number Diff line
@@ -217,20 +217,17 @@ static const int pxa2xx_cp_reg_map[0x10] = {
    [0xa] = ICPR2,
};

static int pxa2xx_pic_cp_read(CPUARMState *env, const ARMCPRegInfo *ri,
                              uint64_t *value)
static uint64_t pxa2xx_pic_cp_read(CPUARMState *env, const ARMCPRegInfo *ri)
{
    int offset = pxa2xx_cp_reg_map[ri->crn];
    *value = pxa2xx_pic_mem_read(ri->opaque, offset, 4);
    return 0;
    return pxa2xx_pic_mem_read(ri->opaque, offset, 4);
}

static int pxa2xx_pic_cp_write(CPUARMState *env, const ARMCPRegInfo *ri,
static void pxa2xx_pic_cp_write(CPUARMState *env, const ARMCPRegInfo *ri,
                                uint64_t value)
{
    int offset = pxa2xx_cp_reg_map[ri->crn];
    pxa2xx_pic_mem_write(ri->opaque, offset, value, 4);
    return 0;
}

#define REGINFO_FOR_PIC_CP(NAME, CRN) \
+1 −1
Original line number Diff line number Diff line
@@ -189,7 +189,7 @@ uint32_t gic_acknowledge_irq(GICState *s, int cpu)
    }
    s->last_active[irq][cpu] = s->running_irq[cpu];

    if (s->revision == REV_11MPCORE) {
    if (s->revision == REV_11MPCORE || s->revision == REV_NVIC) {
        /* Clear pending flags for both level and edge triggered interrupts.
         * Level triggered IRQs will be reasserted once they become inactive.
         */
+3 −0
Original line number Diff line number Diff line
@@ -249,11 +249,14 @@ void float_raise( int8 flags STATUS_PARAM);
| Using these differs from negating an input or output before calling
| the muladd function in that this means that a NaN doesn't have its
| sign bit inverted before it is propagated.
| We also support halving the result before rounding, as a special
| case to support the ARM fused-sqrt-step instruction FRSQRTS.
*----------------------------------------------------------------------------*/
enum {
    float_muladd_negate_c = 1,
    float_muladd_negate_product = 2,
    float_muladd_negate_result = 4,
    float_muladd_halve_result = 8,
};

/*----------------------------------------------------------------------------
Loading