qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2013-08-20 14:07 Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2013-08-20 14:07 UTC (permalink / raw)
  To: Aurelien Jarno, Blue Swirl, Anthony Liguori; +Cc: qemu-devel, Paul Brook

Hi; this is my target-arm queue. Contents:
 * my 'get rid of arm_pic' series
 * generic timer support for A15
 * a few other minor fixes

To avoid potential conflicts between a target-arm pullreq
and an arm-devs pullreq, I've just put all these ARM related
patches in the same tree even though a few of them could
strictly speaking have gone into an arm-devs tree. (I'd
actually prefer to combine target-arm.next and arm-devs.next
into a single tree in future, since I think some of the admin
reasons for the original split have now gone away. Let me know
if this is going to be a problem and I'll maintain the split.)

Please pull.

thanks
--PMM


The following changes since commit f202039811d8746b0586d2fd5f61de6c8cf68056:

  Open up 1.7 development branch (2013-08-15 15:41:13 -0500)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20130820

for you to fetch changes up to 230058106ab26de9b876158dbe27d60719f01f51:

  hw/timer/imx_epit: Simplify and fix imx_epit implementation (2013-08-20 14:54:32 +0100)

----------------------------------------------------------------
target-arm queue

----------------------------------------------------------------
Peter Chubb (1):
      hw/timer/imx_epit: Simplify and fix imx_epit implementation

Peter Maydell (20):
      target-arm: Implement 'int' loglevel
      target-arm: Make IRQ and FIQ gpio lines on the CPU object
      hw/arm/armv7m: Don't use arm_pic_init_cpu()
      hw/arm/exynos4210: Don't use arm_pic_init_cpu()
      hw/arm/highbank: Don't use arm_pic_init_cpu()
      hw/arm/integratorcp: Don't use arm_pic_init_cpu()
      hw/arm/kzm: Don't use arm_pic_init_cpu()
      hw/arm/musicpal: Don't use arm_pic_init_cpu()
      hw/arm/omap*: Don't use arm_pic_init_cpu()
      hw/arm/realview: Don't use arm_pic_init_cpu()
      hw/arm/strongarm: Don't use arm_pic_init_cpu()
      hw/arm/versatilepb: Don't use arm_pic_init_cpu()
      hw/arm/vexpress: Don't use arm_pic_init_cpu()
      hw/arm/xilinx_zynq: Don't use arm_pic_init_cpu()
      hw/arm/pic_cpu: Remove the now-unneeded arm_pic_init_cpu()
      target-arm: Allow raw_read() and raw_write() to handle 64 bit regs
      target-arm: Support coprocessor registers which do I/O
      target-arm: Implement the generic timer
      hw/cpu/a15mpcore: Wire generic timer outputs to GIC inputs
      default-configs: Fix A9MP and A15MP config names

 default-configs/arm-softmmu.mak |    4 +-
 hw/arm/Makefile.objs            |    2 +-
 hw/arm/armv7m.c                 |    5 +-
 hw/arm/exynos4210.c             |   16 +-
 hw/arm/highbank.c               |    4 +-
 hw/arm/integratorcp.c           |    7 +-
 hw/arm/kzm.c                    |    8 +-
 hw/arm/musicpal.c               |    4 +-
 hw/arm/omap1.c                  |    8 +-
 hw/arm/omap2.c                  |    8 +-
 hw/arm/pic_cpu.c                |   68 ---------
 hw/arm/realview.c               |    4 +-
 hw/arm/strongarm.c              |    6 +-
 hw/arm/versatilepb.c            |    7 +-
 hw/arm/vexpress.c               |    8 +-
 hw/arm/xilinx_zynq.c            |    7 +-
 hw/cpu/Makefile.objs            |    4 +-
 hw/cpu/a15mpcore.c              |   18 +++
 hw/timer/imx_epit.c             |   94 +++++-------
 include/hw/arm/arm.h            |    5 -
 target-arm/cpu-qom.h            |    9 ++
 target-arm/cpu.c                |   67 +++++++++
 target-arm/cpu.h                |   27 +++-
 target-arm/helper.c             |  310 ++++++++++++++++++++++++++++++++++++++-
 target-arm/machine.c            |    8 +-
 target-arm/translate.c          |   16 +-
 26 files changed, 514 insertions(+), 210 deletions(-)
 delete mode 100644 hw/arm/pic_cpu.c

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2015-05-18 19:15 Peter Maydell
  2015-05-19  7:57 ` Peter Maydell
  0 siblings, 1 reply; 42+ messages in thread
From: Peter Maydell @ 2015-05-18 19:15 UTC (permalink / raw)
  To: qemu-devel

target-arm queue: mostly the new Xilinx board, plus a handful
of other minor things.

-- PMM


The following changes since commit 385057cbec9b4a0eb6150330c572e875ed714965:

  Merge remote-tracking branch 'remotes/armbru/tags/pull-qapi-2015-05-15' into staging (2015-05-15 17:51:20 +0100)

are available in the git repository at:


  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20150518-3

for you to fetch changes up to 18084b2f71b22b3ec3bf4828b8cb83d1d39e8502:

  target-arm: Remove unneeded '+' (2015-05-18 20:04:19 +0100)

----------------------------------------------------------------
target-arm:
 * New board model: xlnx-ep108
 * Some more preparation for AArch64 EL2/EL3
 * Fix bugs in access checking for generic counter registers
 * Remove a stray '+' sign

----------------------------------------------------------------
Edgar E. Iglesias (3):
      target-arm: Correct accessfn for CNTP_{CT}VAL_EL0
      target-arm: Correct accessfn for CNTV_TVAL_EL0
      target-arm: Remove unneeded '+'

Greg Bellows (3):
      target-arm: Add TTBR regime function and use
      target-arm: Add EL3 and EL2 TCR checking
      target-arm: Add WFx syndrome function

Peter Crosthwaite (14):
      target-arm: cpu64: generalise name of A57 regs
      target-arm: cpu64: Add support for Cortex-A53
      arm: Introduce Xilinx ZynqMP SoC
      arm: xlnx-zynqmp: Add GIC
      arm: xlnx-zynqmp: Connect CPU Timers to GIC
      net: cadence_gem: Clean up variable names
      net: cadence_gem: Split state struct and type into header
      arm: xlnx-zynqmp: Add GEM support
      char: cadence_uart: Clean up variable names
      char: cadence_uart: Split state struct and type into header
      arm: xlnx-zynqmp: Add UART support
      arm: Add xlnx-ep108 machine
      arm: xlnx-ep108: Add external RAM
      arm: xlnx-ep108: Add bootloading

Timothy Baldwin (1):
      linux-user/arm: Correct TARGET_NR_timerfd to TARGET_NR_timerfd_create

 default-configs/aarch64-softmmu.mak |   2 +-
 hw/arm/Makefile.objs                |   1 +
 hw/arm/xlnx-ep108.c                 |  82 ++++++++++++++
 hw/arm/xlnx-zynqmp.c                | 211 ++++++++++++++++++++++++++++++++++++
 hw/char/cadence_uart.c              | 115 ++++++++------------
 hw/net/cadence_gem.c                |  95 +++++-----------
 include/hw/arm/xlnx-zynqmp.h        |  58 ++++++++++
 include/hw/char/cadence_uart.h      |  53 +++++++++
 include/hw/net/cadence_gem.h        |  73 +++++++++++++
 linux-user/arm/syscall_nr.h         |   2 +-
 target-arm/cpu64.c                  |  61 ++++++++++-
 target-arm/helper.c                 |  75 +++++++++----
 target-arm/internals.h              |   6 +
 13 files changed, 671 insertions(+), 163 deletions(-)
 create mode 100644 hw/arm/xlnx-ep108.c
 create mode 100644 hw/arm/xlnx-zynqmp.c
 create mode 100644 include/hw/arm/xlnx-zynqmp.h
 create mode 100644 include/hw/char/cadence_uart.h
 create mode 100644 include/hw/net/cadence_gem.h

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2015-05-18 19:15 Peter Maydell
@ 2015-05-19  7:57 ` Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2015-05-19  7:57 UTC (permalink / raw)
  To: QEMU Developers

On 18 May 2015 at 20:15, Peter Maydell <peter.maydell@linaro.org> wrote:
> target-arm queue: mostly the new Xilinx board, plus a handful
> of other minor things.
>
> -- PMM
>
>
> The following changes since commit 385057cbec9b4a0eb6150330c572e875ed714965:
>
>   Merge remote-tracking branch 'remotes/armbru/tags/pull-qapi-2015-05-15' into staging (2015-05-15 17:51:20 +0100)
>
> are available in the git repository at:
>
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20150518-3
>
> for you to fetch changes up to 18084b2f71b22b3ec3bf4828b8cb83d1d39e8502:
>
>   target-arm: Remove unneeded '+' (2015-05-18 20:04:19 +0100)
>
> ----------------------------------------------------------------
> target-arm:
>  * New board model: xlnx-ep108
>  * Some more preparation for AArch64 EL2/EL3
>  * Fix bugs in access checking for generic counter registers
>  * Remove a stray '+' sign
>
> ----------------------------------------------------------------

Applied, thanks.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2016-03-16 17:18 Peter Maydell
  2016-03-16 17:42 ` Peter Maydell
  2016-03-16 18:19 ` Peter Maydell
  0 siblings, 2 replies; 42+ messages in thread
From: Peter Maydell @ 2016-03-16 17:18 UTC (permalink / raw)
  To: qemu-devel

Here's the target-arm queue; I'm a bit hesitant about the late-landing
various new board/SoC patches, but they won't affect anybody who isn't
trying to use those boards, so I think it's OK.

(There are a few other patches on list which I definitely want to
get in before rc0 but they need a bit more review time I think.)

thanks
-- PMM


The following changes since commit 0ebc03bc065329eaefb6493f5fa7df08df528f2a:

  util/base64.c: Clean includes (2016-03-16 12:48:11 +0000)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20160316

for you to fetch changes up to 10b27d1ab391dbf36f92e1a33179662082401d7a:

  sd: Fix "info qtree" on boards with SD cards (2016-03-16 17:12:46 +0000)

----------------------------------------------------------------
target-arm queue:
 * loader: Fix incorrect parameter name in load_image_mr()
 * Implement MRS (banked) and MSR (banked) instructions
 * virt: Implement versioning for machine model
 * i.MX: some initial patches preparing for i.MX6 support
 * new ASPEED AST2400 SoC and palmetto-bmc machine
 * bcm2835: add some more raspi2 devices
 * sd: fix segfault running "info qtree"

----------------------------------------------------------------
Andrew Baumann (2):
      bcm2835_peripherals: enable sdhci pending-insert quirk for raspberry pi
      bcm2835_aux: add emulation of BCM2835 AUX (aka UART1) block

Andrew Jeffery (4):
      hw/timer: Add ASPEED timer device model
      hw/intc: Add (new) ASPEED VIC device model
      hw/arm: Add ASPEED AST2400 SoC model
      hw/arm: Add palmetto-bmc machine

Grégory ESTRADE (3):
      bcm2835_fb: add framebuffer device for Raspberry Pi
      bcm2835_property: implement framebuffer control/configuration properties
      bcm2835_dma: add emulation of Raspberry Pi DMA controller

Jean-Christophe Dubois (6):
      i.MX: Allow GPT timer to rollover.
      i.MX: Rename CCM NOCLK to CLK_NONE for naming consistency.
      i.MX: Remove CCM useless clock computation handling.
      i.MX: Add the CLK_IPG_HIGH clock
      i.MX: Add i.MX6 CCM and ANALOG device.
      i.MX: Add missing descriptions in devices.

Jens Wiklander (1):
      loader: Fix incorrect parameter name in load_image_mr() macro

Peter Maydell (2):
      target-arm: Implement MRS (banked) and MSR (banked) instructions
      sd: Fix "info qtree" on boards with SD cards

Sergey Sorokin (1):
      target-arm: Fix translation level on early translation faults

Wei Huang (2):
      arm: virt: Add an abstract ARM virt machine type
      arm: virt: Move machine class init code to the abstract machine type

 default-configs/arm-softmmu.mak      |   1 +
 hw/arm/Makefile.objs                 |   1 +
 hw/arm/ast2400.c                     | 137 +++++++
 hw/arm/bcm2835_peripherals.c         | 103 ++++-
 hw/arm/bcm2836.c                     |   2 +
 hw/arm/fsl-imx25.c                   |   1 +
 hw/arm/fsl-imx31.c                   |   1 +
 hw/arm/palmetto-bmc.c                |  65 +++
 hw/arm/raspi.c                       |  12 +-
 hw/arm/virt.c                        |  57 ++-
 hw/char/Makefile.objs                |   1 +
 hw/char/bcm2835_aux.c                | 316 ++++++++++++++
 hw/display/Makefile.objs             |   1 +
 hw/display/bcm2835_fb.c              | 424 +++++++++++++++++++
 hw/dma/Makefile.objs                 |   1 +
 hw/dma/bcm2835_dma.c                 | 408 ++++++++++++++++++
 hw/i2c/imx_i2c.c                     |   1 +
 hw/intc/Makefile.objs                |   1 +
 hw/intc/aspeed_vic.c                 | 339 +++++++++++++++
 hw/misc/Makefile.objs                |   1 +
 hw/misc/bcm2835_property.c           | 139 ++++++-
 hw/misc/imx25_ccm.c                  |  29 +-
 hw/misc/imx31_ccm.c                  |  35 +-
 hw/misc/imx6_ccm.c                   | 774 +++++++++++++++++++++++++++++++++++
 hw/net/imx_fec.c                     |   1 +
 hw/sd/sd.c                           |   6 +-
 hw/timer/Makefile.objs               |   1 +
 hw/timer/aspeed_timer.c              | 449 ++++++++++++++++++++
 hw/timer/imx_epit.c                  |   8 +-
 hw/timer/imx_gpt.c                   |  43 +-
 include/hw/arm/ast2400.h             |  35 ++
 include/hw/arm/bcm2835_peripherals.h |   6 +
 include/hw/char/bcm2835_aux.h        |  33 ++
 include/hw/display/bcm2835_fb.h      |  47 +++
 include/hw/dma/bcm2835_dma.h         |  47 +++
 include/hw/intc/aspeed_vic.h         |  48 +++
 include/hw/loader.h                  |   2 +-
 include/hw/misc/bcm2835_property.h   |   5 +-
 include/hw/misc/imx6_ccm.h           | 197 +++++++++
 include/hw/misc/imx_ccm.h            |  10 +-
 include/hw/timer/aspeed_timer.h      |  59 +++
 target-arm/helper.c                  |  22 +-
 target-arm/helper.h                  |   3 +
 target-arm/op_helper.c               | 120 ++++++
 target-arm/translate.c               | 246 ++++++++++-
 trace-events                         |  16 +
 46 files changed, 4114 insertions(+), 140 deletions(-)
 create mode 100644 hw/arm/ast2400.c
 create mode 100644 hw/arm/palmetto-bmc.c
 create mode 100644 hw/char/bcm2835_aux.c
 create mode 100644 hw/display/bcm2835_fb.c
 create mode 100644 hw/dma/bcm2835_dma.c
 create mode 100644 hw/intc/aspeed_vic.c
 create mode 100644 hw/misc/imx6_ccm.c
 create mode 100644 hw/timer/aspeed_timer.c
 create mode 100644 include/hw/arm/ast2400.h
 create mode 100644 include/hw/char/bcm2835_aux.h
 create mode 100644 include/hw/display/bcm2835_fb.h
 create mode 100644 include/hw/dma/bcm2835_dma.h
 create mode 100644 include/hw/intc/aspeed_vic.h
 create mode 100644 include/hw/misc/imx6_ccm.h
 create mode 100644 include/hw/timer/aspeed_timer.h

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2016-03-16 17:18 Peter Maydell
@ 2016-03-16 17:42 ` Peter Maydell
  2016-03-16 18:19 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2016-03-16 17:42 UTC (permalink / raw)
  To: QEMU Developers

On 16 March 2016 at 17:18, Peter Maydell <peter.maydell@linaro.org> wrote:
> Here's the target-arm queue; I'm a bit hesitant about the late-landing
> various new board/SoC patches, but they won't affect anybody who isn't
> trying to use those boards, so I think it's OK.
>
> (There are a few other patches on list which I definitely want to
> get in before rc0 but they need a bit more review time I think.)
>
> thanks
> -- PMM
>
>
> The following changes since commit 0ebc03bc065329eaefb6493f5fa7df08df528f2a:
>
>   util/base64.c: Clean includes (2016-03-16 12:48:11 +0000)
>
> are available in the git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20160316
>
> for you to fetch changes up to 10b27d1ab391dbf36f92e1a33179662082401d7a:
>
>   sd: Fix "info qtree" on boards with SD cards (2016-03-16 17:12:46 +0000)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * loader: Fix incorrect parameter name in load_image_mr()
>  * Implement MRS (banked) and MSR (banked) instructions
>  * virt: Implement versioning for machine model
>  * i.MX: some initial patches preparing for i.MX6 support
>  * new ASPEED AST2400 SoC and palmetto-bmc machine
>  * bcm2835: add some more raspi2 devices
>  * sd: fix segfault running "info qtree"

Some versions of gcc appear to give false positive 'may be used
uninitialized' warnings about the msr/mrs code:

/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c: In
function ‘gen_msr_banked
.isra.45’:
/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c:4321:17:
error: ‘tgtmode’ ma
y be used uninitialized in this function [-Werror=maybe-uninitialized]
     tcg_tgtmode = tcg_const_i32(tgtmode);
                 ^
/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c:4322:15:
error: ‘regno’ may be used uninitialized in this function
[-Werror=maybe-uninitialized]
     tcg_regno = tcg_const_i32(regno);
               ^
/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c: In
function ‘gen_mrs_banked.isra.48’:
/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c:4343:17:
error: ‘tgtmode’ may be used uninitialized in this function
[-Werror=maybe-uninitialized]
     tcg_tgtmode = tcg_const_i32(tgtmode);
                 ^
/home/petmay01/linaro/qemu-for-merges/target-arm/translate.c:4344:15:
error: ‘regno’ may be used uninitialized in this function
[-Werror=maybe-uninitialized]
     tcg_regno = tcg_const_i32(regno);
               ^

Fixup:
--- a/target-arm/translate.c
+++ b/target-arm/translate.c
@@ -4308,7 +4308,7 @@ undef:
 static void gen_msr_banked(DisasContext *s, int r, int sysm, int rn)
 {
     TCGv_i32 tcg_reg, tcg_tgtmode, tcg_regno;
-    int tgtmode, regno;
+    int tgtmode = 0, regno = 0;

     if (!msr_banked_access_decode(s, r, sysm, rn, &tgtmode, &regno)) {
         return;
@@ -4330,7 +4330,7 @@ static void gen_msr_banked(DisasContext *s, int
r, int sysm, int rn)
 static void gen_mrs_banked(DisasContext *s, int r, int sysm, int rn)
 {
     TCGv_i32 tcg_reg, tcg_tgtmode, tcg_regno;
-    int tgtmode, regno;
+    int tgtmode = 0, regno = 0;

     if (!msr_banked_access_decode(s, r, sysm, rn, &tgtmode, &regno)) {
         return;

which I'll squash into the appropriate patch and respin.

thanks
-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2016-03-16 17:18 Peter Maydell
  2016-03-16 17:42 ` Peter Maydell
@ 2016-03-16 18:19 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2016-03-16 18:19 UTC (permalink / raw)
  To: QEMU Developers

On 16 March 2016 at 17:18, Peter Maydell <peter.maydell@linaro.org> wrote:
> Here's the target-arm queue; I'm a bit hesitant about the late-landing
> various new board/SoC patches, but they won't affect anybody who isn't
> trying to use those boards, so I think it's OK.
>
> (There are a few other patches on list which I definitely want to
> get in before rc0 but they need a bit more review time I think.)
>
> thanks
> -- PMM
>
>
> The following changes since commit 0ebc03bc065329eaefb6493f5fa7df08df528f2a:
>
>   util/base64.c: Clean includes (2016-03-16 12:48:11 +0000)
>
> are available in the git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20160316
>
> for you to fetch changes up to 10b27d1ab391dbf36f92e1a33179662082401d7a:
>
>   sd: Fix "info qtree" on boards with SD cards (2016-03-16 17:12:46 +0000)

Respin with fix now applied to master.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2017-01-09 11:53 Peter Maydell
  2017-01-09 13:44 ` Peter Maydell
  0 siblings, 1 reply; 42+ messages in thread
From: Peter Maydell @ 2017-01-09 11:53 UTC (permalink / raw)
  To: qemu-devel

target-arm queue: nothing hugely exciting here, the
bulk is Andrew's virt-acpi-build refactorings.

thanks
-- PMM

The following changes since commit ffe22bf51065dd33022cf91f77a821d1f11c250d:

  Merge remote-tracking branch 'remotes/gonglei/tags/cryptodev-next-20161224' into staging (2017-01-06 15:18:09 +0000)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20170109

for you to fetch changes up to 556899fc1965d82f5c4a3ba6a0be3b1193e2c4b2:

  hw/ssi/imx_spi.c: Remove MSGDATA register support (2017-01-09 11:50:23 +0000)

----------------------------------------------------------------
target-arm queue:
 * i2c: Allow I2C devices to NAK start events
 * hw/char: QOM'ify exynos4210_uart.c
 * clean up and refactor virt-acpi-build.c
 * virt-acpi-build: Don't incorrectly claim architectural timer
   to be edge-triggered
 * m25p80: Don't let rogue SPI controllers cause buffer overruns
 * imx_spi: Remove broken MSGDATA register support

----------------------------------------------------------------
Andrew Jones (14):
      hw/arm/virt-acpi-build: add all missing cpu_to_le's
      hw/arm/virt-acpi-build: name GIC CPU Interface Structure appropriately
      hw/arm/virt-acpi-build: gtdt: improve flag naming
      hw/arm/virt-acpi-build: fadt: improve flag naming
      hw/arm/virt: parameter passing cleanups
      hw/arm/virt: use VirtMachineState.gic_version
      hw/arm/virt: eliminate struct VirtGuestInfoState
      hw/arm/virt: remove include/hw/arm/virt-acpi-build.h
      hw/arm/virt: move VirtMachineState/Class to virt.h
      hw/arm/virt: pass VirtMachineState instead of VirtGuestInfo
      hw/arm/virt-acpi-build: remove redundant members from VirtGuestInfo
      hw/arm/virt-acpi-build: don't save VirtGuestInfo on AcpiBuildState
      hw/arm/virt: remove VirtGuestInfo
      hw/arm/virt-acpi-build: Don't incorrectly claim architectural timer to be edge-triggered

Corey Minyard (1):
      i2c: Allow I2C devices to NAK start events

Jean-Christophe Dubois (2):
      m25p80: don't let rogue SPI controllers cause buffer overruns
      hw/ssi/imx_spi.c: Remove MSGDATA register support

Peter Maydell (3):
      hw/arm/virt: Merge VirtBoardInfo and VirtMachineState
      hw/arm/virt: Rename 'vbi' variables to 'vms'
      hw/arm/virt: Don't incorrectly claim architectural timer to be edge-triggered

xiaoqiang zhao (1):
      hw/char: QOM'ify exynos4210_uart.c

 include/hw/acpi/acpi-defs.h      |  33 +-
 include/hw/arm/virt-acpi-build.h |  47 ---
 include/hw/arm/virt.h            |  41 ++-
 include/hw/i2c/i2c.h             |  16 +-
 hw/arm/pxa2xx.c                  |   4 +-
 hw/arm/tosa.c                    |   4 +-
 hw/arm/virt-acpi-build.c         | 134 ++++----
 hw/arm/virt.c                    | 691 ++++++++++++++++++---------------------
 hw/arm/z2.c                      |   4 +-
 hw/audio/wm8750.c                |   4 +-
 hw/block/m25p80.c                |  29 +-
 hw/char/exynos4210_uart.c        |  16 +-
 hw/display/ssd0303.c             |   4 +-
 hw/gpio/max7310.c                |   4 +-
 hw/i2c/core.c                    |  31 +-
 hw/i2c/i2c-ddc.c                 |   4 +-
 hw/i2c/smbus.c                   |  13 +-
 hw/input/lm832x.c                |   4 +-
 hw/misc/tmp105.c                 |   3 +-
 hw/ssi/imx_spi.c                 |  11 +-
 hw/timer/ds1338.c                |   4 +-
 hw/timer/twl92230.c              |   4 +-
 MAINTAINERS                      |   2 -
 23 files changed, 572 insertions(+), 535 deletions(-)
 delete mode 100644 include/hw/arm/virt-acpi-build.h

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2017-01-09 11:53 Peter Maydell
@ 2017-01-09 13:44 ` Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2017-01-09 13:44 UTC (permalink / raw)
  To: QEMU Developers

On 9 January 2017 at 11:53, Peter Maydell <peter.maydell@linaro.org> wrote:
> target-arm queue: nothing hugely exciting here, the
> bulk is Andrew's virt-acpi-build refactorings.
>
> thanks
> -- PMM
>
> The following changes since commit ffe22bf51065dd33022cf91f77a821d1f11c250d:
>
>   Merge remote-tracking branch 'remotes/gonglei/tags/cryptodev-next-20161224' into staging (2017-01-06 15:18:09 +0000)
>
> are available in the git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20170109
>
> for you to fetch changes up to 556899fc1965d82f5c4a3ba6a0be3b1193e2c4b2:
>
>   hw/ssi/imx_spi.c: Remove MSGDATA register support (2017-01-09 11:50:23 +0000)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * i2c: Allow I2C devices to NAK start events
>  * hw/char: QOM'ify exynos4210_uart.c
>  * clean up and refactor virt-acpi-build.c
>  * virt-acpi-build: Don't incorrectly claim architectural timer
>    to be edge-triggered
>  * m25p80: Don't let rogue SPI controllers cause buffer overruns
>  * imx_spi: Remove broken MSGDATA register support
>
> ----------------------------------------------------------------

Applied, thanks.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2017-02-28 17:15 Peter Maydell
  2017-03-01 19:28 ` Peter Maydell
  0 siblings, 1 reply; 42+ messages in thread
From: Peter Maydell @ 2017-02-28 17:15 UTC (permalink / raw)
  To: qemu-devel

Second lot of ARM changes to sneak in before freeze:
 * fixed version of the raspi2 sd controller patches
 * GICv3 save/restore
 * v7M QOMify

I've also included the Linux header update patches stolen
from Paolo's pullreq since it hasn't quite hit master yet.

thanks
-- PMM

The following changes since commit 1bbe5dc66b770d7bedd1d51d7935da948a510dd6:

  Merge remote-tracking branch 'remotes/pmaydell/tags/pull-target-arm-20170228' into staging (2017-02-28 14:50:17 +0000)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20170228-1

for you to fetch changes up to 1eeb5c7deacbfb4d4cad17590a16a99f3d85eabb:

  bcm2835: add sdhost and gpio controllers (2017-02-28 17:10:00 +0000)

----------------------------------------------------------------
target-arm queue:
 * raspi2: add gpio controller and sdhost controller, with
   the wiring so the guest can switch which controller the
   SD card is attached to
   (this is sufficient to get raspbian kernels to boot)
 * GICv3: support state save/restore from KVM
 * update Linux headers to 4.11
 * refactor and QOMify the ARMv7M container object

----------------------------------------------------------------
Clement Deschamps (3):
      hw/sd: add card-reparenting function
      bcm2835_gpio: add bcm2835 gpio controller
      bcm2835: add sdhost and gpio controllers

Paolo Bonzini (2):
      update-linux-headers: update for 4.11
      update Linux headers to 4.11

Peter Maydell (12):
      armv7m: Abstract out the "load kernel" code
      armv7m: Move NVICState struct definition into header
      armv7m: QOMify the armv7m container
      armv7m: Use QOMified armv7m object in armv7m_init()
      armv7m: Make ARMv7M object take memory region link
      armv7m: Make NVIC expose a memory region rather than mapping itself
      armv7m: Make bitband device take the address space to access
      armv7m: Don't put core v7M devices under CONFIG_STELLARIS
      armv7m: Split systick out from NVIC
      stm32f205: Create armv7m object without using armv7m_init()
      stm32f205: Rename 'nvic' local to 'armv7m'
      qdev: Have qdev_set_parent_bus() handle devices already on a bus

Vijaya Kumar K (4):
      hw/intc/arm_gicv3_kvm: Add ICC_SRE_EL1 register to vmstate
      hw/intc/arm_gicv3_kvm: Implement get/put functions
      target-arm: Add GICv3CPUState in CPUARMState struct
      hw/intc/arm_gicv3_kvm: Reset GICv3 cpu interface registers

 hw/gpio/Makefile.objs                              |   1 +
 hw/intc/Makefile.objs                              |   2 +-
 hw/timer/Makefile.objs                             |   1 +
 hw/intc/gicv3_internal.h                           |   3 +
 include/hw/arm/arm.h                               |  12 +
 include/hw/arm/armv7m.h                            |  63 +++
 include/hw/arm/armv7m_nvic.h                       |  62 ++
 include/hw/arm/bcm2835_peripherals.h               |   4 +
 include/hw/arm/stm32f205_soc.h                     |   4 +-
 include/hw/gpio/bcm2835_gpio.h                     |  39 ++
 include/hw/intc/arm_gicv3_common.h                 |   1 +
 include/hw/sd/sd.h                                 |  11 +
 include/hw/timer/armv7m_systick.h                  |  34 ++
 include/standard-headers/asm-x86/hyperv.h          |   8 +
 include/standard-headers/linux/input-event-codes.h |   2 +-
 include/standard-headers/linux/pci_regs.h          |  25 +
 include/standard-headers/linux/virtio_ids.h        |   1 +
 linux-headers/asm-arm/kvm.h                        |  15 +
 linux-headers/asm-arm/unistd-common.h              | 357 ++++++++++++
 linux-headers/asm-arm/unistd-eabi.h                |   5 +
 linux-headers/asm-arm/unistd-oabi.h                |  17 +
 linux-headers/asm-arm/unistd.h                     | 419 +-------------
 linux-headers/asm-arm64/kvm.h                      |  13 +
 linux-headers/asm-powerpc/kvm.h                    |  27 +
 linux-headers/asm-powerpc/unistd.h                 |   1 +
 linux-headers/asm-x86/kvm_para.h                   |  13 +-
 linux-headers/linux/kvm.h                          |  24 +-
 linux-headers/linux/kvm_para.h                     |   2 +
 linux-headers/linux/userfaultfd.h                  |  67 ++-
 linux-headers/linux/vfio.h                         |  10 +
 target/arm/cpu.h                                   |   2 +
 hw/arm/armv7m.c                                    | 379 ++++++++-----
 hw/arm/bcm2835_peripherals.c                       |  43 +-
 hw/arm/netduino2.c                                 |   7 +-
 hw/arm/stm32f205_soc.c                             |  28 +-
 hw/core/qdev.c                                     |  14 +
 hw/gpio/bcm2835_gpio.c                             | 353 ++++++++++++
 hw/intc/arm_gicv3_common.c                         |  38 ++
 hw/intc/arm_gicv3_cpuif.c                          |   8 +
 hw/intc/arm_gicv3_kvm.c                            | 629 ++++++++++++++++++++-
 hw/intc/armv7m_nvic.c                              | 214 ++-----
 hw/sd/core.c                                       |  27 +
 hw/timer/armv7m_systick.c                          | 240 ++++++++
 default-configs/arm-softmmu.mak                    |   2 +
 hw/timer/trace-events                              |   6 +
 scripts/update-linux-headers.sh                    |  13 +-
 46 files changed, 2479 insertions(+), 767 deletions(-)
 create mode 100644 include/hw/arm/armv7m.h
 create mode 100644 include/hw/arm/armv7m_nvic.h
 create mode 100644 include/hw/gpio/bcm2835_gpio.h
 create mode 100644 include/hw/timer/armv7m_systick.h
 create mode 100644 linux-headers/asm-arm/unistd-common.h
 create mode 100644 linux-headers/asm-arm/unistd-eabi.h
 create mode 100644 linux-headers/asm-arm/unistd-oabi.h
 create mode 100644 hw/gpio/bcm2835_gpio.c
 create mode 100644 hw/timer/armv7m_systick.c

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2017-02-28 17:15 Peter Maydell
@ 2017-03-01 19:28 ` Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2017-03-01 19:28 UTC (permalink / raw)
  To: QEMU Developers

On 28 February 2017 at 17:15, Peter Maydell <peter.maydell@linaro.org> wrote:
> Second lot of ARM changes to sneak in before freeze:
>  * fixed version of the raspi2 sd controller patches
>  * GICv3 save/restore
>  * v7M QOMify
>
> I've also included the Linux header update patches stolen
> from Paolo's pullreq since it hasn't quite hit master yet.
>
> thanks
> -- PMM
>
> The following changes since commit 1bbe5dc66b770d7bedd1d51d7935da948a510dd6:
>
>   Merge remote-tracking branch 'remotes/pmaydell/tags/pull-target-arm-20170228' into staging (2017-02-28 14:50:17 +0000)
>
> are available in the git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20170228-1
>
> for you to fetch changes up to 1eeb5c7deacbfb4d4cad17590a16a99f3d85eabb:
>
>   bcm2835: add sdhost and gpio controllers (2017-02-28 17:10:00 +0000)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * raspi2: add gpio controller and sdhost controller, with
>    the wiring so the guest can switch which controller the
>    SD card is attached to
>    (this is sufficient to get raspbian kernels to boot)
>  * GICv3: support state save/restore from KVM
>  * update Linux headers to 4.11
>  * refactor and QOMify the ARMv7M container object

Applied, thanks.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2018-01-25 13:43 Peter Maydell
  2018-01-25 14:18 ` no-reply
  2018-01-25 18:06 ` Peter Maydell
  0 siblings, 2 replies; 42+ messages in thread
From: Peter Maydell @ 2018-01-25 13:43 UTC (permalink / raw)
  To: qemu-devel


Arm queue built up to a point where it seems worth sending:
various bug fixes, plus RTH's refactoring in preparation for SVE.

thanks
-- PMM
 
 
The following changes since commit 0f79bfe38a2cf0f43c7ea4959da7f8ebd7858f3d:

  Merge remote-tracking branch 'remotes/vivier2/tags/linux-user-for-2.12-pull-request' into staging (2018-01-25 09:53:53 +0000)

are available in the git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180125

for you to fetch changes up to 24da047af0e99a83fcc0d50b86c0f2627f7418b3:

  pl110: Implement vertical compare/next base interrupts (2018-01-25 11:45:30 +0000)

----------------------------------------------------------------
target-arm queue:
 * target/arm: Fix address truncation in 64-bit pagetable walks
 * i.MX: Fix FEC/ENET receive functions
 * target/arm: preparatory refactoring for SVE emulation
 * hw/intc/arm_gic: Prevent the GIC from signaling an IRQ when it's "active and pending"
 * hw/intc/arm_gic: Fix C_RPR value on idle priority
 * hw/intc/arm_gic: Fix group priority computation for group 1 IRQs
 * hw/intc/arm_gic: Fix the NS view of C_BPR when C_CTRL.CBPR is 1
 * hw/arm/virt: Check that the CPU realize method succeeded
 * sdhci: fix a NULL pointer dereference due to uninitialized AddressSpace object
 * xilinx_spips: Correct usage of an uninitialized local variable
 * pl110: Implement vertical compare/next base interrupts

----------------------------------------------------------------
Ard Biesheuvel (1):
      target/arm: Fix 32-bit address truncation

Francisco Iglesias (1):
      xilinx_spips: Correct usage of an uninitialized local variable

Jean-Christophe Dubois (1):
      i.MX: Fix FEC/ENET receive funtions

Linus Walleij (1):
      pl110: Implement vertical compare/next base interrupts

Luc MICHEL (4):
      hw/intc/arm_gic: Prevent the GIC from signaling an IRQ when it's "active and pending"
      hw/intc/arm_gic: Fix C_RPR value on idle priority
      hw/intc/arm_gic: Fix group priority computation for group 1 IRQs
      hw/intc/arm_gic: Fix the NS view of C_BPR when C_CTRL.CBPR is 1

Peter Maydell (1):
      hw/arm/virt: Check that the CPU realize method succeeded

Philippe Mathieu-Daudé (1):
      sdhci: fix a NULL pointer dereference due to uninitialized AddresSpace object

Richard Henderson (11):
      target/arm: Mark disas_set_insn_syndrome inline
      target/arm: Use pointers in crypto helpers
      target/arm: Use pointers in neon zip/uzp helpers
      target/arm: Use pointers in neon tbl helper
      target/arm: Change the type of vfp.regs
      target/arm: Add aa{32, 64}_vfp_{dreg, qreg} helpers
      vmstate: Add VMSTATE_UINT64_SUB_ARRAY
      target/arm: Add ARM_FEATURE_SVE
      target/arm: Move cpu_get_tb_cpu_state out of line
      target/arm: Hoist store to flags output in cpu_get_tb_cpu_state
      target/arm: Simplify fp_exception_el for user-only

 include/hw/sd/sdhci.h       |   1 +
 include/migration/vmstate.h |   9 ++-
 target/arm/cpu.h            | 157 ++++++++-----------------------------
 target/arm/helper.h         |  46 +++++------
 target/arm/translate.h      |   2 +-
 hw/arm/virt.c               |   2 +-
 hw/display/pl110.c          |  30 +++++++-
 hw/intc/arm_gic.c           |  25 +++++-
 hw/net/imx_fec.c            |   8 +-
 hw/sd/sdhci.c               |   1 +
 hw/ssi/xilinx_spips.c       |  18 ++++-
 linux-user/signal.c         |  22 +++---
 target/arm/arch_dump.c      |   8 +-
 target/arm/crypto_helper.c  | 184 +++++++++++++++++---------------------------
 target/arm/helper-a64.c     |   5 +-
 target/arm/helper.c         | 164 +++++++++++++++++++++++++++++++++++----
 target/arm/kvm32.c          |   4 +-
 target/arm/kvm64.c          |  31 +++-----
 target/arm/machine.c        |   2 +-
 target/arm/neon_helper.c    | 162 ++++++++++++++++++++------------------
 target/arm/op_helper.c      |  17 ++--
 target/arm/translate-a64.c  | 100 ++++++++++++------------
 target/arm/translate.c      | 134 +++++++++++++++++---------------
 23 files changed, 607 insertions(+), 525 deletions(-)

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2018-01-25 13:43 Peter Maydell
@ 2018-01-25 14:18 ` no-reply
  2018-01-25 18:06 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: no-reply @ 2018-01-25 14:18 UTC (permalink / raw)
  To: peter.maydell; +Cc: famz, qemu-devel

Hi,

This series seems to have some coding style problems. See output below for
more information:

Type: series
Message-id: 1516887809-6265-1-git-send-email-peter.maydell@linaro.org
Subject: [Qemu-devel] [PULL 00/21] target-arm queue

=== TEST SCRIPT BEGIN ===
#!/bin/bash

BASE=base
n=1
total=$(git log --oneline $BASE.. | wc -l)
failed=0

git config --local diff.renamelimit 0
git config --local diff.renames True

commits="$(git log --format=%H --reverse $BASE..)"
for c in $commits; do
    echo "Checking PATCH $n/$total: $(git log -n 1 --format=%s $c)..."
    if ! git show $c --format=email | ./scripts/checkpatch.pl --mailback -; then
        failed=1
        echo
    fi
    n=$((n+1))
done

exit $failed
=== TEST SCRIPT END ===

Updating 3c8cf5a9c21ff8782164d1def7f44bd888713384
From https://github.com/patchew-project/qemu
 * [new tag]               patchew/1516887809-6265-1-git-send-email-peter.maydell@linaro.org -> patchew/1516887809-6265-1-git-send-email-peter.maydell@linaro.org
Switched to a new branch 'test'
a7ead1ca00 pl110: Implement vertical compare/next base interrupts
f66ce5c2c3 xilinx_spips: Correct usage of an uninitialized local variable
d88421481d sdhci: fix a NULL pointer dereference due to uninitialized AddresSpace object
7564bd6dfb hw/arm/virt: Check that the CPU realize method succeeded
18db7a35b4 hw/intc/arm_gic: Fix the NS view of C_BPR when C_CTRL.CBPR is 1
157a918a47 hw/intc/arm_gic: Fix group priority computation for group 1 IRQs
a896e5197e hw/intc/arm_gic: Fix C_RPR value on idle priority
ed702de6c2 hw/intc/arm_gic: Prevent the GIC from signaling an IRQ when it's "active and pending"
0c5df69251 target/arm: Simplify fp_exception_el for user-only
0901e742d2 target/arm: Hoist store to flags output in cpu_get_tb_cpu_state
30d076c766 target/arm: Move cpu_get_tb_cpu_state out of line
9bc4918ade target/arm: Add ARM_FEATURE_SVE
9afce6e002 vmstate: Add VMSTATE_UINT64_SUB_ARRAY
911f6046fd target/arm: Add aa{32, 64}_vfp_{dreg, qreg} helpers
768420eeb2 target/arm: Change the type of vfp.regs
d2beafabf0 target/arm: Use pointers in neon tbl helper
e00821354c target/arm: Use pointers in neon zip/uzp helpers
ac24cb1f18 target/arm: Use pointers in crypto helpers
df207ebf53 target/arm: Mark disas_set_insn_syndrome inline
a13bffeacc i.MX: Fix FEC/ENET receive funtions
cc82dfe8c8 target/arm: Fix 32-bit address truncation

=== OUTPUT BEGIN ===
Checking PATCH 1/21: target/arm: Fix 32-bit address truncation...
Checking PATCH 2/21: i.MX: Fix FEC/ENET receive funtions...
Checking PATCH 3/21: target/arm: Mark disas_set_insn_syndrome inline...
Checking PATCH 4/21: target/arm: Use pointers in crypto helpers...
Checking PATCH 5/21: target/arm: Use pointers in neon zip/uzp helpers...
ERROR: trailing whitespace
#321: FILE: target/arm/translate.c:4691:
+    $

total: 1 errors, 0 warnings, 373 lines checked

Your patch has style problems, please review.  If any of these errors
are false positives report them to the maintainer, see
CHECKPATCH in MAINTAINERS.

Checking PATCH 6/21: target/arm: Use pointers in neon tbl helper...
Checking PATCH 7/21: target/arm: Change the type of vfp.regs...
Checking PATCH 8/21: target/arm: Add aa{32, 64}_vfp_{dreg, qreg} helpers...
ERROR: spaces required around that '*' (ctx:VxV)
#88: FILE: target/arm/arch_dump.c:104:
+        note.vfp.vregs[2*i + 0] = cpu_to_dump64(s, q[0]);
                         ^

ERROR: spaces required around that '*' (ctx:VxV)
#89: FILE: target/arm/arch_dump.c:105:
+        note.vfp.vregs[2*i + 1] = cpu_to_dump64(s, q[1]);
                         ^

total: 2 errors, 0 warnings, 327 lines checked

Your patch has style problems, please review.  If any of these errors
are false positives report them to the maintainer, see
CHECKPATCH in MAINTAINERS.

Checking PATCH 9/21: vmstate: Add VMSTATE_UINT64_SUB_ARRAY...
Checking PATCH 10/21: target/arm: Add ARM_FEATURE_SVE...
Checking PATCH 11/21: target/arm: Move cpu_get_tb_cpu_state out of line...
Checking PATCH 12/21: target/arm: Hoist store to flags output in cpu_get_tb_cpu_state...
Checking PATCH 13/21: target/arm: Simplify fp_exception_el for user-only...
Checking PATCH 14/21: hw/intc/arm_gic: Prevent the GIC from signaling an IRQ when it's "active and pending"...
Checking PATCH 15/21: hw/intc/arm_gic: Fix C_RPR value on idle priority...
Checking PATCH 16/21: hw/intc/arm_gic: Fix group priority computation for group 1 IRQs...
Checking PATCH 17/21: hw/intc/arm_gic: Fix the NS view of C_BPR when C_CTRL.CBPR is 1...
Checking PATCH 18/21: hw/arm/virt: Check that the CPU realize method succeeded...
Checking PATCH 19/21: sdhci: fix a NULL pointer dereference due to uninitialized AddresSpace object...
Checking PATCH 20/21: xilinx_spips: Correct usage of an uninitialized local variable...
Checking PATCH 21/21: pl110: Implement vertical compare/next base interrupts...
=== OUTPUT END ===

Test command exited with code: 1


---
Email generated automatically by Patchew [http://patchew.org/].
Please send your feedback to patchew-devel@freelists.org

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2018-01-25 13:43 Peter Maydell
  2018-01-25 14:18 ` no-reply
@ 2018-01-25 18:06 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2018-01-25 18:06 UTC (permalink / raw)
  To: QEMU Developers

On 25 January 2018 at 13:43, Peter Maydell <peter.maydell@linaro.org> wrote:
>
> Arm queue built up to a point where it seems worth sending:
> various bug fixes, plus RTH's refactoring in preparation for SVE.
>
> thanks
> -- PMM
>
>
> The following changes since commit 0f79bfe38a2cf0f43c7ea4959da7f8ebd7858f3d:
>
>   Merge remote-tracking branch 'remotes/vivier2/tags/linux-user-for-2.12-pull-request' into staging (2018-01-25 09:53:53 +0000)
>
> are available in the git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180125
>
> for you to fetch changes up to 24da047af0e99a83fcc0d50b86c0f2627f7418b3:
>
>   pl110: Implement vertical compare/next base interrupts (2018-01-25 11:45:30 +0000)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * target/arm: Fix address truncation in 64-bit pagetable walks
>  * i.MX: Fix FEC/ENET receive functions
>  * target/arm: preparatory refactoring for SVE emulation
>  * hw/intc/arm_gic: Prevent the GIC from signaling an IRQ when it's "active and pending"
>  * hw/intc/arm_gic: Fix C_RPR value on idle priority
>  * hw/intc/arm_gic: Fix group priority computation for group 1 IRQs
>  * hw/intc/arm_gic: Fix the NS view of C_BPR when C_CTRL.CBPR is 1
>  * hw/arm/virt: Check that the CPU realize method succeeded
>  * sdhci: fix a NULL pointer dereference due to uninitialized AddressSpace object
>  * xilinx_spips: Correct usage of an uninitialized local variable
>  * pl110: Implement vertical compare/next base interrupts
>

Applied, thanks.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2018-02-15 13:56 Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2018-02-15 13:56 UTC (permalink / raw)
  To: qemu-devel

target-arm queue: mostly just cleanup/minor stuff, but this does
include the raspi3 board model.

-- PMM

The following changes since commit 9f9c53368b219a9115eddb39f0ff5ad19c977134:

  Merge remote-tracking branch 'remotes/vivier/tags/m68k-for-2.12-pull-request' into staging (2018-02-15 10:14:11 +0000)

are available in the Git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180215

for you to fetch changes up to e545f0f9be1f9e60951017c1e6558216732cc14e:

  target/arm: Implement v8M MSPLIM and PSPLIM registers (2018-02-15 13:48:11 +0000)

----------------------------------------------------------------
target-arm queue:
 * aspeed: code cleanup to use unimplemented_device
 * add 'raspi3' RaspberryPi 3 machine model
 * more SVE prep work
 * v8M: add minor missing registers
 * v7M: fix bug where we weren't migrating v7m.other_sp
 * v7M: fix bugs in handling of interrupt registers for
   external interrupts beyond 32

----------------------------------------------------------------
Pekka Enberg (3):
      bcm2836: Make CPU type configurable
      raspi: Raspberry Pi 3 support
      raspi: Add "raspi3" machine type

Peter Maydell (11):
      hw/intc/armv7m_nvic: Don't hardcode M profile ID registers in NVIC
      hw/intc/armv7m_nvic: Fix ICSR PENDNMISET/CLR handling
      hw/intc/armv7m_nvic: Implement M profile cache maintenance ops
      hw/intc/armv7m_nvic: Implement v8M CPPWR register
      hw/intc/armv7m_nvic: Implement cache ID registers
      hw/intc/armv7m_nvic: Implement SCR
      target/arm: Implement writing to CONTROL_NS for v8M
      hw/intc/armv7m_nvic: Fix byte-to-interrupt number conversions
      target/arm: Add AIRCR to vmstate struct
      target/arm: Migrate v7m.other_sp
      target/arm: Implement v8M MSPLIM and PSPLIM registers

Philippe Mathieu-Daudé (2):
      hw/arm/aspeed: directly map the serial device to the system address space
      hw/arm/aspeed: simplify using the 'unimplemented device' for aspeed_soc.io

Richard Henderson (5):
      target/arm: Remove ARM_CP_64BIT from ZCR_EL registers
      target/arm: Enforce FP access to FPCR/FPSR
      target/arm: Suppress TB end for FPCR/FPSR
      target/arm: Enforce access to ZCR_EL at translation
      target/arm: Handle SVE registers when using clear_vec_high

 include/hw/arm/aspeed_soc.h |   1 -
 include/hw/arm/bcm2836.h    |   1 +
 target/arm/cpu.h            |  71 ++++++++++++-----
 target/arm/internals.h      |   6 ++
 hw/arm/aspeed_soc.c         |  35 ++-------
 hw/arm/bcm2836.c            |  17 +++--
 hw/arm/raspi.c              |  57 +++++++++++---
 hw/intc/armv7m_nvic.c       |  98 ++++++++++++++++++------
 target/arm/cpu.c            |  28 +++++++
 target/arm/helper.c         |  84 +++++++++++++++-----
 target/arm/machine.c        |  84 ++++++++++++++++++++
 target/arm/translate-a64.c  | 181 ++++++++++++++++++++------------------------
 12 files changed, 452 insertions(+), 211 deletions(-)

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2018-05-10 17:44 Peter Maydell
  2018-05-10 18:06 ` no-reply
  2018-05-14  8:46 ` Peter Maydell
  0 siblings, 2 replies; 42+ messages in thread
From: Peter Maydell @ 2018-05-10 17:44 UTC (permalink / raw)
  To: qemu-devel

The following changes since commit e5cd695266c5709308aa95b1baae499e4b5d4544:

  Merge remote-tracking branch 'remotes/cody/tags/block-pull-request' into staging (2018-05-08 17:05:58 +0100)

are available in the Git repository at:

  git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180510

for you to fetch changes up to 9a9f1f59521f46e8ff4527d9a2b52f83577e2aa3:

  target/arm: Clear SVE high bits for FMOV (2018-05-10 18:10:58 +0100)

----------------------------------------------------------------
target-arm queue:
 * hw/arm/iotkit.c: fix minor memory leak
 * softfloat: fix wrong-exception-flags bug for multiply-add corner case
 * arm: isolate and clean up DTB generation
 * implement Arm v8.1-Atomics extension
 * Fix some bugs and missing instructions in the v8.2-FP16 extension

----------------------------------------------------------------
Igor Mammedov (4):
      pc: simplify MachineClass::get_hotplug_handler handling
      platform-bus-device: use device plug callback instead of machine_done notifier
      arm/boot: split load_dtb() from arm_load_kernel()
      make sure that we aren't overwriting mc->get_hotplug_handler by accident

Peter Maydell (3):
      hw/arm/iotkit.c: fix minor memory leak
      softfloat: Handle default NaN mode after pickNaNMulAdd, not before
      atomic.h: Work around gcc spurious "unused value" warning

Richard Henderson (14):
      tcg: Introduce helpers for integer min/max
      target/arm: Use new min/max expanders
      target/xtensa: Use new min/max expanders
      tcg: Introduce atomic helpers for integer min/max
      tcg: Use GEN_ATOMIC_HELPER_FN for opposite endian atomic add
      target/riscv: Use new atomic min/max expanders
      target/arm: Introduce ARM_FEATURE_V8_ATOMICS and initial decode
      target/arm: Fill in disas_ldst_atomic
      target/arm: Implement CAS and CASP
      target/arm: Enable ARM_FEATURE_V8_ATOMICS for user-only
      target/arm: Implement vector shifted SCVF/UCVF for fp16
      target/arm: Implement vector shifted FCVT for fp16
      target/arm: Fix float16 to/from int16
      target/arm: Clear SVE high bits for FMOV

 accel/tcg/atomic_template.h | 112 ++++++----
 accel/tcg/tcg-runtime.h     |   8 +
 hw/ppc/e500.h               |   5 +
 include/hw/arm/arm.h        |  45 +++-
 include/hw/arm/sysbus-fdt.h |  37 +---
 include/hw/arm/virt.h       |   1 +
 include/hw/i386/pc.h        |   8 -
 include/hw/platform-bus.h   |   4 +-
 include/qemu/atomic.h       |   2 +-
 target/arm/cpu.h            |   1 +
 target/arm/helper-a64.h     |   2 +
 target/arm/helper.h         |   4 +-
 tcg/tcg-op.h                |  50 +++++
 tcg/tcg.h                   |   8 +
 fpu/softfloat.c             |  52 +++--
 hw/arm/boot.c               |  72 ++-----
 hw/arm/iotkit.c             |   1 +
 hw/arm/sysbus-fdt.c         |  64 +-----
 hw/arm/virt.c               |  96 ++++++---
 hw/core/platform-bus.c      |  29 +--
 hw/i386/pc.c                |   7 +-
 hw/ppc/e500.c               |  38 ++--
 hw/ppc/e500plat.c           |  32 +++
 hw/ppc/spapr.c              |   1 +
 hw/s390x/s390-virtio-ccw.c  |   1 +
 linux-user/elfload.c        |   1 +
 target/arm/cpu64.c          |   1 +
 target/arm/helper-a64.c     |  43 ++++
 target/arm/helper.c         |  53 ++++-
 target/arm/translate-a64.c  | 490 +++++++++++++++++++++++++++++++++-----------
 target/riscv/translate.c    |  72 ++-----
 target/xtensa/translate.c   |  50 +++--
 tcg/tcg-op.c                |  48 +++++
 33 files changed, 934 insertions(+), 504 deletions(-)

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2018-05-10 17:44 Peter Maydell
@ 2018-05-10 18:06 ` no-reply
  2018-05-14  8:46 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: no-reply @ 2018-05-10 18:06 UTC (permalink / raw)
  To: peter.maydell; +Cc: famz, qemu-devel

Hi,

This series seems to have some coding style problems. See output below for
more information:

Type: series
Message-id: 20180510174519.11264-1-peter.maydell@linaro.org
Subject: [Qemu-devel] [PULL 00/21] target-arm queue

=== TEST SCRIPT BEGIN ===
#!/bin/bash

BASE=base
n=1
total=$(git log --oneline $BASE.. | wc -l)
failed=0

git config --local diff.renamelimit 0
git config --local diff.renames True
git config --local diff.algorithm histogram

commits="$(git log --format=%H --reverse $BASE..)"
for c in $commits; do
    echo "Checking PATCH $n/$total: $(git log -n 1 --format=%s $c)..."
    if ! git show $c --format=email | ./scripts/checkpatch.pl --mailback -; then
        failed=1
        echo
    fi
    n=$((n+1))
done

exit $failed
=== TEST SCRIPT END ===

Updating 3c8cf5a9c21ff8782164d1def7f44bd888713384
From https://github.com/patchew-project/qemu
 t [tag update]            patchew/20180502221552.3873-1-richard.henderson@linaro.org -> patchew/20180502221552.3873-1-richard.henderson@linaro.org
 t [tag update]            patchew/20180503115620.10596-1-edgar.iglesias@gmail.com -> patchew/20180503115620.10596-1-edgar.iglesias@gmail.com
 t [tag update]            patchew/20180509165530.29561-1-mreitz@redhat.com -> patchew/20180509165530.29561-1-mreitz@redhat.com
 t [tag update]            patchew/20180510094206.15354-1-alex.bennee@linaro.org -> patchew/20180510094206.15354-1-alex.bennee@linaro.org
 t [tag update]            patchew/20180510140141.12120-1-peter.maydell@linaro.org -> patchew/20180510140141.12120-1-peter.maydell@linaro.org
 t [tag update]            patchew/20180510140934.22855-1-peter.maydell@linaro.org -> patchew/20180510140934.22855-1-peter.maydell@linaro.org
 t [tag update]            patchew/20180510143618.23673-1-peter.maydell@linaro.org -> patchew/20180510143618.23673-1-peter.maydell@linaro.org
 * [new tag]               patchew/20180510174519.11264-1-peter.maydell@linaro.org -> patchew/20180510174519.11264-1-peter.maydell@linaro.org
Auto packing the repository in background for optimum performance.
See "git help gc" for manual housekeeping.
Switched to a new branch 'test'
ccdba81c4b target/arm: Clear SVE high bits for FMOV
64003f64f0 target/arm: Fix float16 to/from int16
600be1201a target/arm: Implement vector shifted FCVT for fp16
0f941356c9 target/arm: Implement vector shifted SCVF/UCVF for fp16
3ded533d22 target/arm: Enable ARM_FEATURE_V8_ATOMICS for user-only
9d58b9b45c target/arm: Implement CAS and CASP
51a26a9014 target/arm: Fill in disas_ldst_atomic
de4ccb142c target/arm: Introduce ARM_FEATURE_V8_ATOMICS and initial decode
3b7e02239c target/riscv: Use new atomic min/max expanders
d8820204cf tcg: Use GEN_ATOMIC_HELPER_FN for opposite endian atomic add
587522510f tcg: Introduce atomic helpers for integer min/max
adbe86c2cb target/xtensa: Use new min/max expanders
9f9ed0f8b4 target/arm: Use new min/max expanders
0386c2a4f5 tcg: Introduce helpers for integer min/max
7a13cbc1df atomic.h: Work around gcc spurious "unused value" warning
704fd2643a make sure that we aren't overwriting mc->get_hotplug_handler by accident
e35977cfc3 arm/boot: split load_dtb() from arm_load_kernel()
b46a5f4740 platform-bus-device: use device plug callback instead of machine_done notifier
318eae8151 pc: simplify MachineClass::get_hotplug_handler handling
d99828cef6 softfloat: Handle default NaN mode after pickNaNMulAdd, not before
058260b178 hw/arm/iotkit.c: fix minor memory leak

=== OUTPUT BEGIN ===
Checking PATCH 1/21: hw/arm/iotkit.c: fix minor memory leak...
Checking PATCH 2/21: softfloat: Handle default NaN mode after pickNaNMulAdd, not before...
Checking PATCH 3/21: pc: simplify MachineClass::get_hotplug_handler handling...
Checking PATCH 4/21: platform-bus-device: use device plug callback instead of machine_done notifier...
Checking PATCH 5/21: arm/boot: split load_dtb() from arm_load_kernel()...
Checking PATCH 6/21: make sure that we aren't overwriting mc->get_hotplug_handler by accident...
Checking PATCH 7/21: atomic.h: Work around gcc spurious "unused value" warning...
Checking PATCH 8/21: tcg: Introduce helpers for integer min/max...
Checking PATCH 9/21: target/arm: Use new min/max expanders...
Checking PATCH 10/21: target/xtensa: Use new min/max expanders...
Checking PATCH 11/21: tcg: Introduce atomic helpers for integer min/max...
ERROR: memory barrier without comment
#58: FILE: accel/tcg/atomic_template.h:137:
+    smp_mb();                                                       \

ERROR: memory barrier without comment
#98: FILE: accel/tcg/atomic_template.h:285:
+    smp_mb();                                                       \

total: 2 errors, 0 warnings, 236 lines checked

Your patch has style problems, please review.  If any of these errors
are false positives report them to the maintainer, see
CHECKPATCH in MAINTAINERS.

Checking PATCH 12/21: tcg: Use GEN_ATOMIC_HELPER_FN for opposite endian atomic add...
Checking PATCH 13/21: target/riscv: Use new atomic min/max expanders...
Checking PATCH 14/21: target/arm: Introduce ARM_FEATURE_V8_ATOMICS and initial decode...
Checking PATCH 15/21: target/arm: Fill in disas_ldst_atomic...
Checking PATCH 16/21: target/arm: Implement CAS and CASP...
Checking PATCH 17/21: target/arm: Enable ARM_FEATURE_V8_ATOMICS for user-only...
Checking PATCH 18/21: target/arm: Implement vector shifted SCVF/UCVF for fp16...
Checking PATCH 19/21: target/arm: Implement vector shifted FCVT for fp16...
Checking PATCH 20/21: target/arm: Fix float16 to/from int16...
ERROR: spaces required around that '*' (ctx:WxV)
#47: FILE: target/arm/helper.c:11434:
+static float16 do_postscale_fp16(float64 f, int shift, float_status *fpst)
                                                                     ^

total: 1 errors, 0 warnings, 83 lines checked

Your patch has style problems, please review.  If any of these errors
are false positives report them to the maintainer, see
CHECKPATCH in MAINTAINERS.

Checking PATCH 21/21: target/arm: Clear SVE high bits for FMOV...
=== OUTPUT END ===

Test command exited with code: 1


---
Email generated automatically by Patchew [http://patchew.org/].
Please send your feedback to patchew-devel@redhat.com

^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2018-05-10 17:44 Peter Maydell
  2018-05-10 18:06 ` no-reply
@ 2018-05-14  8:46 ` Peter Maydell
  1 sibling, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2018-05-14  8:46 UTC (permalink / raw)
  To: QEMU Developers

On 10 May 2018 at 18:44, Peter Maydell <peter.maydell@linaro.org> wrote:
> The following changes since commit e5cd695266c5709308aa95b1baae499e4b5d4544:
>
>   Merge remote-tracking branch 'remotes/cody/tags/block-pull-request' into staging (2018-05-08 17:05:58 +0100)
>
> are available in the Git repository at:
>
>   git://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20180510
>
> for you to fetch changes up to 9a9f1f59521f46e8ff4527d9a2b52f83577e2aa3:
>
>   target/arm: Clear SVE high bits for FMOV (2018-05-10 18:10:58 +0100)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * hw/arm/iotkit.c: fix minor memory leak
>  * softfloat: fix wrong-exception-flags bug for multiply-add corner case
>  * arm: isolate and clean up DTB generation
>  * implement Arm v8.1-Atomics extension
>  * Fix some bugs and missing instructions in the v8.2-FP16 extension
>

Applied, thanks.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2019-02-21 18:57 Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 01/21] hw/arm/armsse: Fix memory leak in error-exit path Peter Maydell
                   ` (21 more replies)
  0 siblings, 22 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Arm queue -- mostly the first slice of my Musca patches.

thanks
-- PMM

The following changes since commit fc3dbb90f2eb069801bfb4cfe9cbc83cf9c5f4a9:

  Merge remote-tracking branch 'remotes/jnsnow/tags/bitmaps-pull-request' into staging (2019-02-21 13:09:33 +0000)

are available in the Git repository at:

  https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20190221

for you to fetch changes up to 3733f80308d2a7f23f5e39b039e0547aba6c07f1:

  hw/arm/armsse: Make 0x5... alias region work for per-CPU devices (2019-02-21 18:17:48 +0000)

----------------------------------------------------------------
target-arm queue:
 * Model the Arm "Musca" development boards: "musca-a" and "musca-b1"
 * Implement the ARMv8.3-JSConv extension
 * v8M MPU should use background region as default, not always
 * Stop unintentional sign extension in pmu_init

----------------------------------------------------------------
Aaron Lindsay OS (1):
      target/arm: Stop unintentional sign extension in pmu_init

Peter Maydell (16):
      hw/arm/armsse: Fix memory leak in error-exit path
      target/arm: v8M MPU should use background region as default, not always
      hw/misc/tz-ppc: Support having unused ports in the middle of the range
      hw/timer/pl031: Allow use as an embedded-struct device
      hw/timer/pl031: Convert to using trace events
      hw/char/pl011: Allow use as an embedded-struct device
      hw/char/pl011: Support all interrupt lines
      hw/char/pl011: Use '0x' prefix when logging hex numbers
      hw/arm/armsse: Document SRAM_ADDR_WIDTH property in header comment
      hw/arm/armsse: Allow boards to specify init-svtor
      hw/arm/musca.c: Implement models of the Musca-A and -B1 boards
      hw/arm/musca: Add PPCs
      hw/arm/musca: Add MPCs
      hw/arm/musca: Wire up PL031 RTC
      hw/arm/musca: Wire up PL011 UARTs
      hw/arm/armsse: Make 0x5... alias region work for per-CPU devices

Richard Henderson (4):
      target/arm: Restructure disas_fp_int_conv
      target/arm: Split out vfp_helper.c
      target/arm: Rearrange Floating-point data-processing (2 regs)
      target/arm: Implement ARMv8.3-JSConv

 hw/arm/Makefile.objs            |    1 +
 target/arm/Makefile.objs        |    2 +-
 include/hw/arm/armsse.h         |    7 +-
 include/hw/char/pl011.h         |   34 ++
 include/hw/misc/tz-ppc.h        |    8 +-
 include/hw/timer/pl031.h        |   44 ++
 target/arm/cpu.h                |   10 +
 target/arm/helper.h             |    3 +
 hw/arm/armsse.c                 |   44 +-
 hw/arm/musca.c                  |  669 ++++++++++++++++++++++
 hw/char/pl011.c                 |   81 +--
 hw/misc/tz-ppc.c                |   32 ++
 hw/timer/pl031.c                |   80 ++-
 target/arm/cpu.c                |    1 +
 target/arm/cpu64.c              |    2 +
 target/arm/helper.c             | 1072 +----------------------------------
 target/arm/translate-a64.c      |  120 ++--
 target/arm/translate.c          |  237 ++++----
 target/arm/vfp_helper.c         | 1176 +++++++++++++++++++++++++++++++++++++++
 MAINTAINERS                     |    7 +
 default-configs/arm-softmmu.mak |    1 +
 hw/timer/trace-events           |    6 +
 22 files changed, 2307 insertions(+), 1330 deletions(-)
 create mode 100644 include/hw/timer/pl031.h
 create mode 100644 hw/arm/musca.c
 create mode 100644 target/arm/vfp_helper.c

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 01/21] hw/arm/armsse: Fix memory leak in error-exit path
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 02/21] target/arm: v8M MPU should use background region as default, not always Peter Maydell
                   ` (20 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Coverity points out (CID 1398632, CID 1398650) that we
leak a couple of allocated strings in the error-exit
code path for setting up the MHUs in the ARMSSE.
Fix this bug by moving the allocate-and-free of each
string to be closer to the use, so we do the free before
doing the error-exit check.

Fixes: f8574705f62b38a ("hw/arm/armsse: Add unimplemented-device stubs for MHUs")
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Message-id: 20190215113707.24553-1-peter.maydell@linaro.org
---
 hw/arm/armsse.c | 10 ++++++----
 1 file changed, 6 insertions(+), 4 deletions(-)

diff --git a/hw/arm/armsse.c b/hw/arm/armsse.c
index 9a8c49547db..d0207dbabc7 100644
--- a/hw/arm/armsse.c
+++ b/hw/arm/armsse.c
@@ -762,26 +762,28 @@ static void armsse_realize(DeviceState *dev, Error **errp)
 
     if (info->has_mhus) {
         for (i = 0; i < ARRAY_SIZE(s->mhu); i++) {
-            char *name = g_strdup_printf("MHU%d", i);
-            char *port = g_strdup_printf("port[%d]", i + 3);
+            char *name;
+            char *port;
 
+            name = g_strdup_printf("MHU%d", i);
             qdev_prop_set_string(DEVICE(&s->mhu[i]), "name", name);
             qdev_prop_set_uint64(DEVICE(&s->mhu[i]), "size", 0x1000);
             object_property_set_bool(OBJECT(&s->mhu[i]), true,
                                      "realized", &err);
+            g_free(name);
             if (err) {
                 error_propagate(errp, err);
                 return;
             }
+            port = g_strdup_printf("port[%d]", i + 3);
             mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->mhu[i]), 0);
             object_property_set_link(OBJECT(&s->apb_ppc0), OBJECT(mr),
                                      port, &err);
+            g_free(port);
             if (err) {
                 error_propagate(errp, err);
                 return;
             }
-            g_free(name);
-            g_free(port);
         }
     }
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 02/21] target/arm: v8M MPU should use background region as default, not always
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 01/21] hw/arm/armsse: Fix memory leak in error-exit path Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 03/21] target/arm: Stop unintentional sign extension in pmu_init Peter Maydell
                   ` (19 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The "background region" for a v8M MPU is a default which will be used
(if enabled, and if the access is privileged) if the access does
not match any specific MPU region. We were incorrectly using it
always (by putting the condition at the wrong nesting level). This
meant that we would always return the default background permissions
rather than the correct permissions for a specific region, and also
that we would not return the right information in response to a
TT instruction.

Move the check for the background region to the same place in the
logic as the equivalent v8M MPUCheck() pseudocode puts it.
This in turn means we must adjust the condition we use to detect
matches in multiple regions to avoid false-positives.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190214113408.10214-1-peter.maydell@linaro.org
---
 target/arm/helper.c | 8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/target/arm/helper.c b/target/arm/helper.c
index a018eb23fe2..fe054897c78 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -11387,9 +11387,11 @@ static bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
         hit = true;
     } else if (m_is_ppb_region(env, address)) {
         hit = true;
-    } else if (pmsav7_use_background_region(cpu, mmu_idx, is_user)) {
-        hit = true;
     } else {
+        if (pmsav7_use_background_region(cpu, mmu_idx, is_user)) {
+            hit = true;
+        }
+
         for (n = (int)cpu->pmsav7_dregion - 1; n >= 0; n--) {
             /* region search */
             /* Note that the base address is bits [31:5] from the register
@@ -11427,7 +11429,7 @@ static bool pmsav8_mpu_lookup(CPUARMState *env, uint32_t address,
                 *is_subpage = true;
             }
 
-            if (hit) {
+            if (matchregion != -1) {
                 /* Multiple regions match -- always a failure (unlike
                  * PMSAv7 where highest-numbered-region wins)
                  */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 03/21] target/arm: Stop unintentional sign extension in pmu_init
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 01/21] hw/arm/armsse: Fix memory leak in error-exit path Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 02/21] target/arm: v8M MPU should use background region as default, not always Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 04/21] target/arm: Restructure disas_fp_int_conv Peter Maydell
                   ` (18 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

From: Aaron Lindsay OS <aaron@os.amperecomputing.com>

This was introduced by
    commit bf8d09694ccc07487cd73d7562081fdaec3370c8
    target/arm: Don't clear supported PMU events when initializing PMCEID1
and identified by Coverity (CID 1398645).

Signed-off-by: Aaron Lindsay <aaron@os.amperecomputing.com>
Reported-by: Peter Maydell <peter.maydell@linaro.org>
Message-id: 20190219144621.450-1-aaron@os.amperecomputing.com
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target/arm/helper.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/target/arm/helper.c b/target/arm/helper.c
index fe054897c78..c2630fa1ea4 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -1167,7 +1167,7 @@ void pmu_init(ARMCPU *cpu)
 
         if (cnt->supported(&cpu->env)) {
             supported_event_map[cnt->number] = i;
-            uint64_t event_mask = 1 << (cnt->number & 0x1f);
+            uint64_t event_mask = 1ULL << (cnt->number & 0x1f);
             if (cnt->number & 0x20) {
                 cpu->pmceid1 |= event_mask;
             } else {
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 04/21] target/arm: Restructure disas_fp_int_conv
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (2 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 03/21] target/arm: Stop unintentional sign extension in pmu_init Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 05/21] target/arm: Split out vfp_helper.c Peter Maydell
                   ` (17 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

From: Richard Henderson <richard.henderson@linaro.org>

For opcodes 0-5, move some if conditions into the structure
of a switch statement.  For opcodes 6 & 7, decode everything
at once with a second switch.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190215192302.27855-2-richard.henderson@linaro.org
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target/arm/translate-a64.c | 94 ++++++++++++++++++++------------------
 1 file changed, 49 insertions(+), 45 deletions(-)

diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
index af8e4fd4be1..dbce24fe32c 100644
--- a/target/arm/translate-a64.c
+++ b/target/arm/translate-a64.c
@@ -6541,68 +6541,72 @@ static void disas_fp_int_conv(DisasContext *s, uint32_t insn)
     int type = extract32(insn, 22, 2);
     bool sbit = extract32(insn, 29, 1);
     bool sf = extract32(insn, 31, 1);
+    bool itof = false;
 
     if (sbit) {
-        unallocated_encoding(s);
-        return;
+        goto do_unallocated;
     }
 
-    if (opcode > 5) {
-        /* FMOV */
-        bool itof = opcode & 1;
-
-        if (rmode >= 2) {
-            unallocated_encoding(s);
-            return;
-        }
-
-        switch (sf << 3 | type << 1 | rmode) {
-        case 0x0: /* 32 bit */
-        case 0xa: /* 64 bit */
-        case 0xd: /* 64 bit to top half of quad */
-            break;
-        case 0x6: /* 16-bit float, 32-bit int */
-        case 0xe: /* 16-bit float, 64-bit int */
-            if (dc_isar_feature(aa64_fp16, s)) {
-                break;
-            }
-            /* fallthru */
-        default:
-            /* all other sf/type/rmode combinations are invalid */
-            unallocated_encoding(s);
-            return;
-        }
-
-        if (!fp_access_check(s)) {
-            return;
-        }
-        handle_fmov(s, rd, rn, type, itof);
-    } else {
-        /* actual FP conversions */
-        bool itof = extract32(opcode, 1, 1);
-
-        if (rmode != 0 && opcode > 1) {
-            unallocated_encoding(s);
-            return;
+    switch (opcode) {
+    case 2: /* SCVTF */
+    case 3: /* UCVTF */
+        itof = true;
+        /* fallthru */
+    case 4: /* FCVTAS */
+    case 5: /* FCVTAU */
+        if (rmode != 0) {
+            goto do_unallocated;
         }
+        /* fallthru */
+    case 0: /* FCVT[NPMZ]S */
+    case 1: /* FCVT[NPMZ]U */
         switch (type) {
         case 0: /* float32 */
         case 1: /* float64 */
             break;
         case 3: /* float16 */
-            if (dc_isar_feature(aa64_fp16, s)) {
-                break;
+            if (!dc_isar_feature(aa64_fp16, s)) {
+                goto do_unallocated;
             }
-            /* fallthru */
+            break;
         default:
-            unallocated_encoding(s);
-            return;
+            goto do_unallocated;
         }
-
         if (!fp_access_check(s)) {
             return;
         }
         handle_fpfpcvt(s, rd, rn, opcode, itof, rmode, 64, sf, type);
+        break;
+
+    default:
+        switch (sf << 7 | type << 5 | rmode << 3 | opcode) {
+        case 0b01100110: /* FMOV half <-> 32-bit int */
+        case 0b01100111:
+        case 0b11100110: /* FMOV half <-> 64-bit int */
+        case 0b11100111:
+            if (!dc_isar_feature(aa64_fp16, s)) {
+                goto do_unallocated;
+            }
+            /* fallthru */
+        case 0b00000110: /* FMOV 32-bit */
+        case 0b00000111:
+        case 0b10100110: /* FMOV 64-bit */
+        case 0b10100111:
+        case 0b11001110: /* FMOV top half of 128-bit */
+        case 0b11001111:
+            if (!fp_access_check(s)) {
+                return;
+            }
+            itof = opcode & 1;
+            handle_fmov(s, rd, rn, type, itof);
+            break;
+
+        default:
+        do_unallocated:
+            unallocated_encoding(s);
+            return;
+        }
+        break;
     }
 }
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 05/21] target/arm: Split out vfp_helper.c
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (3 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 04/21] target/arm: Restructure disas_fp_int_conv Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 06/21] target/arm: Rearrange Floating-point data-processing (2 regs) Peter Maydell
                   ` (16 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

From: Richard Henderson <richard.henderson@linaro.org>

Move all of the fp helpers out of helper.c into a new file.
This is code movement only.  Since helper.c has no copyright
header, take the one from cpu.h for the new file.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190215192302.27855-3-richard.henderson@linaro.org
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target/arm/Makefile.objs |    2 +-
 target/arm/helper.c      | 1062 -------------------------------------
 target/arm/vfp_helper.c  | 1088 ++++++++++++++++++++++++++++++++++++++
 3 files changed, 1089 insertions(+), 1063 deletions(-)
 create mode 100644 target/arm/vfp_helper.c

diff --git a/target/arm/Makefile.objs b/target/arm/Makefile.objs
index 1a4fc06448d..6bdcc65c2c8 100644
--- a/target/arm/Makefile.objs
+++ b/target/arm/Makefile.objs
@@ -5,7 +5,7 @@ obj-$(call land,$(CONFIG_KVM),$(call lnot,$(TARGET_AARCH64))) += kvm32.o
 obj-$(call land,$(CONFIG_KVM),$(TARGET_AARCH64)) += kvm64.o
 obj-$(call lnot,$(CONFIG_KVM)) += kvm-stub.o
 obj-y += translate.o op_helper.o helper.o cpu.o
-obj-y += neon_helper.o iwmmxt_helper.o vec_helper.o
+obj-y += neon_helper.o iwmmxt_helper.o vec_helper.o vfp_helper.o
 obj-y += gdbstub.o
 obj-$(TARGET_AARCH64) += cpu64.o translate-a64.o helper-a64.o gdbstub64.o
 obj-$(TARGET_AARCH64) += pauth_helper.o
diff --git a/target/arm/helper.c b/target/arm/helper.c
index c2630fa1ea4..fbaa801ceaa 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -12681,1068 +12681,6 @@ uint32_t HELPER(sel_flags)(uint32_t flags, uint32_t a, uint32_t b)
     return (a & mask) | (b & ~mask);
 }
 
-/* VFP support.  We follow the convention used for VFP instructions:
-   Single precision routines have a "s" suffix, double precision a
-   "d" suffix.  */
-
-/* Convert host exception flags to vfp form.  */
-static inline int vfp_exceptbits_from_host(int host_bits)
-{
-    int target_bits = 0;
-
-    if (host_bits & float_flag_invalid)
-        target_bits |= 1;
-    if (host_bits & float_flag_divbyzero)
-        target_bits |= 2;
-    if (host_bits & float_flag_overflow)
-        target_bits |= 4;
-    if (host_bits & (float_flag_underflow | float_flag_output_denormal))
-        target_bits |= 8;
-    if (host_bits & float_flag_inexact)
-        target_bits |= 0x10;
-    if (host_bits & float_flag_input_denormal)
-        target_bits |= 0x80;
-    return target_bits;
-}
-
-uint32_t HELPER(vfp_get_fpscr)(CPUARMState *env)
-{
-    uint32_t i, fpscr;
-
-    fpscr = env->vfp.xregs[ARM_VFP_FPSCR]
-            | (env->vfp.vec_len << 16)
-            | (env->vfp.vec_stride << 20);
-
-    i = get_float_exception_flags(&env->vfp.fp_status);
-    i |= get_float_exception_flags(&env->vfp.standard_fp_status);
-    /* FZ16 does not generate an input denormal exception.  */
-    i |= (get_float_exception_flags(&env->vfp.fp_status_f16)
-          & ~float_flag_input_denormal);
-    fpscr |= vfp_exceptbits_from_host(i);
-
-    i = env->vfp.qc[0] | env->vfp.qc[1] | env->vfp.qc[2] | env->vfp.qc[3];
-    fpscr |= i ? FPCR_QC : 0;
-
-    return fpscr;
-}
-
-uint32_t vfp_get_fpscr(CPUARMState *env)
-{
-    return HELPER(vfp_get_fpscr)(env);
-}
-
-/* Convert vfp exception flags to target form.  */
-static inline int vfp_exceptbits_to_host(int target_bits)
-{
-    int host_bits = 0;
-
-    if (target_bits & 1)
-        host_bits |= float_flag_invalid;
-    if (target_bits & 2)
-        host_bits |= float_flag_divbyzero;
-    if (target_bits & 4)
-        host_bits |= float_flag_overflow;
-    if (target_bits & 8)
-        host_bits |= float_flag_underflow;
-    if (target_bits & 0x10)
-        host_bits |= float_flag_inexact;
-    if (target_bits & 0x80)
-        host_bits |= float_flag_input_denormal;
-    return host_bits;
-}
-
-void HELPER(vfp_set_fpscr)(CPUARMState *env, uint32_t val)
-{
-    int i;
-    uint32_t changed = env->vfp.xregs[ARM_VFP_FPSCR];
-
-    /* When ARMv8.2-FP16 is not supported, FZ16 is RES0.  */
-    if (!cpu_isar_feature(aa64_fp16, arm_env_get_cpu(env))) {
-        val &= ~FPCR_FZ16;
-    }
-
-    /*
-     * We don't implement trapped exception handling, so the
-     * trap enable bits, IDE|IXE|UFE|OFE|DZE|IOE are all RAZ/WI (not RES0!)
-     *
-     * If we exclude the exception flags, IOC|DZC|OFC|UFC|IXC|IDC
-     * (which are stored in fp_status), and the other RES0 bits
-     * in between, then we clear all of the low 16 bits.
-     */
-    env->vfp.xregs[ARM_VFP_FPSCR] = val & 0xf7c80000;
-    env->vfp.vec_len = (val >> 16) & 7;
-    env->vfp.vec_stride = (val >> 20) & 3;
-
-    /*
-     * The bit we set within fpscr_q is arbitrary; the register as a
-     * whole being zero/non-zero is what counts.
-     */
-    env->vfp.qc[0] = val & FPCR_QC;
-    env->vfp.qc[1] = 0;
-    env->vfp.qc[2] = 0;
-    env->vfp.qc[3] = 0;
-
-    changed ^= val;
-    if (changed & (3 << 22)) {
-        i = (val >> 22) & 3;
-        switch (i) {
-        case FPROUNDING_TIEEVEN:
-            i = float_round_nearest_even;
-            break;
-        case FPROUNDING_POSINF:
-            i = float_round_up;
-            break;
-        case FPROUNDING_NEGINF:
-            i = float_round_down;
-            break;
-        case FPROUNDING_ZERO:
-            i = float_round_to_zero;
-            break;
-        }
-        set_float_rounding_mode(i, &env->vfp.fp_status);
-        set_float_rounding_mode(i, &env->vfp.fp_status_f16);
-    }
-    if (changed & FPCR_FZ16) {
-        bool ftz_enabled = val & FPCR_FZ16;
-        set_flush_to_zero(ftz_enabled, &env->vfp.fp_status_f16);
-        set_flush_inputs_to_zero(ftz_enabled, &env->vfp.fp_status_f16);
-    }
-    if (changed & FPCR_FZ) {
-        bool ftz_enabled = val & FPCR_FZ;
-        set_flush_to_zero(ftz_enabled, &env->vfp.fp_status);
-        set_flush_inputs_to_zero(ftz_enabled, &env->vfp.fp_status);
-    }
-    if (changed & FPCR_DN) {
-        bool dnan_enabled = val & FPCR_DN;
-        set_default_nan_mode(dnan_enabled, &env->vfp.fp_status);
-        set_default_nan_mode(dnan_enabled, &env->vfp.fp_status_f16);
-    }
-
-    /* The exception flags are ORed together when we read fpscr so we
-     * only need to preserve the current state in one of our
-     * float_status values.
-     */
-    i = vfp_exceptbits_to_host(val);
-    set_float_exception_flags(i, &env->vfp.fp_status);
-    set_float_exception_flags(0, &env->vfp.fp_status_f16);
-    set_float_exception_flags(0, &env->vfp.standard_fp_status);
-}
-
-void vfp_set_fpscr(CPUARMState *env, uint32_t val)
-{
-    HELPER(vfp_set_fpscr)(env, val);
-}
-
-#define VFP_HELPER(name, p) HELPER(glue(glue(vfp_,name),p))
-
-#define VFP_BINOP(name) \
-float32 VFP_HELPER(name, s)(float32 a, float32 b, void *fpstp) \
-{ \
-    float_status *fpst = fpstp; \
-    return float32_ ## name(a, b, fpst); \
-} \
-float64 VFP_HELPER(name, d)(float64 a, float64 b, void *fpstp) \
-{ \
-    float_status *fpst = fpstp; \
-    return float64_ ## name(a, b, fpst); \
-}
-VFP_BINOP(add)
-VFP_BINOP(sub)
-VFP_BINOP(mul)
-VFP_BINOP(div)
-VFP_BINOP(min)
-VFP_BINOP(max)
-VFP_BINOP(minnum)
-VFP_BINOP(maxnum)
-#undef VFP_BINOP
-
-float32 VFP_HELPER(neg, s)(float32 a)
-{
-    return float32_chs(a);
-}
-
-float64 VFP_HELPER(neg, d)(float64 a)
-{
-    return float64_chs(a);
-}
-
-float32 VFP_HELPER(abs, s)(float32 a)
-{
-    return float32_abs(a);
-}
-
-float64 VFP_HELPER(abs, d)(float64 a)
-{
-    return float64_abs(a);
-}
-
-float32 VFP_HELPER(sqrt, s)(float32 a, CPUARMState *env)
-{
-    return float32_sqrt(a, &env->vfp.fp_status);
-}
-
-float64 VFP_HELPER(sqrt, d)(float64 a, CPUARMState *env)
-{
-    return float64_sqrt(a, &env->vfp.fp_status);
-}
-
-static void softfloat_to_vfp_compare(CPUARMState *env, int cmp)
-{
-    uint32_t flags;
-    switch (cmp) {
-    case float_relation_equal:
-        flags = 0x6;
-        break;
-    case float_relation_less:
-        flags = 0x8;
-        break;
-    case float_relation_greater:
-        flags = 0x2;
-        break;
-    case float_relation_unordered:
-        flags = 0x3;
-        break;
-    default:
-        g_assert_not_reached();
-    }
-    env->vfp.xregs[ARM_VFP_FPSCR] =
-        deposit32(env->vfp.xregs[ARM_VFP_FPSCR], 28, 4, flags);
-}
-
-/* XXX: check quiet/signaling case */
-#define DO_VFP_cmp(p, type) \
-void VFP_HELPER(cmp, p)(type a, type b, CPUARMState *env)  \
-{ \
-    softfloat_to_vfp_compare(env, \
-        type ## _compare_quiet(a, b, &env->vfp.fp_status)); \
-} \
-void VFP_HELPER(cmpe, p)(type a, type b, CPUARMState *env) \
-{ \
-    softfloat_to_vfp_compare(env, \
-        type ## _compare(a, b, &env->vfp.fp_status)); \
-}
-DO_VFP_cmp(s, float32)
-DO_VFP_cmp(d, float64)
-#undef DO_VFP_cmp
-
-/* Integer to float and float to integer conversions */
-
-#define CONV_ITOF(name, ftype, fsz, sign)                           \
-ftype HELPER(name)(uint32_t x, void *fpstp)                         \
-{                                                                   \
-    float_status *fpst = fpstp;                                     \
-    return sign##int32_to_##float##fsz((sign##int32_t)x, fpst);     \
-}
-
-#define CONV_FTOI(name, ftype, fsz, sign, round)                \
-sign##int32_t HELPER(name)(ftype x, void *fpstp)                \
-{                                                               \
-    float_status *fpst = fpstp;                                 \
-    if (float##fsz##_is_any_nan(x)) {                           \
-        float_raise(float_flag_invalid, fpst);                  \
-        return 0;                                               \
-    }                                                           \
-    return float##fsz##_to_##sign##int32##round(x, fpst);       \
-}
-
-#define FLOAT_CONVS(name, p, ftype, fsz, sign)            \
-    CONV_ITOF(vfp_##name##to##p, ftype, fsz, sign)        \
-    CONV_FTOI(vfp_to##name##p, ftype, fsz, sign, )        \
-    CONV_FTOI(vfp_to##name##z##p, ftype, fsz, sign, _round_to_zero)
-
-FLOAT_CONVS(si, h, uint32_t, 16, )
-FLOAT_CONVS(si, s, float32, 32, )
-FLOAT_CONVS(si, d, float64, 64, )
-FLOAT_CONVS(ui, h, uint32_t, 16, u)
-FLOAT_CONVS(ui, s, float32, 32, u)
-FLOAT_CONVS(ui, d, float64, 64, u)
-
-#undef CONV_ITOF
-#undef CONV_FTOI
-#undef FLOAT_CONVS
-
-/* floating point conversion */
-float64 VFP_HELPER(fcvtd, s)(float32 x, CPUARMState *env)
-{
-    return float32_to_float64(x, &env->vfp.fp_status);
-}
-
-float32 VFP_HELPER(fcvts, d)(float64 x, CPUARMState *env)
-{
-    return float64_to_float32(x, &env->vfp.fp_status);
-}
-
-/* VFP3 fixed point conversion.  */
-#define VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
-float##fsz HELPER(vfp_##name##to##p)(uint##isz##_t  x, uint32_t shift, \
-                                     void *fpstp) \
-{ return itype##_to_##float##fsz##_scalbn(x, -shift, fpstp); }
-
-#define VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, ROUND, suff)   \
-uint##isz##_t HELPER(vfp_to##name##p##suff)(float##fsz x, uint32_t shift, \
-                                            void *fpst)                   \
-{                                                                         \
-    if (unlikely(float##fsz##_is_any_nan(x))) {                           \
-        float_raise(float_flag_invalid, fpst);                            \
-        return 0;                                                         \
-    }                                                                     \
-    return float##fsz##_to_##itype##_scalbn(x, ROUND, shift, fpst);       \
-}
-
-#define VFP_CONV_FIX(name, p, fsz, isz, itype)                   \
-VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype)                     \
-VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
-                         float_round_to_zero, _round_to_zero)    \
-VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
-                         get_float_rounding_mode(fpst), )
-
-#define VFP_CONV_FIX_A64(name, p, fsz, isz, itype)               \
-VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype)                     \
-VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
-                         get_float_rounding_mode(fpst), )
-
-VFP_CONV_FIX(sh, d, 64, 64, int16)
-VFP_CONV_FIX(sl, d, 64, 64, int32)
-VFP_CONV_FIX_A64(sq, d, 64, 64, int64)
-VFP_CONV_FIX(uh, d, 64, 64, uint16)
-VFP_CONV_FIX(ul, d, 64, 64, uint32)
-VFP_CONV_FIX_A64(uq, d, 64, 64, uint64)
-VFP_CONV_FIX(sh, s, 32, 32, int16)
-VFP_CONV_FIX(sl, s, 32, 32, int32)
-VFP_CONV_FIX_A64(sq, s, 32, 64, int64)
-VFP_CONV_FIX(uh, s, 32, 32, uint16)
-VFP_CONV_FIX(ul, s, 32, 32, uint32)
-VFP_CONV_FIX_A64(uq, s, 32, 64, uint64)
-
-#undef VFP_CONV_FIX
-#undef VFP_CONV_FIX_FLOAT
-#undef VFP_CONV_FLOAT_FIX_ROUND
-#undef VFP_CONV_FIX_A64
-
-uint32_t HELPER(vfp_sltoh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    return int32_to_float16_scalbn(x, -shift, fpst);
-}
-
-uint32_t HELPER(vfp_ultoh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    return uint32_to_float16_scalbn(x, -shift, fpst);
-}
-
-uint32_t HELPER(vfp_sqtoh)(uint64_t x, uint32_t shift, void *fpst)
-{
-    return int64_to_float16_scalbn(x, -shift, fpst);
-}
-
-uint32_t HELPER(vfp_uqtoh)(uint64_t x, uint32_t shift, void *fpst)
-{
-    return uint64_to_float16_scalbn(x, -shift, fpst);
-}
-
-uint32_t HELPER(vfp_toshh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_int16_scalbn(x, get_float_rounding_mode(fpst),
-                                   shift, fpst);
-}
-
-uint32_t HELPER(vfp_touhh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_uint16_scalbn(x, get_float_rounding_mode(fpst),
-                                    shift, fpst);
-}
-
-uint32_t HELPER(vfp_toslh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_int32_scalbn(x, get_float_rounding_mode(fpst),
-                                   shift, fpst);
-}
-
-uint32_t HELPER(vfp_toulh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_uint32_scalbn(x, get_float_rounding_mode(fpst),
-                                    shift, fpst);
-}
-
-uint64_t HELPER(vfp_tosqh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_int64_scalbn(x, get_float_rounding_mode(fpst),
-                                   shift, fpst);
-}
-
-uint64_t HELPER(vfp_touqh)(uint32_t x, uint32_t shift, void *fpst)
-{
-    if (unlikely(float16_is_any_nan(x))) {
-        float_raise(float_flag_invalid, fpst);
-        return 0;
-    }
-    return float16_to_uint64_scalbn(x, get_float_rounding_mode(fpst),
-                                    shift, fpst);
-}
-
-/* Set the current fp rounding mode and return the old one.
- * The argument is a softfloat float_round_ value.
- */
-uint32_t HELPER(set_rmode)(uint32_t rmode, void *fpstp)
-{
-    float_status *fp_status = fpstp;
-
-    uint32_t prev_rmode = get_float_rounding_mode(fp_status);
-    set_float_rounding_mode(rmode, fp_status);
-
-    return prev_rmode;
-}
-
-/* Set the current fp rounding mode in the standard fp status and return
- * the old one. This is for NEON instructions that need to change the
- * rounding mode but wish to use the standard FPSCR values for everything
- * else. Always set the rounding mode back to the correct value after
- * modifying it.
- * The argument is a softfloat float_round_ value.
- */
-uint32_t HELPER(set_neon_rmode)(uint32_t rmode, CPUARMState *env)
-{
-    float_status *fp_status = &env->vfp.standard_fp_status;
-
-    uint32_t prev_rmode = get_float_rounding_mode(fp_status);
-    set_float_rounding_mode(rmode, fp_status);
-
-    return prev_rmode;
-}
-
-/* Half precision conversions.  */
-float32 HELPER(vfp_fcvt_f16_to_f32)(uint32_t a, void *fpstp, uint32_t ahp_mode)
-{
-    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
-     * it would affect flushing input denormals.
-     */
-    float_status *fpst = fpstp;
-    flag save = get_flush_inputs_to_zero(fpst);
-    set_flush_inputs_to_zero(false, fpst);
-    float32 r = float16_to_float32(a, !ahp_mode, fpst);
-    set_flush_inputs_to_zero(save, fpst);
-    return r;
-}
-
-uint32_t HELPER(vfp_fcvt_f32_to_f16)(float32 a, void *fpstp, uint32_t ahp_mode)
-{
-    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
-     * it would affect flushing output denormals.
-     */
-    float_status *fpst = fpstp;
-    flag save = get_flush_to_zero(fpst);
-    set_flush_to_zero(false, fpst);
-    float16 r = float32_to_float16(a, !ahp_mode, fpst);
-    set_flush_to_zero(save, fpst);
-    return r;
-}
-
-float64 HELPER(vfp_fcvt_f16_to_f64)(uint32_t a, void *fpstp, uint32_t ahp_mode)
-{
-    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
-     * it would affect flushing input denormals.
-     */
-    float_status *fpst = fpstp;
-    flag save = get_flush_inputs_to_zero(fpst);
-    set_flush_inputs_to_zero(false, fpst);
-    float64 r = float16_to_float64(a, !ahp_mode, fpst);
-    set_flush_inputs_to_zero(save, fpst);
-    return r;
-}
-
-uint32_t HELPER(vfp_fcvt_f64_to_f16)(float64 a, void *fpstp, uint32_t ahp_mode)
-{
-    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
-     * it would affect flushing output denormals.
-     */
-    float_status *fpst = fpstp;
-    flag save = get_flush_to_zero(fpst);
-    set_flush_to_zero(false, fpst);
-    float16 r = float64_to_float16(a, !ahp_mode, fpst);
-    set_flush_to_zero(save, fpst);
-    return r;
-}
-
-#define float32_two make_float32(0x40000000)
-#define float32_three make_float32(0x40400000)
-#define float32_one_point_five make_float32(0x3fc00000)
-
-float32 HELPER(recps_f32)(float32 a, float32 b, CPUARMState *env)
-{
-    float_status *s = &env->vfp.standard_fp_status;
-    if ((float32_is_infinity(a) && float32_is_zero_or_denormal(b)) ||
-        (float32_is_infinity(b) && float32_is_zero_or_denormal(a))) {
-        if (!(float32_is_zero(a) || float32_is_zero(b))) {
-            float_raise(float_flag_input_denormal, s);
-        }
-        return float32_two;
-    }
-    return float32_sub(float32_two, float32_mul(a, b, s), s);
-}
-
-float32 HELPER(rsqrts_f32)(float32 a, float32 b, CPUARMState *env)
-{
-    float_status *s = &env->vfp.standard_fp_status;
-    float32 product;
-    if ((float32_is_infinity(a) && float32_is_zero_or_denormal(b)) ||
-        (float32_is_infinity(b) && float32_is_zero_or_denormal(a))) {
-        if (!(float32_is_zero(a) || float32_is_zero(b))) {
-            float_raise(float_flag_input_denormal, s);
-        }
-        return float32_one_point_five;
-    }
-    product = float32_mul(a, b, s);
-    return float32_div(float32_sub(float32_three, product, s), float32_two, s);
-}
-
-/* NEON helpers.  */
-
-/* Constants 256 and 512 are used in some helpers; we avoid relying on
- * int->float conversions at run-time.  */
-#define float64_256 make_float64(0x4070000000000000LL)
-#define float64_512 make_float64(0x4080000000000000LL)
-#define float16_maxnorm make_float16(0x7bff)
-#define float32_maxnorm make_float32(0x7f7fffff)
-#define float64_maxnorm make_float64(0x7fefffffffffffffLL)
-
-/* Reciprocal functions
- *
- * The algorithm that must be used to calculate the estimate
- * is specified by the ARM ARM, see FPRecipEstimate()/RecipEstimate
- */
-
-/* See RecipEstimate()
- *
- * input is a 9 bit fixed point number
- * input range 256 .. 511 for a number from 0.5 <= x < 1.0.
- * result range 256 .. 511 for a number from 1.0 to 511/256.
- */
-
-static int recip_estimate(int input)
-{
-    int a, b, r;
-    assert(256 <= input && input < 512);
-    a = (input * 2) + 1;
-    b = (1 << 19) / a;
-    r = (b + 1) >> 1;
-    assert(256 <= r && r < 512);
-    return r;
-}
-
-/*
- * Common wrapper to call recip_estimate
- *
- * The parameters are exponent and 64 bit fraction (without implicit
- * bit) where the binary point is nominally at bit 52. Returns a
- * float64 which can then be rounded to the appropriate size by the
- * callee.
- */
-
-static uint64_t call_recip_estimate(int *exp, int exp_off, uint64_t frac)
-{
-    uint32_t scaled, estimate;
-    uint64_t result_frac;
-    int result_exp;
-
-    /* Handle sub-normals */
-    if (*exp == 0) {
-        if (extract64(frac, 51, 1) == 0) {
-            *exp = -1;
-            frac <<= 2;
-        } else {
-            frac <<= 1;
-        }
-    }
-
-    /* scaled = UInt('1':fraction<51:44>) */
-    scaled = deposit32(1 << 8, 0, 8, extract64(frac, 44, 8));
-    estimate = recip_estimate(scaled);
-
-    result_exp = exp_off - *exp;
-    result_frac = deposit64(0, 44, 8, estimate);
-    if (result_exp == 0) {
-        result_frac = deposit64(result_frac >> 1, 51, 1, 1);
-    } else if (result_exp == -1) {
-        result_frac = deposit64(result_frac >> 2, 50, 2, 1);
-        result_exp = 0;
-    }
-
-    *exp = result_exp;
-
-    return result_frac;
-}
-
-static bool round_to_inf(float_status *fpst, bool sign_bit)
-{
-    switch (fpst->float_rounding_mode) {
-    case float_round_nearest_even: /* Round to Nearest */
-        return true;
-    case float_round_up: /* Round to +Inf */
-        return !sign_bit;
-    case float_round_down: /* Round to -Inf */
-        return sign_bit;
-    case float_round_to_zero: /* Round to Zero */
-        return false;
-    }
-
-    g_assert_not_reached();
-}
-
-uint32_t HELPER(recpe_f16)(uint32_t input, void *fpstp)
-{
-    float_status *fpst = fpstp;
-    float16 f16 = float16_squash_input_denormal(input, fpst);
-    uint32_t f16_val = float16_val(f16);
-    uint32_t f16_sign = float16_is_neg(f16);
-    int f16_exp = extract32(f16_val, 10, 5);
-    uint32_t f16_frac = extract32(f16_val, 0, 10);
-    uint64_t f64_frac;
-
-    if (float16_is_any_nan(f16)) {
-        float16 nan = f16;
-        if (float16_is_signaling_nan(f16, fpst)) {
-            float_raise(float_flag_invalid, fpst);
-            nan = float16_silence_nan(f16, fpst);
-        }
-        if (fpst->default_nan_mode) {
-            nan =  float16_default_nan(fpst);
-        }
-        return nan;
-    } else if (float16_is_infinity(f16)) {
-        return float16_set_sign(float16_zero, float16_is_neg(f16));
-    } else if (float16_is_zero(f16)) {
-        float_raise(float_flag_divbyzero, fpst);
-        return float16_set_sign(float16_infinity, float16_is_neg(f16));
-    } else if (float16_abs(f16) < (1 << 8)) {
-        /* Abs(value) < 2.0^-16 */
-        float_raise(float_flag_overflow | float_flag_inexact, fpst);
-        if (round_to_inf(fpst, f16_sign)) {
-            return float16_set_sign(float16_infinity, f16_sign);
-        } else {
-            return float16_set_sign(float16_maxnorm, f16_sign);
-        }
-    } else if (f16_exp >= 29 && fpst->flush_to_zero) {
-        float_raise(float_flag_underflow, fpst);
-        return float16_set_sign(float16_zero, float16_is_neg(f16));
-    }
-
-    f64_frac = call_recip_estimate(&f16_exp, 29,
-                                   ((uint64_t) f16_frac) << (52 - 10));
-
-    /* result = sign : result_exp<4:0> : fraction<51:42> */
-    f16_val = deposit32(0, 15, 1, f16_sign);
-    f16_val = deposit32(f16_val, 10, 5, f16_exp);
-    f16_val = deposit32(f16_val, 0, 10, extract64(f64_frac, 52 - 10, 10));
-    return make_float16(f16_val);
-}
-
-float32 HELPER(recpe_f32)(float32 input, void *fpstp)
-{
-    float_status *fpst = fpstp;
-    float32 f32 = float32_squash_input_denormal(input, fpst);
-    uint32_t f32_val = float32_val(f32);
-    bool f32_sign = float32_is_neg(f32);
-    int f32_exp = extract32(f32_val, 23, 8);
-    uint32_t f32_frac = extract32(f32_val, 0, 23);
-    uint64_t f64_frac;
-
-    if (float32_is_any_nan(f32)) {
-        float32 nan = f32;
-        if (float32_is_signaling_nan(f32, fpst)) {
-            float_raise(float_flag_invalid, fpst);
-            nan = float32_silence_nan(f32, fpst);
-        }
-        if (fpst->default_nan_mode) {
-            nan =  float32_default_nan(fpst);
-        }
-        return nan;
-    } else if (float32_is_infinity(f32)) {
-        return float32_set_sign(float32_zero, float32_is_neg(f32));
-    } else if (float32_is_zero(f32)) {
-        float_raise(float_flag_divbyzero, fpst);
-        return float32_set_sign(float32_infinity, float32_is_neg(f32));
-    } else if (float32_abs(f32) < (1ULL << 21)) {
-        /* Abs(value) < 2.0^-128 */
-        float_raise(float_flag_overflow | float_flag_inexact, fpst);
-        if (round_to_inf(fpst, f32_sign)) {
-            return float32_set_sign(float32_infinity, f32_sign);
-        } else {
-            return float32_set_sign(float32_maxnorm, f32_sign);
-        }
-    } else if (f32_exp >= 253 && fpst->flush_to_zero) {
-        float_raise(float_flag_underflow, fpst);
-        return float32_set_sign(float32_zero, float32_is_neg(f32));
-    }
-
-    f64_frac = call_recip_estimate(&f32_exp, 253,
-                                   ((uint64_t) f32_frac) << (52 - 23));
-
-    /* result = sign : result_exp<7:0> : fraction<51:29> */
-    f32_val = deposit32(0, 31, 1, f32_sign);
-    f32_val = deposit32(f32_val, 23, 8, f32_exp);
-    f32_val = deposit32(f32_val, 0, 23, extract64(f64_frac, 52 - 23, 23));
-    return make_float32(f32_val);
-}
-
-float64 HELPER(recpe_f64)(float64 input, void *fpstp)
-{
-    float_status *fpst = fpstp;
-    float64 f64 = float64_squash_input_denormal(input, fpst);
-    uint64_t f64_val = float64_val(f64);
-    bool f64_sign = float64_is_neg(f64);
-    int f64_exp = extract64(f64_val, 52, 11);
-    uint64_t f64_frac = extract64(f64_val, 0, 52);
-
-    /* Deal with any special cases */
-    if (float64_is_any_nan(f64)) {
-        float64 nan = f64;
-        if (float64_is_signaling_nan(f64, fpst)) {
-            float_raise(float_flag_invalid, fpst);
-            nan = float64_silence_nan(f64, fpst);
-        }
-        if (fpst->default_nan_mode) {
-            nan =  float64_default_nan(fpst);
-        }
-        return nan;
-    } else if (float64_is_infinity(f64)) {
-        return float64_set_sign(float64_zero, float64_is_neg(f64));
-    } else if (float64_is_zero(f64)) {
-        float_raise(float_flag_divbyzero, fpst);
-        return float64_set_sign(float64_infinity, float64_is_neg(f64));
-    } else if ((f64_val & ~(1ULL << 63)) < (1ULL << 50)) {
-        /* Abs(value) < 2.0^-1024 */
-        float_raise(float_flag_overflow | float_flag_inexact, fpst);
-        if (round_to_inf(fpst, f64_sign)) {
-            return float64_set_sign(float64_infinity, f64_sign);
-        } else {
-            return float64_set_sign(float64_maxnorm, f64_sign);
-        }
-    } else if (f64_exp >= 2045 && fpst->flush_to_zero) {
-        float_raise(float_flag_underflow, fpst);
-        return float64_set_sign(float64_zero, float64_is_neg(f64));
-    }
-
-    f64_frac = call_recip_estimate(&f64_exp, 2045, f64_frac);
-
-    /* result = sign : result_exp<10:0> : fraction<51:0>; */
-    f64_val = deposit64(0, 63, 1, f64_sign);
-    f64_val = deposit64(f64_val, 52, 11, f64_exp);
-    f64_val = deposit64(f64_val, 0, 52, f64_frac);
-    return make_float64(f64_val);
-}
-
-/* The algorithm that must be used to calculate the estimate
- * is specified by the ARM ARM.
- */
-
-static int do_recip_sqrt_estimate(int a)
-{
-    int b, estimate;
-
-    assert(128 <= a && a < 512);
-    if (a < 256) {
-        a = a * 2 + 1;
-    } else {
-        a = (a >> 1) << 1;
-        a = (a + 1) * 2;
-    }
-    b = 512;
-    while (a * (b + 1) * (b + 1) < (1 << 28)) {
-        b += 1;
-    }
-    estimate = (b + 1) / 2;
-    assert(256 <= estimate && estimate < 512);
-
-    return estimate;
-}
-
-
-static uint64_t recip_sqrt_estimate(int *exp , int exp_off, uint64_t frac)
-{
-    int estimate;
-    uint32_t scaled;
-
-    if (*exp == 0) {
-        while (extract64(frac, 51, 1) == 0) {
-            frac = frac << 1;
-            *exp -= 1;
-        }
-        frac = extract64(frac, 0, 51) << 1;
-    }
-
-    if (*exp & 1) {
-        /* scaled = UInt('01':fraction<51:45>) */
-        scaled = deposit32(1 << 7, 0, 7, extract64(frac, 45, 7));
-    } else {
-        /* scaled = UInt('1':fraction<51:44>) */
-        scaled = deposit32(1 << 8, 0, 8, extract64(frac, 44, 8));
-    }
-    estimate = do_recip_sqrt_estimate(scaled);
-
-    *exp = (exp_off - *exp) / 2;
-    return extract64(estimate, 0, 8) << 44;
-}
-
-uint32_t HELPER(rsqrte_f16)(uint32_t input, void *fpstp)
-{
-    float_status *s = fpstp;
-    float16 f16 = float16_squash_input_denormal(input, s);
-    uint16_t val = float16_val(f16);
-    bool f16_sign = float16_is_neg(f16);
-    int f16_exp = extract32(val, 10, 5);
-    uint16_t f16_frac = extract32(val, 0, 10);
-    uint64_t f64_frac;
-
-    if (float16_is_any_nan(f16)) {
-        float16 nan = f16;
-        if (float16_is_signaling_nan(f16, s)) {
-            float_raise(float_flag_invalid, s);
-            nan = float16_silence_nan(f16, s);
-        }
-        if (s->default_nan_mode) {
-            nan =  float16_default_nan(s);
-        }
-        return nan;
-    } else if (float16_is_zero(f16)) {
-        float_raise(float_flag_divbyzero, s);
-        return float16_set_sign(float16_infinity, f16_sign);
-    } else if (f16_sign) {
-        float_raise(float_flag_invalid, s);
-        return float16_default_nan(s);
-    } else if (float16_is_infinity(f16)) {
-        return float16_zero;
-    }
-
-    /* Scale and normalize to a double-precision value between 0.25 and 1.0,
-     * preserving the parity of the exponent.  */
-
-    f64_frac = ((uint64_t) f16_frac) << (52 - 10);
-
-    f64_frac = recip_sqrt_estimate(&f16_exp, 44, f64_frac);
-
-    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(2) */
-    val = deposit32(0, 15, 1, f16_sign);
-    val = deposit32(val, 10, 5, f16_exp);
-    val = deposit32(val, 2, 8, extract64(f64_frac, 52 - 8, 8));
-    return make_float16(val);
-}
-
-float32 HELPER(rsqrte_f32)(float32 input, void *fpstp)
-{
-    float_status *s = fpstp;
-    float32 f32 = float32_squash_input_denormal(input, s);
-    uint32_t val = float32_val(f32);
-    uint32_t f32_sign = float32_is_neg(f32);
-    int f32_exp = extract32(val, 23, 8);
-    uint32_t f32_frac = extract32(val, 0, 23);
-    uint64_t f64_frac;
-
-    if (float32_is_any_nan(f32)) {
-        float32 nan = f32;
-        if (float32_is_signaling_nan(f32, s)) {
-            float_raise(float_flag_invalid, s);
-            nan = float32_silence_nan(f32, s);
-        }
-        if (s->default_nan_mode) {
-            nan =  float32_default_nan(s);
-        }
-        return nan;
-    } else if (float32_is_zero(f32)) {
-        float_raise(float_flag_divbyzero, s);
-        return float32_set_sign(float32_infinity, float32_is_neg(f32));
-    } else if (float32_is_neg(f32)) {
-        float_raise(float_flag_invalid, s);
-        return float32_default_nan(s);
-    } else if (float32_is_infinity(f32)) {
-        return float32_zero;
-    }
-
-    /* Scale and normalize to a double-precision value between 0.25 and 1.0,
-     * preserving the parity of the exponent.  */
-
-    f64_frac = ((uint64_t) f32_frac) << 29;
-
-    f64_frac = recip_sqrt_estimate(&f32_exp, 380, f64_frac);
-
-    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(15) */
-    val = deposit32(0, 31, 1, f32_sign);
-    val = deposit32(val, 23, 8, f32_exp);
-    val = deposit32(val, 15, 8, extract64(f64_frac, 52 - 8, 8));
-    return make_float32(val);
-}
-
-float64 HELPER(rsqrte_f64)(float64 input, void *fpstp)
-{
-    float_status *s = fpstp;
-    float64 f64 = float64_squash_input_denormal(input, s);
-    uint64_t val = float64_val(f64);
-    bool f64_sign = float64_is_neg(f64);
-    int f64_exp = extract64(val, 52, 11);
-    uint64_t f64_frac = extract64(val, 0, 52);
-
-    if (float64_is_any_nan(f64)) {
-        float64 nan = f64;
-        if (float64_is_signaling_nan(f64, s)) {
-            float_raise(float_flag_invalid, s);
-            nan = float64_silence_nan(f64, s);
-        }
-        if (s->default_nan_mode) {
-            nan =  float64_default_nan(s);
-        }
-        return nan;
-    } else if (float64_is_zero(f64)) {
-        float_raise(float_flag_divbyzero, s);
-        return float64_set_sign(float64_infinity, float64_is_neg(f64));
-    } else if (float64_is_neg(f64)) {
-        float_raise(float_flag_invalid, s);
-        return float64_default_nan(s);
-    } else if (float64_is_infinity(f64)) {
-        return float64_zero;
-    }
-
-    f64_frac = recip_sqrt_estimate(&f64_exp, 3068, f64_frac);
-
-    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(44) */
-    val = deposit64(0, 61, 1, f64_sign);
-    val = deposit64(val, 52, 11, f64_exp);
-    val = deposit64(val, 44, 8, extract64(f64_frac, 52 - 8, 8));
-    return make_float64(val);
-}
-
-uint32_t HELPER(recpe_u32)(uint32_t a, void *fpstp)
-{
-    /* float_status *s = fpstp; */
-    int input, estimate;
-
-    if ((a & 0x80000000) == 0) {
-        return 0xffffffff;
-    }
-
-    input = extract32(a, 23, 9);
-    estimate = recip_estimate(input);
-
-    return deposit32(0, (32 - 9), 9, estimate);
-}
-
-uint32_t HELPER(rsqrte_u32)(uint32_t a, void *fpstp)
-{
-    int estimate;
-
-    if ((a & 0xc0000000) == 0) {
-        return 0xffffffff;
-    }
-
-    estimate = do_recip_sqrt_estimate(extract32(a, 23, 9));
-
-    return deposit32(0, 23, 9, estimate);
-}
-
-/* VFPv4 fused multiply-accumulate */
-float32 VFP_HELPER(muladd, s)(float32 a, float32 b, float32 c, void *fpstp)
-{
-    float_status *fpst = fpstp;
-    return float32_muladd(a, b, c, 0, fpst);
-}
-
-float64 VFP_HELPER(muladd, d)(float64 a, float64 b, float64 c, void *fpstp)
-{
-    float_status *fpst = fpstp;
-    return float64_muladd(a, b, c, 0, fpst);
-}
-
-/* ARMv8 round to integral */
-float32 HELPER(rints_exact)(float32 x, void *fp_status)
-{
-    return float32_round_to_int(x, fp_status);
-}
-
-float64 HELPER(rintd_exact)(float64 x, void *fp_status)
-{
-    return float64_round_to_int(x, fp_status);
-}
-
-float32 HELPER(rints)(float32 x, void *fp_status)
-{
-    int old_flags = get_float_exception_flags(fp_status), new_flags;
-    float32 ret;
-
-    ret = float32_round_to_int(x, fp_status);
-
-    /* Suppress any inexact exceptions the conversion produced */
-    if (!(old_flags & float_flag_inexact)) {
-        new_flags = get_float_exception_flags(fp_status);
-        set_float_exception_flags(new_flags & ~float_flag_inexact, fp_status);
-    }
-
-    return ret;
-}
-
-float64 HELPER(rintd)(float64 x, void *fp_status)
-{
-    int old_flags = get_float_exception_flags(fp_status), new_flags;
-    float64 ret;
-
-    ret = float64_round_to_int(x, fp_status);
-
-    new_flags = get_float_exception_flags(fp_status);
-
-    /* Suppress any inexact exceptions the conversion produced */
-    if (!(old_flags & float_flag_inexact)) {
-        new_flags = get_float_exception_flags(fp_status);
-        set_float_exception_flags(new_flags & ~float_flag_inexact, fp_status);
-    }
-
-    return ret;
-}
-
-/* Convert ARM rounding mode to softfloat */
-int arm_rmode_to_sf(int rmode)
-{
-    switch (rmode) {
-    case FPROUNDING_TIEAWAY:
-        rmode = float_round_ties_away;
-        break;
-    case FPROUNDING_ODD:
-        /* FIXME: add support for TIEAWAY and ODD */
-        qemu_log_mask(LOG_UNIMP, "arm: unimplemented rounding mode: %d\n",
-                      rmode);
-        /* fall through for now */
-    case FPROUNDING_TIEEVEN:
-    default:
-        rmode = float_round_nearest_even;
-        break;
-    case FPROUNDING_POSINF:
-        rmode = float_round_up;
-        break;
-    case FPROUNDING_NEGINF:
-        rmode = float_round_down;
-        break;
-    case FPROUNDING_ZERO:
-        rmode = float_round_to_zero;
-        break;
-    }
-    return rmode;
-}
-
 /* CRC helpers.
  * The upper bytes of val (above the number specified by 'bytes') must have
  * been zeroed out by the caller.
diff --git a/target/arm/vfp_helper.c b/target/arm/vfp_helper.c
new file mode 100644
index 00000000000..74d3030c471
--- /dev/null
+++ b/target/arm/vfp_helper.c
@@ -0,0 +1,1088 @@
+/*
+ * ARM VFP floating-point operations
+ *
+ *  Copyright (c) 2003 Fabrice Bellard
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/log.h"
+#include "cpu.h"
+#include "exec/helper-proto.h"
+#include "fpu/softfloat.h"
+#include "internals.h"
+
+
+/* VFP support.  We follow the convention used for VFP instructions:
+   Single precision routines have a "s" suffix, double precision a
+   "d" suffix.  */
+
+/* Convert host exception flags to vfp form.  */
+static inline int vfp_exceptbits_from_host(int host_bits)
+{
+    int target_bits = 0;
+
+    if (host_bits & float_flag_invalid)
+        target_bits |= 1;
+    if (host_bits & float_flag_divbyzero)
+        target_bits |= 2;
+    if (host_bits & float_flag_overflow)
+        target_bits |= 4;
+    if (host_bits & (float_flag_underflow | float_flag_output_denormal))
+        target_bits |= 8;
+    if (host_bits & float_flag_inexact)
+        target_bits |= 0x10;
+    if (host_bits & float_flag_input_denormal)
+        target_bits |= 0x80;
+    return target_bits;
+}
+
+uint32_t HELPER(vfp_get_fpscr)(CPUARMState *env)
+{
+    uint32_t i, fpscr;
+
+    fpscr = env->vfp.xregs[ARM_VFP_FPSCR]
+            | (env->vfp.vec_len << 16)
+            | (env->vfp.vec_stride << 20);
+
+    i = get_float_exception_flags(&env->vfp.fp_status);
+    i |= get_float_exception_flags(&env->vfp.standard_fp_status);
+    /* FZ16 does not generate an input denormal exception.  */
+    i |= (get_float_exception_flags(&env->vfp.fp_status_f16)
+          & ~float_flag_input_denormal);
+    fpscr |= vfp_exceptbits_from_host(i);
+
+    i = env->vfp.qc[0] | env->vfp.qc[1] | env->vfp.qc[2] | env->vfp.qc[3];
+    fpscr |= i ? FPCR_QC : 0;
+
+    return fpscr;
+}
+
+uint32_t vfp_get_fpscr(CPUARMState *env)
+{
+    return HELPER(vfp_get_fpscr)(env);
+}
+
+/* Convert vfp exception flags to target form.  */
+static inline int vfp_exceptbits_to_host(int target_bits)
+{
+    int host_bits = 0;
+
+    if (target_bits & 1)
+        host_bits |= float_flag_invalid;
+    if (target_bits & 2)
+        host_bits |= float_flag_divbyzero;
+    if (target_bits & 4)
+        host_bits |= float_flag_overflow;
+    if (target_bits & 8)
+        host_bits |= float_flag_underflow;
+    if (target_bits & 0x10)
+        host_bits |= float_flag_inexact;
+    if (target_bits & 0x80)
+        host_bits |= float_flag_input_denormal;
+    return host_bits;
+}
+
+void HELPER(vfp_set_fpscr)(CPUARMState *env, uint32_t val)
+{
+    int i;
+    uint32_t changed = env->vfp.xregs[ARM_VFP_FPSCR];
+
+    /* When ARMv8.2-FP16 is not supported, FZ16 is RES0.  */
+    if (!cpu_isar_feature(aa64_fp16, arm_env_get_cpu(env))) {
+        val &= ~FPCR_FZ16;
+    }
+
+    /*
+     * We don't implement trapped exception handling, so the
+     * trap enable bits, IDE|IXE|UFE|OFE|DZE|IOE are all RAZ/WI (not RES0!)
+     *
+     * If we exclude the exception flags, IOC|DZC|OFC|UFC|IXC|IDC
+     * (which are stored in fp_status), and the other RES0 bits
+     * in between, then we clear all of the low 16 bits.
+     */
+    env->vfp.xregs[ARM_VFP_FPSCR] = val & 0xf7c80000;
+    env->vfp.vec_len = (val >> 16) & 7;
+    env->vfp.vec_stride = (val >> 20) & 3;
+
+    /*
+     * The bit we set within fpscr_q is arbitrary; the register as a
+     * whole being zero/non-zero is what counts.
+     */
+    env->vfp.qc[0] = val & FPCR_QC;
+    env->vfp.qc[1] = 0;
+    env->vfp.qc[2] = 0;
+    env->vfp.qc[3] = 0;
+
+    changed ^= val;
+    if (changed & (3 << 22)) {
+        i = (val >> 22) & 3;
+        switch (i) {
+        case FPROUNDING_TIEEVEN:
+            i = float_round_nearest_even;
+            break;
+        case FPROUNDING_POSINF:
+            i = float_round_up;
+            break;
+        case FPROUNDING_NEGINF:
+            i = float_round_down;
+            break;
+        case FPROUNDING_ZERO:
+            i = float_round_to_zero;
+            break;
+        }
+        set_float_rounding_mode(i, &env->vfp.fp_status);
+        set_float_rounding_mode(i, &env->vfp.fp_status_f16);
+    }
+    if (changed & FPCR_FZ16) {
+        bool ftz_enabled = val & FPCR_FZ16;
+        set_flush_to_zero(ftz_enabled, &env->vfp.fp_status_f16);
+        set_flush_inputs_to_zero(ftz_enabled, &env->vfp.fp_status_f16);
+    }
+    if (changed & FPCR_FZ) {
+        bool ftz_enabled = val & FPCR_FZ;
+        set_flush_to_zero(ftz_enabled, &env->vfp.fp_status);
+        set_flush_inputs_to_zero(ftz_enabled, &env->vfp.fp_status);
+    }
+    if (changed & FPCR_DN) {
+        bool dnan_enabled = val & FPCR_DN;
+        set_default_nan_mode(dnan_enabled, &env->vfp.fp_status);
+        set_default_nan_mode(dnan_enabled, &env->vfp.fp_status_f16);
+    }
+
+    /* The exception flags are ORed together when we read fpscr so we
+     * only need to preserve the current state in one of our
+     * float_status values.
+     */
+    i = vfp_exceptbits_to_host(val);
+    set_float_exception_flags(i, &env->vfp.fp_status);
+    set_float_exception_flags(0, &env->vfp.fp_status_f16);
+    set_float_exception_flags(0, &env->vfp.standard_fp_status);
+}
+
+void vfp_set_fpscr(CPUARMState *env, uint32_t val)
+{
+    HELPER(vfp_set_fpscr)(env, val);
+}
+
+#define VFP_HELPER(name, p) HELPER(glue(glue(vfp_,name),p))
+
+#define VFP_BINOP(name) \
+float32 VFP_HELPER(name, s)(float32 a, float32 b, void *fpstp) \
+{ \
+    float_status *fpst = fpstp; \
+    return float32_ ## name(a, b, fpst); \
+} \
+float64 VFP_HELPER(name, d)(float64 a, float64 b, void *fpstp) \
+{ \
+    float_status *fpst = fpstp; \
+    return float64_ ## name(a, b, fpst); \
+}
+VFP_BINOP(add)
+VFP_BINOP(sub)
+VFP_BINOP(mul)
+VFP_BINOP(div)
+VFP_BINOP(min)
+VFP_BINOP(max)
+VFP_BINOP(minnum)
+VFP_BINOP(maxnum)
+#undef VFP_BINOP
+
+float32 VFP_HELPER(neg, s)(float32 a)
+{
+    return float32_chs(a);
+}
+
+float64 VFP_HELPER(neg, d)(float64 a)
+{
+    return float64_chs(a);
+}
+
+float32 VFP_HELPER(abs, s)(float32 a)
+{
+    return float32_abs(a);
+}
+
+float64 VFP_HELPER(abs, d)(float64 a)
+{
+    return float64_abs(a);
+}
+
+float32 VFP_HELPER(sqrt, s)(float32 a, CPUARMState *env)
+{
+    return float32_sqrt(a, &env->vfp.fp_status);
+}
+
+float64 VFP_HELPER(sqrt, d)(float64 a, CPUARMState *env)
+{
+    return float64_sqrt(a, &env->vfp.fp_status);
+}
+
+static void softfloat_to_vfp_compare(CPUARMState *env, int cmp)
+{
+    uint32_t flags;
+    switch (cmp) {
+    case float_relation_equal:
+        flags = 0x6;
+        break;
+    case float_relation_less:
+        flags = 0x8;
+        break;
+    case float_relation_greater:
+        flags = 0x2;
+        break;
+    case float_relation_unordered:
+        flags = 0x3;
+        break;
+    default:
+        g_assert_not_reached();
+    }
+    env->vfp.xregs[ARM_VFP_FPSCR] =
+        deposit32(env->vfp.xregs[ARM_VFP_FPSCR], 28, 4, flags);
+}
+
+/* XXX: check quiet/signaling case */
+#define DO_VFP_cmp(p, type) \
+void VFP_HELPER(cmp, p)(type a, type b, CPUARMState *env)  \
+{ \
+    softfloat_to_vfp_compare(env, \
+        type ## _compare_quiet(a, b, &env->vfp.fp_status)); \
+} \
+void VFP_HELPER(cmpe, p)(type a, type b, CPUARMState *env) \
+{ \
+    softfloat_to_vfp_compare(env, \
+        type ## _compare(a, b, &env->vfp.fp_status)); \
+}
+DO_VFP_cmp(s, float32)
+DO_VFP_cmp(d, float64)
+#undef DO_VFP_cmp
+
+/* Integer to float and float to integer conversions */
+
+#define CONV_ITOF(name, ftype, fsz, sign)                           \
+ftype HELPER(name)(uint32_t x, void *fpstp)                         \
+{                                                                   \
+    float_status *fpst = fpstp;                                     \
+    return sign##int32_to_##float##fsz((sign##int32_t)x, fpst);     \
+}
+
+#define CONV_FTOI(name, ftype, fsz, sign, round)                \
+sign##int32_t HELPER(name)(ftype x, void *fpstp)                \
+{                                                               \
+    float_status *fpst = fpstp;                                 \
+    if (float##fsz##_is_any_nan(x)) {                           \
+        float_raise(float_flag_invalid, fpst);                  \
+        return 0;                                               \
+    }                                                           \
+    return float##fsz##_to_##sign##int32##round(x, fpst);       \
+}
+
+#define FLOAT_CONVS(name, p, ftype, fsz, sign)            \
+    CONV_ITOF(vfp_##name##to##p, ftype, fsz, sign)        \
+    CONV_FTOI(vfp_to##name##p, ftype, fsz, sign, )        \
+    CONV_FTOI(vfp_to##name##z##p, ftype, fsz, sign, _round_to_zero)
+
+FLOAT_CONVS(si, h, uint32_t, 16, )
+FLOAT_CONVS(si, s, float32, 32, )
+FLOAT_CONVS(si, d, float64, 64, )
+FLOAT_CONVS(ui, h, uint32_t, 16, u)
+FLOAT_CONVS(ui, s, float32, 32, u)
+FLOAT_CONVS(ui, d, float64, 64, u)
+
+#undef CONV_ITOF
+#undef CONV_FTOI
+#undef FLOAT_CONVS
+
+/* floating point conversion */
+float64 VFP_HELPER(fcvtd, s)(float32 x, CPUARMState *env)
+{
+    return float32_to_float64(x, &env->vfp.fp_status);
+}
+
+float32 VFP_HELPER(fcvts, d)(float64 x, CPUARMState *env)
+{
+    return float64_to_float32(x, &env->vfp.fp_status);
+}
+
+/* VFP3 fixed point conversion.  */
+#define VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype) \
+float##fsz HELPER(vfp_##name##to##p)(uint##isz##_t  x, uint32_t shift, \
+                                     void *fpstp) \
+{ return itype##_to_##float##fsz##_scalbn(x, -shift, fpstp); }
+
+#define VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype, ROUND, suff)   \
+uint##isz##_t HELPER(vfp_to##name##p##suff)(float##fsz x, uint32_t shift, \
+                                            void *fpst)                   \
+{                                                                         \
+    if (unlikely(float##fsz##_is_any_nan(x))) {                           \
+        float_raise(float_flag_invalid, fpst);                            \
+        return 0;                                                         \
+    }                                                                     \
+    return float##fsz##_to_##itype##_scalbn(x, ROUND, shift, fpst);       \
+}
+
+#define VFP_CONV_FIX(name, p, fsz, isz, itype)                   \
+VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype)                     \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
+                         float_round_to_zero, _round_to_zero)    \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
+                         get_float_rounding_mode(fpst), )
+
+#define VFP_CONV_FIX_A64(name, p, fsz, isz, itype)               \
+VFP_CONV_FIX_FLOAT(name, p, fsz, isz, itype)                     \
+VFP_CONV_FLOAT_FIX_ROUND(name, p, fsz, isz, itype,               \
+                         get_float_rounding_mode(fpst), )
+
+VFP_CONV_FIX(sh, d, 64, 64, int16)
+VFP_CONV_FIX(sl, d, 64, 64, int32)
+VFP_CONV_FIX_A64(sq, d, 64, 64, int64)
+VFP_CONV_FIX(uh, d, 64, 64, uint16)
+VFP_CONV_FIX(ul, d, 64, 64, uint32)
+VFP_CONV_FIX_A64(uq, d, 64, 64, uint64)
+VFP_CONV_FIX(sh, s, 32, 32, int16)
+VFP_CONV_FIX(sl, s, 32, 32, int32)
+VFP_CONV_FIX_A64(sq, s, 32, 64, int64)
+VFP_CONV_FIX(uh, s, 32, 32, uint16)
+VFP_CONV_FIX(ul, s, 32, 32, uint32)
+VFP_CONV_FIX_A64(uq, s, 32, 64, uint64)
+
+#undef VFP_CONV_FIX
+#undef VFP_CONV_FIX_FLOAT
+#undef VFP_CONV_FLOAT_FIX_ROUND
+#undef VFP_CONV_FIX_A64
+
+uint32_t HELPER(vfp_sltoh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    return int32_to_float16_scalbn(x, -shift, fpst);
+}
+
+uint32_t HELPER(vfp_ultoh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    return uint32_to_float16_scalbn(x, -shift, fpst);
+}
+
+uint32_t HELPER(vfp_sqtoh)(uint64_t x, uint32_t shift, void *fpst)
+{
+    return int64_to_float16_scalbn(x, -shift, fpst);
+}
+
+uint32_t HELPER(vfp_uqtoh)(uint64_t x, uint32_t shift, void *fpst)
+{
+    return uint64_to_float16_scalbn(x, -shift, fpst);
+}
+
+uint32_t HELPER(vfp_toshh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_int16_scalbn(x, get_float_rounding_mode(fpst),
+                                   shift, fpst);
+}
+
+uint32_t HELPER(vfp_touhh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_uint16_scalbn(x, get_float_rounding_mode(fpst),
+                                    shift, fpst);
+}
+
+uint32_t HELPER(vfp_toslh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_int32_scalbn(x, get_float_rounding_mode(fpst),
+                                   shift, fpst);
+}
+
+uint32_t HELPER(vfp_toulh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_uint32_scalbn(x, get_float_rounding_mode(fpst),
+                                    shift, fpst);
+}
+
+uint64_t HELPER(vfp_tosqh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_int64_scalbn(x, get_float_rounding_mode(fpst),
+                                   shift, fpst);
+}
+
+uint64_t HELPER(vfp_touqh)(uint32_t x, uint32_t shift, void *fpst)
+{
+    if (unlikely(float16_is_any_nan(x))) {
+        float_raise(float_flag_invalid, fpst);
+        return 0;
+    }
+    return float16_to_uint64_scalbn(x, get_float_rounding_mode(fpst),
+                                    shift, fpst);
+}
+
+/* Set the current fp rounding mode and return the old one.
+ * The argument is a softfloat float_round_ value.
+ */
+uint32_t HELPER(set_rmode)(uint32_t rmode, void *fpstp)
+{
+    float_status *fp_status = fpstp;
+
+    uint32_t prev_rmode = get_float_rounding_mode(fp_status);
+    set_float_rounding_mode(rmode, fp_status);
+
+    return prev_rmode;
+}
+
+/* Set the current fp rounding mode in the standard fp status and return
+ * the old one. This is for NEON instructions that need to change the
+ * rounding mode but wish to use the standard FPSCR values for everything
+ * else. Always set the rounding mode back to the correct value after
+ * modifying it.
+ * The argument is a softfloat float_round_ value.
+ */
+uint32_t HELPER(set_neon_rmode)(uint32_t rmode, CPUARMState *env)
+{
+    float_status *fp_status = &env->vfp.standard_fp_status;
+
+    uint32_t prev_rmode = get_float_rounding_mode(fp_status);
+    set_float_rounding_mode(rmode, fp_status);
+
+    return prev_rmode;
+}
+
+/* Half precision conversions.  */
+float32 HELPER(vfp_fcvt_f16_to_f32)(uint32_t a, void *fpstp, uint32_t ahp_mode)
+{
+    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
+     * it would affect flushing input denormals.
+     */
+    float_status *fpst = fpstp;
+    flag save = get_flush_inputs_to_zero(fpst);
+    set_flush_inputs_to_zero(false, fpst);
+    float32 r = float16_to_float32(a, !ahp_mode, fpst);
+    set_flush_inputs_to_zero(save, fpst);
+    return r;
+}
+
+uint32_t HELPER(vfp_fcvt_f32_to_f16)(float32 a, void *fpstp, uint32_t ahp_mode)
+{
+    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
+     * it would affect flushing output denormals.
+     */
+    float_status *fpst = fpstp;
+    flag save = get_flush_to_zero(fpst);
+    set_flush_to_zero(false, fpst);
+    float16 r = float32_to_float16(a, !ahp_mode, fpst);
+    set_flush_to_zero(save, fpst);
+    return r;
+}
+
+float64 HELPER(vfp_fcvt_f16_to_f64)(uint32_t a, void *fpstp, uint32_t ahp_mode)
+{
+    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
+     * it would affect flushing input denormals.
+     */
+    float_status *fpst = fpstp;
+    flag save = get_flush_inputs_to_zero(fpst);
+    set_flush_inputs_to_zero(false, fpst);
+    float64 r = float16_to_float64(a, !ahp_mode, fpst);
+    set_flush_inputs_to_zero(save, fpst);
+    return r;
+}
+
+uint32_t HELPER(vfp_fcvt_f64_to_f16)(float64 a, void *fpstp, uint32_t ahp_mode)
+{
+    /* Squash FZ16 to 0 for the duration of conversion.  In this case,
+     * it would affect flushing output denormals.
+     */
+    float_status *fpst = fpstp;
+    flag save = get_flush_to_zero(fpst);
+    set_flush_to_zero(false, fpst);
+    float16 r = float64_to_float16(a, !ahp_mode, fpst);
+    set_flush_to_zero(save, fpst);
+    return r;
+}
+
+#define float32_two make_float32(0x40000000)
+#define float32_three make_float32(0x40400000)
+#define float32_one_point_five make_float32(0x3fc00000)
+
+float32 HELPER(recps_f32)(float32 a, float32 b, CPUARMState *env)
+{
+    float_status *s = &env->vfp.standard_fp_status;
+    if ((float32_is_infinity(a) && float32_is_zero_or_denormal(b)) ||
+        (float32_is_infinity(b) && float32_is_zero_or_denormal(a))) {
+        if (!(float32_is_zero(a) || float32_is_zero(b))) {
+            float_raise(float_flag_input_denormal, s);
+        }
+        return float32_two;
+    }
+    return float32_sub(float32_two, float32_mul(a, b, s), s);
+}
+
+float32 HELPER(rsqrts_f32)(float32 a, float32 b, CPUARMState *env)
+{
+    float_status *s = &env->vfp.standard_fp_status;
+    float32 product;
+    if ((float32_is_infinity(a) && float32_is_zero_or_denormal(b)) ||
+        (float32_is_infinity(b) && float32_is_zero_or_denormal(a))) {
+        if (!(float32_is_zero(a) || float32_is_zero(b))) {
+            float_raise(float_flag_input_denormal, s);
+        }
+        return float32_one_point_five;
+    }
+    product = float32_mul(a, b, s);
+    return float32_div(float32_sub(float32_three, product, s), float32_two, s);
+}
+
+/* NEON helpers.  */
+
+/* Constants 256 and 512 are used in some helpers; we avoid relying on
+ * int->float conversions at run-time.  */
+#define float64_256 make_float64(0x4070000000000000LL)
+#define float64_512 make_float64(0x4080000000000000LL)
+#define float16_maxnorm make_float16(0x7bff)
+#define float32_maxnorm make_float32(0x7f7fffff)
+#define float64_maxnorm make_float64(0x7fefffffffffffffLL)
+
+/* Reciprocal functions
+ *
+ * The algorithm that must be used to calculate the estimate
+ * is specified by the ARM ARM, see FPRecipEstimate()/RecipEstimate
+ */
+
+/* See RecipEstimate()
+ *
+ * input is a 9 bit fixed point number
+ * input range 256 .. 511 for a number from 0.5 <= x < 1.0.
+ * result range 256 .. 511 for a number from 1.0 to 511/256.
+ */
+
+static int recip_estimate(int input)
+{
+    int a, b, r;
+    assert(256 <= input && input < 512);
+    a = (input * 2) + 1;
+    b = (1 << 19) / a;
+    r = (b + 1) >> 1;
+    assert(256 <= r && r < 512);
+    return r;
+}
+
+/*
+ * Common wrapper to call recip_estimate
+ *
+ * The parameters are exponent and 64 bit fraction (without implicit
+ * bit) where the binary point is nominally at bit 52. Returns a
+ * float64 which can then be rounded to the appropriate size by the
+ * callee.
+ */
+
+static uint64_t call_recip_estimate(int *exp, int exp_off, uint64_t frac)
+{
+    uint32_t scaled, estimate;
+    uint64_t result_frac;
+    int result_exp;
+
+    /* Handle sub-normals */
+    if (*exp == 0) {
+        if (extract64(frac, 51, 1) == 0) {
+            *exp = -1;
+            frac <<= 2;
+        } else {
+            frac <<= 1;
+        }
+    }
+
+    /* scaled = UInt('1':fraction<51:44>) */
+    scaled = deposit32(1 << 8, 0, 8, extract64(frac, 44, 8));
+    estimate = recip_estimate(scaled);
+
+    result_exp = exp_off - *exp;
+    result_frac = deposit64(0, 44, 8, estimate);
+    if (result_exp == 0) {
+        result_frac = deposit64(result_frac >> 1, 51, 1, 1);
+    } else if (result_exp == -1) {
+        result_frac = deposit64(result_frac >> 2, 50, 2, 1);
+        result_exp = 0;
+    }
+
+    *exp = result_exp;
+
+    return result_frac;
+}
+
+static bool round_to_inf(float_status *fpst, bool sign_bit)
+{
+    switch (fpst->float_rounding_mode) {
+    case float_round_nearest_even: /* Round to Nearest */
+        return true;
+    case float_round_up: /* Round to +Inf */
+        return !sign_bit;
+    case float_round_down: /* Round to -Inf */
+        return sign_bit;
+    case float_round_to_zero: /* Round to Zero */
+        return false;
+    }
+
+    g_assert_not_reached();
+}
+
+uint32_t HELPER(recpe_f16)(uint32_t input, void *fpstp)
+{
+    float_status *fpst = fpstp;
+    float16 f16 = float16_squash_input_denormal(input, fpst);
+    uint32_t f16_val = float16_val(f16);
+    uint32_t f16_sign = float16_is_neg(f16);
+    int f16_exp = extract32(f16_val, 10, 5);
+    uint32_t f16_frac = extract32(f16_val, 0, 10);
+    uint64_t f64_frac;
+
+    if (float16_is_any_nan(f16)) {
+        float16 nan = f16;
+        if (float16_is_signaling_nan(f16, fpst)) {
+            float_raise(float_flag_invalid, fpst);
+            nan = float16_silence_nan(f16, fpst);
+        }
+        if (fpst->default_nan_mode) {
+            nan =  float16_default_nan(fpst);
+        }
+        return nan;
+    } else if (float16_is_infinity(f16)) {
+        return float16_set_sign(float16_zero, float16_is_neg(f16));
+    } else if (float16_is_zero(f16)) {
+        float_raise(float_flag_divbyzero, fpst);
+        return float16_set_sign(float16_infinity, float16_is_neg(f16));
+    } else if (float16_abs(f16) < (1 << 8)) {
+        /* Abs(value) < 2.0^-16 */
+        float_raise(float_flag_overflow | float_flag_inexact, fpst);
+        if (round_to_inf(fpst, f16_sign)) {
+            return float16_set_sign(float16_infinity, f16_sign);
+        } else {
+            return float16_set_sign(float16_maxnorm, f16_sign);
+        }
+    } else if (f16_exp >= 29 && fpst->flush_to_zero) {
+        float_raise(float_flag_underflow, fpst);
+        return float16_set_sign(float16_zero, float16_is_neg(f16));
+    }
+
+    f64_frac = call_recip_estimate(&f16_exp, 29,
+                                   ((uint64_t) f16_frac) << (52 - 10));
+
+    /* result = sign : result_exp<4:0> : fraction<51:42> */
+    f16_val = deposit32(0, 15, 1, f16_sign);
+    f16_val = deposit32(f16_val, 10, 5, f16_exp);
+    f16_val = deposit32(f16_val, 0, 10, extract64(f64_frac, 52 - 10, 10));
+    return make_float16(f16_val);
+}
+
+float32 HELPER(recpe_f32)(float32 input, void *fpstp)
+{
+    float_status *fpst = fpstp;
+    float32 f32 = float32_squash_input_denormal(input, fpst);
+    uint32_t f32_val = float32_val(f32);
+    bool f32_sign = float32_is_neg(f32);
+    int f32_exp = extract32(f32_val, 23, 8);
+    uint32_t f32_frac = extract32(f32_val, 0, 23);
+    uint64_t f64_frac;
+
+    if (float32_is_any_nan(f32)) {
+        float32 nan = f32;
+        if (float32_is_signaling_nan(f32, fpst)) {
+            float_raise(float_flag_invalid, fpst);
+            nan = float32_silence_nan(f32, fpst);
+        }
+        if (fpst->default_nan_mode) {
+            nan =  float32_default_nan(fpst);
+        }
+        return nan;
+    } else if (float32_is_infinity(f32)) {
+        return float32_set_sign(float32_zero, float32_is_neg(f32));
+    } else if (float32_is_zero(f32)) {
+        float_raise(float_flag_divbyzero, fpst);
+        return float32_set_sign(float32_infinity, float32_is_neg(f32));
+    } else if (float32_abs(f32) < (1ULL << 21)) {
+        /* Abs(value) < 2.0^-128 */
+        float_raise(float_flag_overflow | float_flag_inexact, fpst);
+        if (round_to_inf(fpst, f32_sign)) {
+            return float32_set_sign(float32_infinity, f32_sign);
+        } else {
+            return float32_set_sign(float32_maxnorm, f32_sign);
+        }
+    } else if (f32_exp >= 253 && fpst->flush_to_zero) {
+        float_raise(float_flag_underflow, fpst);
+        return float32_set_sign(float32_zero, float32_is_neg(f32));
+    }
+
+    f64_frac = call_recip_estimate(&f32_exp, 253,
+                                   ((uint64_t) f32_frac) << (52 - 23));
+
+    /* result = sign : result_exp<7:0> : fraction<51:29> */
+    f32_val = deposit32(0, 31, 1, f32_sign);
+    f32_val = deposit32(f32_val, 23, 8, f32_exp);
+    f32_val = deposit32(f32_val, 0, 23, extract64(f64_frac, 52 - 23, 23));
+    return make_float32(f32_val);
+}
+
+float64 HELPER(recpe_f64)(float64 input, void *fpstp)
+{
+    float_status *fpst = fpstp;
+    float64 f64 = float64_squash_input_denormal(input, fpst);
+    uint64_t f64_val = float64_val(f64);
+    bool f64_sign = float64_is_neg(f64);
+    int f64_exp = extract64(f64_val, 52, 11);
+    uint64_t f64_frac = extract64(f64_val, 0, 52);
+
+    /* Deal with any special cases */
+    if (float64_is_any_nan(f64)) {
+        float64 nan = f64;
+        if (float64_is_signaling_nan(f64, fpst)) {
+            float_raise(float_flag_invalid, fpst);
+            nan = float64_silence_nan(f64, fpst);
+        }
+        if (fpst->default_nan_mode) {
+            nan =  float64_default_nan(fpst);
+        }
+        return nan;
+    } else if (float64_is_infinity(f64)) {
+        return float64_set_sign(float64_zero, float64_is_neg(f64));
+    } else if (float64_is_zero(f64)) {
+        float_raise(float_flag_divbyzero, fpst);
+        return float64_set_sign(float64_infinity, float64_is_neg(f64));
+    } else if ((f64_val & ~(1ULL << 63)) < (1ULL << 50)) {
+        /* Abs(value) < 2.0^-1024 */
+        float_raise(float_flag_overflow | float_flag_inexact, fpst);
+        if (round_to_inf(fpst, f64_sign)) {
+            return float64_set_sign(float64_infinity, f64_sign);
+        } else {
+            return float64_set_sign(float64_maxnorm, f64_sign);
+        }
+    } else if (f64_exp >= 2045 && fpst->flush_to_zero) {
+        float_raise(float_flag_underflow, fpst);
+        return float64_set_sign(float64_zero, float64_is_neg(f64));
+    }
+
+    f64_frac = call_recip_estimate(&f64_exp, 2045, f64_frac);
+
+    /* result = sign : result_exp<10:0> : fraction<51:0>; */
+    f64_val = deposit64(0, 63, 1, f64_sign);
+    f64_val = deposit64(f64_val, 52, 11, f64_exp);
+    f64_val = deposit64(f64_val, 0, 52, f64_frac);
+    return make_float64(f64_val);
+}
+
+/* The algorithm that must be used to calculate the estimate
+ * is specified by the ARM ARM.
+ */
+
+static int do_recip_sqrt_estimate(int a)
+{
+    int b, estimate;
+
+    assert(128 <= a && a < 512);
+    if (a < 256) {
+        a = a * 2 + 1;
+    } else {
+        a = (a >> 1) << 1;
+        a = (a + 1) * 2;
+    }
+    b = 512;
+    while (a * (b + 1) * (b + 1) < (1 << 28)) {
+        b += 1;
+    }
+    estimate = (b + 1) / 2;
+    assert(256 <= estimate && estimate < 512);
+
+    return estimate;
+}
+
+
+static uint64_t recip_sqrt_estimate(int *exp , int exp_off, uint64_t frac)
+{
+    int estimate;
+    uint32_t scaled;
+
+    if (*exp == 0) {
+        while (extract64(frac, 51, 1) == 0) {
+            frac = frac << 1;
+            *exp -= 1;
+        }
+        frac = extract64(frac, 0, 51) << 1;
+    }
+
+    if (*exp & 1) {
+        /* scaled = UInt('01':fraction<51:45>) */
+        scaled = deposit32(1 << 7, 0, 7, extract64(frac, 45, 7));
+    } else {
+        /* scaled = UInt('1':fraction<51:44>) */
+        scaled = deposit32(1 << 8, 0, 8, extract64(frac, 44, 8));
+    }
+    estimate = do_recip_sqrt_estimate(scaled);
+
+    *exp = (exp_off - *exp) / 2;
+    return extract64(estimate, 0, 8) << 44;
+}
+
+uint32_t HELPER(rsqrte_f16)(uint32_t input, void *fpstp)
+{
+    float_status *s = fpstp;
+    float16 f16 = float16_squash_input_denormal(input, s);
+    uint16_t val = float16_val(f16);
+    bool f16_sign = float16_is_neg(f16);
+    int f16_exp = extract32(val, 10, 5);
+    uint16_t f16_frac = extract32(val, 0, 10);
+    uint64_t f64_frac;
+
+    if (float16_is_any_nan(f16)) {
+        float16 nan = f16;
+        if (float16_is_signaling_nan(f16, s)) {
+            float_raise(float_flag_invalid, s);
+            nan = float16_silence_nan(f16, s);
+        }
+        if (s->default_nan_mode) {
+            nan =  float16_default_nan(s);
+        }
+        return nan;
+    } else if (float16_is_zero(f16)) {
+        float_raise(float_flag_divbyzero, s);
+        return float16_set_sign(float16_infinity, f16_sign);
+    } else if (f16_sign) {
+        float_raise(float_flag_invalid, s);
+        return float16_default_nan(s);
+    } else if (float16_is_infinity(f16)) {
+        return float16_zero;
+    }
+
+    /* Scale and normalize to a double-precision value between 0.25 and 1.0,
+     * preserving the parity of the exponent.  */
+
+    f64_frac = ((uint64_t) f16_frac) << (52 - 10);
+
+    f64_frac = recip_sqrt_estimate(&f16_exp, 44, f64_frac);
+
+    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(2) */
+    val = deposit32(0, 15, 1, f16_sign);
+    val = deposit32(val, 10, 5, f16_exp);
+    val = deposit32(val, 2, 8, extract64(f64_frac, 52 - 8, 8));
+    return make_float16(val);
+}
+
+float32 HELPER(rsqrte_f32)(float32 input, void *fpstp)
+{
+    float_status *s = fpstp;
+    float32 f32 = float32_squash_input_denormal(input, s);
+    uint32_t val = float32_val(f32);
+    uint32_t f32_sign = float32_is_neg(f32);
+    int f32_exp = extract32(val, 23, 8);
+    uint32_t f32_frac = extract32(val, 0, 23);
+    uint64_t f64_frac;
+
+    if (float32_is_any_nan(f32)) {
+        float32 nan = f32;
+        if (float32_is_signaling_nan(f32, s)) {
+            float_raise(float_flag_invalid, s);
+            nan = float32_silence_nan(f32, s);
+        }
+        if (s->default_nan_mode) {
+            nan =  float32_default_nan(s);
+        }
+        return nan;
+    } else if (float32_is_zero(f32)) {
+        float_raise(float_flag_divbyzero, s);
+        return float32_set_sign(float32_infinity, float32_is_neg(f32));
+    } else if (float32_is_neg(f32)) {
+        float_raise(float_flag_invalid, s);
+        return float32_default_nan(s);
+    } else if (float32_is_infinity(f32)) {
+        return float32_zero;
+    }
+
+    /* Scale and normalize to a double-precision value between 0.25 and 1.0,
+     * preserving the parity of the exponent.  */
+
+    f64_frac = ((uint64_t) f32_frac) << 29;
+
+    f64_frac = recip_sqrt_estimate(&f32_exp, 380, f64_frac);
+
+    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(15) */
+    val = deposit32(0, 31, 1, f32_sign);
+    val = deposit32(val, 23, 8, f32_exp);
+    val = deposit32(val, 15, 8, extract64(f64_frac, 52 - 8, 8));
+    return make_float32(val);
+}
+
+float64 HELPER(rsqrte_f64)(float64 input, void *fpstp)
+{
+    float_status *s = fpstp;
+    float64 f64 = float64_squash_input_denormal(input, s);
+    uint64_t val = float64_val(f64);
+    bool f64_sign = float64_is_neg(f64);
+    int f64_exp = extract64(val, 52, 11);
+    uint64_t f64_frac = extract64(val, 0, 52);
+
+    if (float64_is_any_nan(f64)) {
+        float64 nan = f64;
+        if (float64_is_signaling_nan(f64, s)) {
+            float_raise(float_flag_invalid, s);
+            nan = float64_silence_nan(f64, s);
+        }
+        if (s->default_nan_mode) {
+            nan =  float64_default_nan(s);
+        }
+        return nan;
+    } else if (float64_is_zero(f64)) {
+        float_raise(float_flag_divbyzero, s);
+        return float64_set_sign(float64_infinity, float64_is_neg(f64));
+    } else if (float64_is_neg(f64)) {
+        float_raise(float_flag_invalid, s);
+        return float64_default_nan(s);
+    } else if (float64_is_infinity(f64)) {
+        return float64_zero;
+    }
+
+    f64_frac = recip_sqrt_estimate(&f64_exp, 3068, f64_frac);
+
+    /* result = sign : result_exp<4:0> : estimate<7:0> : Zeros(44) */
+    val = deposit64(0, 61, 1, f64_sign);
+    val = deposit64(val, 52, 11, f64_exp);
+    val = deposit64(val, 44, 8, extract64(f64_frac, 52 - 8, 8));
+    return make_float64(val);
+}
+
+uint32_t HELPER(recpe_u32)(uint32_t a, void *fpstp)
+{
+    /* float_status *s = fpstp; */
+    int input, estimate;
+
+    if ((a & 0x80000000) == 0) {
+        return 0xffffffff;
+    }
+
+    input = extract32(a, 23, 9);
+    estimate = recip_estimate(input);
+
+    return deposit32(0, (32 - 9), 9, estimate);
+}
+
+uint32_t HELPER(rsqrte_u32)(uint32_t a, void *fpstp)
+{
+    int estimate;
+
+    if ((a & 0xc0000000) == 0) {
+        return 0xffffffff;
+    }
+
+    estimate = do_recip_sqrt_estimate(extract32(a, 23, 9));
+
+    return deposit32(0, 23, 9, estimate);
+}
+
+/* VFPv4 fused multiply-accumulate */
+float32 VFP_HELPER(muladd, s)(float32 a, float32 b, float32 c, void *fpstp)
+{
+    float_status *fpst = fpstp;
+    return float32_muladd(a, b, c, 0, fpst);
+}
+
+float64 VFP_HELPER(muladd, d)(float64 a, float64 b, float64 c, void *fpstp)
+{
+    float_status *fpst = fpstp;
+    return float64_muladd(a, b, c, 0, fpst);
+}
+
+/* ARMv8 round to integral */
+float32 HELPER(rints_exact)(float32 x, void *fp_status)
+{
+    return float32_round_to_int(x, fp_status);
+}
+
+float64 HELPER(rintd_exact)(float64 x, void *fp_status)
+{
+    return float64_round_to_int(x, fp_status);
+}
+
+float32 HELPER(rints)(float32 x, void *fp_status)
+{
+    int old_flags = get_float_exception_flags(fp_status), new_flags;
+    float32 ret;
+
+    ret = float32_round_to_int(x, fp_status);
+
+    /* Suppress any inexact exceptions the conversion produced */
+    if (!(old_flags & float_flag_inexact)) {
+        new_flags = get_float_exception_flags(fp_status);
+        set_float_exception_flags(new_flags & ~float_flag_inexact, fp_status);
+    }
+
+    return ret;
+}
+
+float64 HELPER(rintd)(float64 x, void *fp_status)
+{
+    int old_flags = get_float_exception_flags(fp_status), new_flags;
+    float64 ret;
+
+    ret = float64_round_to_int(x, fp_status);
+
+    new_flags = get_float_exception_flags(fp_status);
+
+    /* Suppress any inexact exceptions the conversion produced */
+    if (!(old_flags & float_flag_inexact)) {
+        new_flags = get_float_exception_flags(fp_status);
+        set_float_exception_flags(new_flags & ~float_flag_inexact, fp_status);
+    }
+
+    return ret;
+}
+
+/* Convert ARM rounding mode to softfloat */
+int arm_rmode_to_sf(int rmode)
+{
+    switch (rmode) {
+    case FPROUNDING_TIEAWAY:
+        rmode = float_round_ties_away;
+        break;
+    case FPROUNDING_ODD:
+        /* FIXME: add support for TIEAWAY and ODD */
+        qemu_log_mask(LOG_UNIMP, "arm: unimplemented rounding mode: %d\n",
+                      rmode);
+        /* fall through for now */
+    case FPROUNDING_TIEEVEN:
+    default:
+        rmode = float_round_nearest_even;
+        break;
+    case FPROUNDING_POSINF:
+        rmode = float_round_up;
+        break;
+    case FPROUNDING_NEGINF:
+        rmode = float_round_down;
+        break;
+    case FPROUNDING_ZERO:
+        rmode = float_round_to_zero;
+        break;
+    }
+    return rmode;
+}
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 06/21] target/arm: Rearrange Floating-point data-processing (2 regs)
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (4 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 05/21] target/arm: Split out vfp_helper.c Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 07/21] target/arm: Implement ARMv8.3-JSConv Peter Maydell
                   ` (15 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

From: Richard Henderson <richard.henderson@linaro.org>

There are lots of special cases within these insns.  Split the
major argument decode/loading/saving into no_output (compares),
rd_is_dp, and rm_is_dp.

We still need to special case argument load for compare (rd as
input, rm as zero) and vcvt fixed (rd as input+output), but lots
of special cases do disappear.

Now that we have a full switch at the beginning, hoist the ISA
checks from the code generation.

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190215192302.27855-4-richard.henderson@linaro.org
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target/arm/translate.c | 227 ++++++++++++++++++++---------------------
 1 file changed, 111 insertions(+), 116 deletions(-)

diff --git a/target/arm/translate.c b/target/arm/translate.c
index dac737f6cac..64c5fe0df3e 100644
--- a/target/arm/translate.c
+++ b/target/arm/translate.c
@@ -3639,52 +3639,108 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
             }
         } else {
             /* data processing */
+            bool rd_is_dp = dp;
+            bool rm_is_dp = dp;
+            bool no_output = false;
+
             /* The opcode is in bits 23, 21, 20 and 6.  */
             op = ((insn >> 20) & 8) | ((insn >> 19) & 6) | ((insn >> 6) & 1);
-            if (dp) {
-                if (op == 15) {
-                    /* rn is opcode */
-                    rn = ((insn >> 15) & 0x1e) | ((insn >> 7) & 1);
-                } else {
-                    /* rn is register number */
-                    VFP_DREG_N(rn, insn);
-                }
+            rn = VFP_SREG_N(insn);
 
-                if (op == 15 && (rn == 15 || ((rn & 0x1c) == 0x18) ||
-                                 ((rn & 0x1e) == 0x6))) {
-                    /* Integer or single/half precision destination.  */
-                    rd = VFP_SREG_D(insn);
-                } else {
-                    VFP_DREG_D(rd, insn);
-                }
-                if (op == 15 &&
-                    (((rn & 0x1c) == 0x10) || ((rn & 0x14) == 0x14) ||
-                     ((rn & 0x1e) == 0x4))) {
-                    /* VCVT from int or half precision is always from S reg
-                     * regardless of dp bit. VCVT with immediate frac_bits
-                     * has same format as SREG_M.
+            if (op == 15) {
+                /* rn is opcode, encoded as per VFP_SREG_N. */
+                switch (rn) {
+                case 0x00: /* vmov */
+                case 0x01: /* vabs */
+                case 0x02: /* vneg */
+                case 0x03: /* vsqrt */
+                    break;
+
+                case 0x04: /* vcvtb.f64.f16, vcvtb.f32.f16 */
+                case 0x05: /* vcvtt.f64.f16, vcvtt.f32.f16 */
+                    /*
+                     * VCVTB, VCVTT: only present with the halfprec extension
+                     * UNPREDICTABLE if bit 8 is set prior to ARMv8
+                     * (we choose to UNDEF)
                      */
-                    rm = VFP_SREG_M(insn);
-                } else {
-                    VFP_DREG_M(rm, insn);
+                    if ((dp && !arm_dc_feature(s, ARM_FEATURE_V8)) ||
+                        !arm_dc_feature(s, ARM_FEATURE_VFP_FP16)) {
+                        return 1;
+                    }
+                    rm_is_dp = false;
+                    break;
+                case 0x06: /* vcvtb.f16.f32, vcvtb.f16.f64 */
+                case 0x07: /* vcvtt.f16.f32, vcvtt.f16.f64 */
+                    if ((dp && !arm_dc_feature(s, ARM_FEATURE_V8)) ||
+                        !arm_dc_feature(s, ARM_FEATURE_VFP_FP16)) {
+                        return 1;
+                    }
+                    rd_is_dp = false;
+                    break;
+
+                case 0x08: case 0x0a: /* vcmp, vcmpz */
+                case 0x09: case 0x0b: /* vcmpe, vcmpez */
+                    no_output = true;
+                    break;
+
+                case 0x0c: /* vrintr */
+                case 0x0d: /* vrintz */
+                case 0x0e: /* vrintx */
+                    break;
+
+                case 0x0f: /* vcvt double<->single */
+                    rd_is_dp = !dp;
+                    break;
+
+                case 0x10: /* vcvt.fxx.u32 */
+                case 0x11: /* vcvt.fxx.s32 */
+                    rm_is_dp = false;
+                    break;
+                case 0x18: /* vcvtr.u32.fxx */
+                case 0x19: /* vcvtz.u32.fxx */
+                case 0x1a: /* vcvtr.s32.fxx */
+                case 0x1b: /* vcvtz.s32.fxx */
+                    rd_is_dp = false;
+                    break;
+
+                case 0x14: /* vcvt fp <-> fixed */
+                case 0x15:
+                case 0x16:
+                case 0x17:
+                case 0x1c:
+                case 0x1d:
+                case 0x1e:
+                case 0x1f:
+                    if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
+                        return 1;
+                    }
+                    /* Immediate frac_bits has same format as SREG_M.  */
+                    rm_is_dp = false;
+                    break;
+
+                default:
+                    return 1;
                 }
+            } else if (dp) {
+                /* rn is register number */
+                VFP_DREG_N(rn, insn);
+            }
+
+            if (rd_is_dp) {
+                VFP_DREG_D(rd, insn);
+            } else {
+                rd = VFP_SREG_D(insn);
+            }
+            if (rm_is_dp) {
+                VFP_DREG_M(rm, insn);
             } else {
-                rn = VFP_SREG_N(insn);
-                if (op == 15 && rn == 15) {
-                    /* Double precision destination.  */
-                    VFP_DREG_D(rd, insn);
-                } else {
-                    rd = VFP_SREG_D(insn);
-                }
-                /* NB that we implicitly rely on the encoding for the frac_bits
-                 * in VCVT of fixed to float being the same as that of an SREG_M
-                 */
                 rm = VFP_SREG_M(insn);
             }
 
             veclen = s->vec_len;
-            if (op == 15 && rn > 3)
+            if (op == 15 && rn > 3) {
                 veclen = 0;
+            }
 
             /* Shut up compiler warnings.  */
             delta_m = 0;
@@ -3720,55 +3776,28 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
             /* Load the initial operands.  */
             if (op == 15) {
                 switch (rn) {
-                case 16:
-                case 17:
-                    /* Integer source */
-                    gen_mov_F0_vreg(0, rm);
-                    break;
-                case 8:
-                case 9:
-                    /* Compare */
+                case 0x08: case 0x09: /* Compare */
                     gen_mov_F0_vreg(dp, rd);
                     gen_mov_F1_vreg(dp, rm);
                     break;
-                case 10:
-                case 11:
-                    /* Compare with zero */
+                case 0x0a: case 0x0b: /* Compare with zero */
                     gen_mov_F0_vreg(dp, rd);
                     gen_vfp_F1_ld0(dp);
                     break;
-                case 20:
-                case 21:
-                case 22:
-                case 23:
-                case 28:
-                case 29:
-                case 30:
-                case 31:
+                case 0x14: /* vcvt fp <-> fixed */
+                case 0x15:
+                case 0x16:
+                case 0x17:
+                case 0x1c:
+                case 0x1d:
+                case 0x1e:
+                case 0x1f:
                     /* Source and destination the same.  */
                     gen_mov_F0_vreg(dp, rd);
                     break;
-                case 4:
-                case 5:
-                case 6:
-                case 7:
-                    /* VCVTB, VCVTT: only present with the halfprec extension
-                     * UNPREDICTABLE if bit 8 is set prior to ARMv8
-                     * (we choose to UNDEF)
-                     */
-                    if ((dp && !arm_dc_feature(s, ARM_FEATURE_V8)) ||
-                        !arm_dc_feature(s, ARM_FEATURE_VFP_FP16)) {
-                        return 1;
-                    }
-                    if (!extract32(rn, 1, 1)) {
-                        /* Half precision source.  */
-                        gen_mov_F0_vreg(0, rm);
-                        break;
-                    }
-                    /* Otherwise fall through */
                 default:
                     /* One source operand.  */
-                    gen_mov_F0_vreg(dp, rm);
+                    gen_mov_F0_vreg(rm_is_dp, rm);
                     break;
                 }
             } else {
@@ -4047,10 +4076,11 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
                         break;
                     }
                     case 15: /* single<->double conversion */
-                        if (dp)
+                        if (dp) {
                             gen_helper_vfp_fcvtsd(cpu_F0s, cpu_F0d, cpu_env);
-                        else
+                        } else {
                             gen_helper_vfp_fcvtds(cpu_F0d, cpu_F0s, cpu_env);
+                        }
                         break;
                     case 16: /* fuito */
                         gen_vfp_uito(dp, 0);
@@ -4059,27 +4089,15 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
                         gen_vfp_sito(dp, 0);
                         break;
                     case 20: /* fshto */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_shto(dp, 16 - rm, 0);
                         break;
                     case 21: /* fslto */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_slto(dp, 32 - rm, 0);
                         break;
                     case 22: /* fuhto */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_uhto(dp, 16 - rm, 0);
                         break;
                     case 23: /* fulto */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_ulto(dp, 32 - rm, 0);
                         break;
                     case 24: /* ftoui */
@@ -4095,57 +4113,34 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
                         gen_vfp_tosiz(dp, 0);
                         break;
                     case 28: /* ftosh */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_tosh(dp, 16 - rm, 0);
                         break;
                     case 29: /* ftosl */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_tosl(dp, 32 - rm, 0);
                         break;
                     case 30: /* ftouh */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_touh(dp, 16 - rm, 0);
                         break;
                     case 31: /* ftoul */
-                        if (!arm_dc_feature(s, ARM_FEATURE_VFP3)) {
-                            return 1;
-                        }
                         gen_vfp_toul(dp, 32 - rm, 0);
                         break;
                     default: /* undefined */
-                        return 1;
+                        g_assert_not_reached();
                     }
                     break;
                 default: /* undefined */
                     return 1;
                 }
 
-                /* Write back the result.  */
-                if (op == 15 && (rn >= 8 && rn <= 11)) {
-                    /* Comparison, do nothing.  */
-                } else if (op == 15 && dp && ((rn & 0x1c) == 0x18 ||
-                                              (rn & 0x1e) == 0x6)) {
-                    /* VCVT double to int: always integer result.
-                     * VCVT double to half precision is always a single
-                     * precision result.
-                     */
-                    gen_mov_vreg_F0(0, rd);
-                } else if (op == 15 && rn == 15) {
-                    /* conversion */
-                    gen_mov_vreg_F0(!dp, rd);
-                } else {
-                    gen_mov_vreg_F0(dp, rd);
+                /* Write back the result, if any.  */
+                if (!no_output) {
+                    gen_mov_vreg_F0(rd_is_dp, rd);
                 }
 
                 /* break out of the loop if we have finished  */
-                if (veclen == 0)
+                if (veclen == 0) {
                     break;
+                }
 
                 if (op == 15 && delta_m == 0) {
                     /* single source one-many */
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 07/21] target/arm: Implement ARMv8.3-JSConv
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (5 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 06/21] target/arm: Rearrange Floating-point data-processing (2 regs) Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 08/21] hw/misc/tz-ppc: Support having unused ports in the middle of the range Peter Maydell
                   ` (14 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

From: Richard Henderson <richard.henderson@linaro.org>

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190215192302.27855-5-richard.henderson@linaro.org
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
[PMM: fixed a couple of comment typos]
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
 target/arm/cpu.h           | 10 +++++
 target/arm/helper.h        |  3 ++
 target/arm/cpu.c           |  1 +
 target/arm/cpu64.c         |  2 +
 target/arm/translate-a64.c | 26 +++++++++++
 target/arm/translate.c     | 10 +++++
 target/arm/vfp_helper.c    | 88 ++++++++++++++++++++++++++++++++++++++
 7 files changed, 140 insertions(+)

diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 84ae6849c2f..1eea1a408b8 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -3273,6 +3273,11 @@ static inline bool isar_feature_aa32_vcma(const ARMISARegisters *id)
     return FIELD_EX32(id->id_isar5, ID_ISAR5, VCMA) != 0;
 }
 
+static inline bool isar_feature_aa32_jscvt(const ARMISARegisters *id)
+{
+    return FIELD_EX32(id->id_isar6, ID_ISAR6, JSCVT) != 0;
+}
+
 static inline bool isar_feature_aa32_dp(const ARMISARegisters *id)
 {
     return FIELD_EX32(id->id_isar6, ID_ISAR6, DP) != 0;
@@ -3351,6 +3356,11 @@ static inline bool isar_feature_aa64_dp(const ARMISARegisters *id)
     return FIELD_EX64(id->id_aa64isar0, ID_AA64ISAR0, DP) != 0;
 }
 
+static inline bool isar_feature_aa64_jscvt(const ARMISARegisters *id)
+{
+    return FIELD_EX64(id->id_aa64isar1, ID_AA64ISAR1, JSCVT) != 0;
+}
+
 static inline bool isar_feature_aa64_fcma(const ARMISARegisters *id)
 {
     return FIELD_EX64(id->id_aa64isar1, ID_AA64ISAR1, FCMA) != 0;
diff --git a/target/arm/helper.h b/target/arm/helper.h
index 923e8e15255..747cb64d29f 100644
--- a/target/arm/helper.h
+++ b/target/arm/helper.h
@@ -218,6 +218,9 @@ DEF_HELPER_FLAGS_2(rintd_exact, TCG_CALL_NO_RWG, f64, f64, ptr)
 DEF_HELPER_FLAGS_2(rints, TCG_CALL_NO_RWG, f32, f32, ptr)
 DEF_HELPER_FLAGS_2(rintd, TCG_CALL_NO_RWG, f64, f64, ptr)
 
+DEF_HELPER_FLAGS_2(vjcvt, TCG_CALL_NO_RWG, i32, f64, env)
+DEF_HELPER_FLAGS_2(fjcvtzs, TCG_CALL_NO_RWG, i64, f64, ptr)
+
 /* neon_helper.c */
 DEF_HELPER_FLAGS_3(neon_qadd_u8, TCG_CALL_NO_RWG, i32, env, i32, i32)
 DEF_HELPER_FLAGS_3(neon_qadd_s8, TCG_CALL_NO_RWG, i32, env, i32, i32)
diff --git a/target/arm/cpu.c b/target/arm/cpu.c
index edf6e0e1f1c..8ea6569088d 100644
--- a/target/arm/cpu.c
+++ b/target/arm/cpu.c
@@ -2001,6 +2001,7 @@ static void arm_max_initfn(Object *obj)
             cpu->isar.id_isar5 = t;
 
             t = cpu->isar.id_isar6;
+            t = FIELD_DP32(t, ID_ISAR6, JSCVT, 1);
             t = FIELD_DP32(t, ID_ISAR6, DP, 1);
             cpu->isar.id_isar6 = t;
 
diff --git a/target/arm/cpu64.c b/target/arm/cpu64.c
index eff0f164dd0..69e4134f79f 100644
--- a/target/arm/cpu64.c
+++ b/target/arm/cpu64.c
@@ -311,6 +311,7 @@ static void aarch64_max_initfn(Object *obj)
         cpu->isar.id_aa64isar0 = t;
 
         t = cpu->isar.id_aa64isar1;
+        t = FIELD_DP64(t, ID_AA64ISAR1, JSCVT, 1);
         t = FIELD_DP64(t, ID_AA64ISAR1, FCMA, 1);
         t = FIELD_DP64(t, ID_AA64ISAR1, APA, 1); /* PAuth, architected only */
         t = FIELD_DP64(t, ID_AA64ISAR1, API, 0);
@@ -344,6 +345,7 @@ static void aarch64_max_initfn(Object *obj)
         cpu->isar.id_isar5 = u;
 
         u = cpu->isar.id_isar6;
+        u = FIELD_DP32(u, ID_ISAR6, JSCVT, 1);
         u = FIELD_DP32(u, ID_ISAR6, DP, 1);
         cpu->isar.id_isar6 = u;
 
diff --git a/target/arm/translate-a64.c b/target/arm/translate-a64.c
index dbce24fe32c..c56e878787c 100644
--- a/target/arm/translate-a64.c
+++ b/target/arm/translate-a64.c
@@ -6526,6 +6526,24 @@ static void handle_fmov(DisasContext *s, int rd, int rn, int type, bool itof)
     }
 }
 
+static void handle_fjcvtzs(DisasContext *s, int rd, int rn)
+{
+    TCGv_i64 t = read_fp_dreg(s, rn);
+    TCGv_ptr fpstatus = get_fpstatus_ptr(false);
+
+    gen_helper_fjcvtzs(t, t, fpstatus);
+
+    tcg_temp_free_ptr(fpstatus);
+
+    tcg_gen_ext32u_i64(cpu_reg(s, rd), t);
+    tcg_gen_extrh_i64_i32(cpu_ZF, t);
+    tcg_gen_movi_i32(cpu_CF, 0);
+    tcg_gen_movi_i32(cpu_NF, 0);
+    tcg_gen_movi_i32(cpu_VF, 0);
+
+    tcg_temp_free_i64(t);
+}
+
 /* Floating point <-> integer conversions
  *   31   30  29 28       24 23  22  21 20   19 18 16 15         10 9  5 4  0
  * +----+---+---+-----------+------+---+-------+-----+-------------+----+----+
@@ -6601,6 +6619,14 @@ static void disas_fp_int_conv(DisasContext *s, uint32_t insn)
             handle_fmov(s, rd, rn, type, itof);
             break;
 
+        case 0b00111110: /* FJCVTZS */
+            if (!dc_isar_feature(aa64_jscvt, s)) {
+                goto do_unallocated;
+            } else if (fp_access_check(s)) {
+                handle_fjcvtzs(s, rd, rn);
+            }
+            break;
+
         default:
         do_unallocated:
             unallocated_encoding(s);
diff --git a/target/arm/translate.c b/target/arm/translate.c
index 64c5fe0df3e..c1175798ac9 100644
--- a/target/arm/translate.c
+++ b/target/arm/translate.c
@@ -3718,6 +3718,13 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
                     rm_is_dp = false;
                     break;
 
+                case 0x13: /* vjcvt */
+                    if (!dp || !dc_isar_feature(aa32_jscvt, s)) {
+                        return 1;
+                    }
+                    rd_is_dp = false;
+                    break;
+
                 default:
                     return 1;
                 }
@@ -4088,6 +4095,9 @@ static int disas_vfp_insn(DisasContext *s, uint32_t insn)
                     case 17: /* fsito */
                         gen_vfp_sito(dp, 0);
                         break;
+                    case 19: /* vjcvt */
+                        gen_helper_vjcvt(cpu_F0s, cpu_F0d, cpu_env);
+                        break;
                     case 20: /* fshto */
                         gen_vfp_shto(dp, 16 - rm, 0);
                         break;
diff --git a/target/arm/vfp_helper.c b/target/arm/vfp_helper.c
index 74d3030c471..cc7f9f5cb19 100644
--- a/target/arm/vfp_helper.c
+++ b/target/arm/vfp_helper.c
@@ -1086,3 +1086,91 @@ int arm_rmode_to_sf(int rmode)
     }
     return rmode;
 }
+
+/*
+ * Implement float64 to int32_t conversion without saturation;
+ * the result is supplied modulo 2^32.
+ */
+uint64_t HELPER(fjcvtzs)(float64 value, void *vstatus)
+{
+    float_status *status = vstatus;
+    uint32_t exp, sign;
+    uint64_t frac;
+    uint32_t inexact = 1; /* !Z */
+
+    sign = extract64(value, 63, 1);
+    exp = extract64(value, 52, 11);
+    frac = extract64(value, 0, 52);
+
+    if (exp == 0) {
+        /* While not inexact for IEEE FP, -0.0 is inexact for JavaScript.  */
+        inexact = sign;
+        if (frac != 0) {
+            if (status->flush_inputs_to_zero) {
+                float_raise(float_flag_input_denormal, status);
+            } else {
+                float_raise(float_flag_inexact, status);
+                inexact = 1;
+            }
+        }
+        frac = 0;
+    } else if (exp == 0x7ff) {
+        /* This operation raises Invalid for both NaN and overflow (Inf).  */
+        float_raise(float_flag_invalid, status);
+        frac = 0;
+    } else {
+        int true_exp = exp - 1023;
+        int shift = true_exp - 52;
+
+        /* Restore implicit bit.  */
+        frac |= 1ull << 52;
+
+        /* Shift the fraction into place.  */
+        if (shift >= 0) {
+            /* The number is so large we must shift the fraction left.  */
+            if (shift >= 64) {
+                /* The fraction is shifted out entirely.  */
+                frac = 0;
+            } else {
+                frac <<= shift;
+            }
+        } else if (shift > -64) {
+            /* Normal case -- shift right and notice if bits shift out.  */
+            inexact = (frac << (64 + shift)) != 0;
+            frac >>= -shift;
+        } else {
+            /* The fraction is shifted out entirely.  */
+            frac = 0;
+        }
+
+        /* Notice overflow or inexact exceptions.  */
+        if (true_exp > 31 || frac > (sign ? 0x80000000ull : 0x7fffffff)) {
+            /* Overflow, for which this operation raises invalid.  */
+            float_raise(float_flag_invalid, status);
+            inexact = 1;
+        } else if (inexact) {
+            float_raise(float_flag_inexact, status);
+        }
+
+        /* Honor the sign.  */
+        if (sign) {
+            frac = -frac;
+        }
+    }
+
+    /* Pack the result and the env->ZF representation of Z together.  */
+    return deposit64(frac, 32, 32, inexact);
+}
+
+uint32_t HELPER(vjcvt)(float64 value, CPUARMState *env)
+{
+    uint64_t pair = HELPER(fjcvtzs)(value, &env->vfp.fp_status);
+    uint32_t result = pair;
+    uint32_t z = (pair >> 32) == 0;
+
+    /* Store Z, clear NCV, in FPSCR.NZCV.  */
+    env->vfp.xregs[ARM_VFP_FPSCR]
+        = (env->vfp.xregs[ARM_VFP_FPSCR] & ~CPSR_NZCV) | (z * CPSR_Z);
+
+    return result;
+}
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 08/21] hw/misc/tz-ppc: Support having unused ports in the middle of the range
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (6 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 07/21] target/arm: Implement ARMv8.3-JSConv Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 09/21] hw/timer/pl031: Allow use as an embedded-struct device Peter Maydell
                   ` (13 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The Peripheral Protection Controller's handling of unused ports
is that if there is nothing connected to the port's downstream
then it does not create the sysbus MMIO region for the upstream
end of the port. This results in odd behaviour when there is
an unused port in the middle of the range: since sysbus MMIO
regions are implicitly consecutively allocated, any used ports
above the unused ones end up with sysbus MMIO region numbers
that don't match the port number.

Avoid this numbering mismatch by creating dummy MMIO regions
for the unused ports. This doesn't change anything for our
existing boards, which don't have any gaps in the middle of
the port ranges they use; but it will be needed for the Musca
board.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/misc/tz-ppc.h |  8 +++++++-
 hw/misc/tz-ppc.c         | 32 ++++++++++++++++++++++++++++++++
 2 files changed, 39 insertions(+), 1 deletion(-)

diff --git a/include/hw/misc/tz-ppc.h b/include/hw/misc/tz-ppc.h
index fc8b806e4df..080d6e2ec17 100644
--- a/include/hw/misc/tz-ppc.h
+++ b/include/hw/misc/tz-ppc.h
@@ -38,7 +38,13 @@
  *
  * QEMU interface:
  * + sysbus MMIO regions 0..15: MemoryRegions defining the upstream end
- *   of each of the 16 ports of the PPC
+ *   of each of the 16 ports of the PPC. When a port is unused (i.e. no
+ *   downstream MemoryRegion is connected to it) at the end of the 0..15
+ *   range then no sysbus MMIO region is created for its upstream. When an
+ *   unused port lies in the middle of the range with other used ports at
+ *   higher port numbers, a dummy MMIO region is created to ensure that
+ *   port N's upstream is always sysbus MMIO region N. Dummy regions should
+ *   not be mapped, and will assert if any access is made to them.
  * + Property "port[0..15]": MemoryRegion defining the downstream device(s)
  *   for each of the 16 ports of the PPC
  * + Named GPIO inputs "cfg_nonsec[0..15]": set to 1 if the port should be
diff --git a/hw/misc/tz-ppc.c b/hw/misc/tz-ppc.c
index 3dd045c15f5..2e04837bea9 100644
--- a/hw/misc/tz-ppc.c
+++ b/hw/misc/tz-ppc.c
@@ -181,6 +181,21 @@ static const MemoryRegionOps tz_ppc_ops = {
     .endianness = DEVICE_LITTLE_ENDIAN,
 };
 
+static bool tz_ppc_dummy_accepts(void *opaque, hwaddr addr,
+                                 unsigned size, bool is_write,
+                                 MemTxAttrs attrs)
+{
+    /*
+     * Board code should never map the upstream end of an unused port,
+     * so we should never try to make a memory access to it.
+     */
+    g_assert_not_reached();
+}
+
+static const MemoryRegionOps tz_ppc_dummy_ops = {
+    .valid.accepts = tz_ppc_dummy_accepts,
+};
+
 static void tz_ppc_reset(DeviceState *dev)
 {
     TZPPC *s = TZ_PPC(dev);
@@ -210,16 +225,33 @@ static void tz_ppc_realize(DeviceState *dev, Error **errp)
     SysBusDevice *sbd = SYS_BUS_DEVICE(dev);
     TZPPC *s = TZ_PPC(dev);
     int i;
+    int max_port = 0;
 
     /* We can't create the upstream end of the port until realize,
      * as we don't know the size of the MR used as the downstream until then.
      */
     for (i = 0; i < TZ_NUM_PORTS; i++) {
+        if (s->port[i].downstream) {
+            max_port = i;
+        }
+    }
+
+    for (i = 0; i <= max_port; i++) {
         TZPPCPort *port = &s->port[i];
         char *name;
         uint64_t size;
 
         if (!port->downstream) {
+            /*
+             * Create dummy sysbus MMIO region so the sysbus region
+             * numbering doesn't get out of sync with the port numbers.
+             * The size is entirely arbitrary.
+             */
+            name = g_strdup_printf("tz-ppc-dummy-port[%d]", i);
+            memory_region_init_io(&port->upstream, obj, &tz_ppc_dummy_ops,
+                                  port, name, 0x10000);
+            sysbus_init_mmio(sbd, &port->upstream);
+            g_free(name);
             continue;
         }
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 09/21] hw/timer/pl031: Allow use as an embedded-struct device
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (7 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 08/21] hw/misc/tz-ppc: Support having unused ports in the middle of the range Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 10/21] hw/timer/pl031: Convert to using trace events Peter Maydell
                   ` (12 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Create a new include file for the pl031's device struct,
type macros, etc, so that it can be instantiated using
the "embedded struct" coding style.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/timer/pl031.h | 44 ++++++++++++++++++++++++++++++++++++++++
 hw/timer/pl031.c         | 25 +----------------------
 MAINTAINERS              |  1 +
 3 files changed, 46 insertions(+), 24 deletions(-)
 create mode 100644 include/hw/timer/pl031.h

diff --git a/include/hw/timer/pl031.h b/include/hw/timer/pl031.h
new file mode 100644
index 00000000000..99416d8ba52
--- /dev/null
+++ b/include/hw/timer/pl031.h
@@ -0,0 +1,44 @@
+/*
+ * ARM AMBA PrimeCell PL031 RTC
+ *
+ * Copyright (c) 2007 CodeSourcery
+ *
+ * This file is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * Contributions after 2012-01-13 are licensed under the terms of the
+ * GNU GPL, version 2 or (at your option) any later version.
+ */
+
+#ifndef HW_TIMER_PL031
+#define HW_TIMER_PL031
+
+#include "hw/sysbus.h"
+
+#define TYPE_PL031 "pl031"
+#define PL031(obj) OBJECT_CHECK(PL031State, (obj), TYPE_PL031)
+
+typedef struct PL031State {
+    SysBusDevice parent_obj;
+
+    MemoryRegion iomem;
+    QEMUTimer *timer;
+    qemu_irq irq;
+
+    /*
+     * Needed to preserve the tick_count across migration, even if the
+     * absolute value of the rtc_clock is different on the source and
+     * destination.
+     */
+    uint32_t tick_offset_vmstate;
+    uint32_t tick_offset;
+
+    uint32_t mr;
+    uint32_t lr;
+    uint32_t cr;
+    uint32_t im;
+    uint32_t is;
+} PL031State;
+
+#endif
diff --git a/hw/timer/pl031.c b/hw/timer/pl031.c
index d3aacce80da..f774dcd5223 100644
--- a/hw/timer/pl031.c
+++ b/hw/timer/pl031.c
@@ -12,6 +12,7 @@
  */
 
 #include "qemu/osdep.h"
+#include "hw/timer/pl031.h"
 #include "hw/sysbus.h"
 #include "qemu/timer.h"
 #include "sysemu/sysemu.h"
@@ -36,30 +37,6 @@ do { printf("pl031: " fmt , ## __VA_ARGS__); } while (0)
 #define RTC_MIS     0x18    /* Masked interrupt status register */
 #define RTC_ICR     0x1c    /* Interrupt clear register */
 
-#define TYPE_PL031 "pl031"
-#define PL031(obj) OBJECT_CHECK(PL031State, (obj), TYPE_PL031)
-
-typedef struct PL031State {
-    SysBusDevice parent_obj;
-
-    MemoryRegion iomem;
-    QEMUTimer *timer;
-    qemu_irq irq;
-
-    /* Needed to preserve the tick_count across migration, even if the
-     * absolute value of the rtc_clock is different on the source and
-     * destination.
-     */
-    uint32_t tick_offset_vmstate;
-    uint32_t tick_offset;
-
-    uint32_t mr;
-    uint32_t lr;
-    uint32_t cr;
-    uint32_t im;
-    uint32_t is;
-} PL031State;
-
 static const unsigned char pl031_id[] = {
     0x31, 0x10, 0x14, 0x00,         /* Device ID        */
     0x0d, 0xf0, 0x05, 0xb1          /* Cell ID      */
diff --git a/MAINTAINERS b/MAINTAINERS
index b1d786cfd87..db31bc4486c 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -491,6 +491,7 @@ F: hw/sd/pl181.c
 F: hw/ssi/pl022.c
 F: include/hw/ssi/pl022.h
 F: hw/timer/pl031.c
+F: include/hw/timer/pl031.h
 F: include/hw/arm/primecell.h
 F: hw/timer/cmsdk-apb-timer.c
 F: include/hw/timer/cmsdk-apb-timer.h
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 10/21] hw/timer/pl031: Convert to using trace events
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (8 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 09/21] hw/timer/pl031: Allow use as an embedded-struct device Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 11/21] hw/char/pl011: Allow use as an embedded-struct device Peter Maydell
                   ` (11 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Convert the debug printing in the PL031 device to use trace events,
and augment it to cover the interesting parts of device operation.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/timer/pl031.c      | 55 +++++++++++++++++++++++--------------------
 hw/timer/trace-events |  6 +++++
 2 files changed, 36 insertions(+), 25 deletions(-)

diff --git a/hw/timer/pl031.c b/hw/timer/pl031.c
index f774dcd5223..274ad47a33a 100644
--- a/hw/timer/pl031.c
+++ b/hw/timer/pl031.c
@@ -18,15 +18,7 @@
 #include "sysemu/sysemu.h"
 #include "qemu/cutils.h"
 #include "qemu/log.h"
-
-//#define DEBUG_PL031
-
-#ifdef DEBUG_PL031
-#define DPRINTF(fmt, ...) \
-do { printf("pl031: " fmt , ## __VA_ARGS__); } while (0)
-#else
-#define DPRINTF(fmt, ...) do {} while(0)
-#endif
+#include "trace.h"
 
 #define RTC_DR      0x00    /* Data read register */
 #define RTC_MR      0x04    /* Match register */
@@ -44,7 +36,10 @@ static const unsigned char pl031_id[] = {
 
 static void pl031_update(PL031State *s)
 {
-    qemu_set_irq(s->irq, s->is & s->im);
+    uint32_t flags = s->is & s->im;
+
+    trace_pl031_irq_state(flags);
+    qemu_set_irq(s->irq, flags);
 }
 
 static void pl031_interrupt(void * opaque)
@@ -52,7 +47,7 @@ static void pl031_interrupt(void * opaque)
     PL031State *s = (PL031State *)opaque;
 
     s->is = 1;
-    DPRINTF("Alarm raised\n");
+    trace_pl031_alarm_raised();
     pl031_update(s);
 }
 
@@ -69,7 +64,7 @@ static void pl031_set_alarm(PL031State *s)
     /* The timer wraps around.  This subtraction also wraps in the same way,
        and gives correct results when alarm < now_ticks.  */
     ticks = s->mr - pl031_get_count(s);
-    DPRINTF("Alarm set in %ud ticks\n", ticks);
+    trace_pl031_set_alarm(ticks);
     if (ticks == 0) {
         timer_del(s->timer);
         pl031_interrupt(s);
@@ -83,38 +78,49 @@ static uint64_t pl031_read(void *opaque, hwaddr offset,
                            unsigned size)
 {
     PL031State *s = (PL031State *)opaque;
-
-    if (offset >= 0xfe0  &&  offset < 0x1000)
-        return pl031_id[(offset - 0xfe0) >> 2];
+    uint64_t r;
 
     switch (offset) {
     case RTC_DR:
-        return pl031_get_count(s);
+        r = pl031_get_count(s);
+        break;
     case RTC_MR:
-        return s->mr;
+        r = s->mr;
+        break;
     case RTC_IMSC:
-        return s->im;
+        r = s->im;
+        break;
     case RTC_RIS:
-        return s->is;
+        r = s->is;
+        break;
     case RTC_LR:
-        return s->lr;
+        r = s->lr;
+        break;
     case RTC_CR:
         /* RTC is permanently enabled.  */
-        return 1;
+        r = 1;
+        break;
     case RTC_MIS:
-        return s->is & s->im;
+        r = s->is & s->im;
+        break;
+    case 0xfe0 ... 0xfff:
+        r = pl031_id[(offset - 0xfe0) >> 2];
+        break;
     case RTC_ICR:
         qemu_log_mask(LOG_GUEST_ERROR,
                       "pl031: read of write-only register at offset 0x%x\n",
                       (int)offset);
+        r = 0;
         break;
     default:
         qemu_log_mask(LOG_GUEST_ERROR,
                       "pl031_read: Bad offset 0x%x\n", (int)offset);
+        r = 0;
         break;
     }
 
-    return 0;
+    trace_pl031_read(offset, r);
+    return r;
 }
 
 static void pl031_write(void * opaque, hwaddr offset,
@@ -122,6 +128,7 @@ static void pl031_write(void * opaque, hwaddr offset,
 {
     PL031State *s = (PL031State *)opaque;
 
+    trace_pl031_write(offset, value);
 
     switch (offset) {
     case RTC_LR:
@@ -134,7 +141,6 @@ static void pl031_write(void * opaque, hwaddr offset,
         break;
     case RTC_IMSC:
         s->im = value & 1;
-        DPRINTF("Interrupt mask %d\n", s->im);
         pl031_update(s);
         break;
     case RTC_ICR:
@@ -142,7 +148,6 @@ static void pl031_write(void * opaque, hwaddr offset,
            cleared when bit 0 of the written value is set.  However the
            arm926e documentation (DDI0287B) states that the interrupt is
            cleared when any value is written.  */
-        DPRINTF("Interrupt cleared");
         s->is = 0;
         pl031_update(s);
         break;
diff --git a/hw/timer/trace-events b/hw/timer/trace-events
index 0144a68951c..12eb505fee7 100644
--- a/hw/timer/trace-events
+++ b/hw/timer/trace-events
@@ -77,3 +77,9 @@ xlnx_zynqmp_rtc_gettime(int year, int month, int day, int hour, int min, int sec
 nrf51_timer_read(uint64_t addr, uint32_t value, unsigned size) "read addr 0x%" PRIx64 " data 0x%" PRIx32 " size %u"
 nrf51_timer_write(uint64_t addr, uint32_t value, unsigned size) "write addr 0x%" PRIx64 " data 0x%" PRIx32 " size %u"
 
+# hw/timer/pl031.c
+pl031_irq_state(int level) "irq state %d"
+pl031_read(uint32_t addr, uint32_t value) "addr 0x%08x value 0x%08x"
+pl031_write(uint32_t addr, uint32_t value) "addr 0x%08x value 0x%08x"
+pl031_alarm_raised(void) "alarm raised"
+pl031_set_alarm(uint32_t ticks) "alarm set for %u ticks"
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 11/21] hw/char/pl011: Allow use as an embedded-struct device
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (9 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 10/21] hw/timer/pl031: Convert to using trace events Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 12/21] hw/char/pl011: Support all interrupt lines Peter Maydell
                   ` (10 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Create a new include file for the pl011's device struct,
type macros, etc, so that it can be instantiated using
the "embedded struct" coding style.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/char/pl011.h | 34 ++++++++++++++++++++++++++++++++++
 hw/char/pl011.c         | 31 ++-----------------------------
 2 files changed, 36 insertions(+), 29 deletions(-)

diff --git a/include/hw/char/pl011.h b/include/hw/char/pl011.h
index 83649324b6a..1b52bfd5c90 100644
--- a/include/hw/char/pl011.h
+++ b/include/hw/char/pl011.h
@@ -15,6 +15,40 @@
 #ifndef HW_PL011_H
 #define HW_PL011_H
 
+#include "hw/sysbus.h"
+#include "chardev/char-fe.h"
+
+#define TYPE_PL011 "pl011"
+#define PL011(obj) OBJECT_CHECK(PL011State, (obj), TYPE_PL011)
+
+/* This shares the same struct (and cast macro) as the base pl011 device */
+#define TYPE_PL011_LUMINARY "pl011_luminary"
+
+typedef struct PL011State {
+    SysBusDevice parent_obj;
+
+    MemoryRegion iomem;
+    uint32_t readbuff;
+    uint32_t flags;
+    uint32_t lcr;
+    uint32_t rsr;
+    uint32_t cr;
+    uint32_t dmacr;
+    uint32_t int_enabled;
+    uint32_t int_level;
+    uint32_t read_fifo[16];
+    uint32_t ilpr;
+    uint32_t ibrd;
+    uint32_t fbrd;
+    uint32_t ifl;
+    int read_pos;
+    int read_count;
+    int read_trigger;
+    CharBackend chr;
+    qemu_irq irq;
+    const unsigned char *id;
+} PL011State;
+
 static inline DeviceState *pl011_create(hwaddr addr,
                                         qemu_irq irq,
                                         Chardev *chr)
diff --git a/hw/char/pl011.c b/hw/char/pl011.c
index 2aa277fc4f2..0c4711e4027 100644
--- a/hw/char/pl011.c
+++ b/hw/char/pl011.c
@@ -8,39 +8,12 @@
  */
 
 #include "qemu/osdep.h"
+#include "hw/char/pl011.h"
 #include "hw/sysbus.h"
 #include "chardev/char-fe.h"
 #include "qemu/log.h"
 #include "trace.h"
 
-#define TYPE_PL011 "pl011"
-#define PL011(obj) OBJECT_CHECK(PL011State, (obj), TYPE_PL011)
-
-typedef struct PL011State {
-    SysBusDevice parent_obj;
-
-    MemoryRegion iomem;
-    uint32_t readbuff;
-    uint32_t flags;
-    uint32_t lcr;
-    uint32_t rsr;
-    uint32_t cr;
-    uint32_t dmacr;
-    uint32_t int_enabled;
-    uint32_t int_level;
-    uint32_t read_fifo[16];
-    uint32_t ilpr;
-    uint32_t ibrd;
-    uint32_t fbrd;
-    uint32_t ifl;
-    int read_pos;
-    int read_count;
-    int read_trigger;
-    CharBackend chr;
-    qemu_irq irq;
-    const unsigned char *id;
-} PL011State;
-
 #define PL011_INT_TX 0x20
 #define PL011_INT_RX 0x10
 
@@ -357,7 +330,7 @@ static void pl011_luminary_init(Object *obj)
 }
 
 static const TypeInfo pl011_luminary_info = {
-    .name          = "pl011_luminary",
+    .name          = TYPE_PL011_LUMINARY,
     .parent        = TYPE_PL011,
     .instance_init = pl011_luminary_init,
 };
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 12/21] hw/char/pl011: Support all interrupt lines
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (10 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 11/21] hw/char/pl011: Allow use as an embedded-struct device Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 13/21] hw/char/pl011: Use '0x' prefix when logging hex numbers Peter Maydell
                   ` (9 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The PL011 UART has six interrupt lines:
 * RX (receive data)
 * TX (transmit data)
 * RT (receive timeout)
 * MS (modem status)
 * E (errors)
 * combined (logical OR of all the above)

So far we have only emulated the combined interrupt line;
add support for the others, so that boards that wire them
up to different interrupt controller inputs can do so.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/char/pl011.h |  2 +-
 hw/char/pl011.c         | 46 +++++++++++++++++++++++++++++++++++++++--
 2 files changed, 45 insertions(+), 3 deletions(-)

diff --git a/include/hw/char/pl011.h b/include/hw/char/pl011.h
index 1b52bfd5c90..dad3cf29121 100644
--- a/include/hw/char/pl011.h
+++ b/include/hw/char/pl011.h
@@ -45,7 +45,7 @@ typedef struct PL011State {
     int read_count;
     int read_trigger;
     CharBackend chr;
-    qemu_irq irq;
+    qemu_irq irq[6];
     const unsigned char *id;
 } PL011State;
 
diff --git a/hw/char/pl011.c b/hw/char/pl011.c
index 0c4711e4027..29f4e5eb224 100644
--- a/hw/char/pl011.c
+++ b/hw/char/pl011.c
@@ -7,6 +7,17 @@
  * This code is licensed under the GPL.
  */
 
+/*
+ * QEMU interface:
+ *  + sysbus MMIO region 0: device registers
+ *  + sysbus IRQ 0: UARTINTR (combined interrupt line)
+ *  + sysbus IRQ 1: UARTRXINTR (receive FIFO interrupt line)
+ *  + sysbus IRQ 2: UARTTXINTR (transmit FIFO interrupt line)
+ *  + sysbus IRQ 3: UARTRTINTR (receive timeout interrupt line)
+ *  + sysbus IRQ 4: UARTMSINTR (momem status interrupt line)
+ *  + sysbus IRQ 5: UARTEINTR (error interrupt line)
+ */
+
 #include "qemu/osdep.h"
 #include "hw/char/pl011.h"
 #include "hw/sysbus.h"
@@ -22,18 +33,46 @@
 #define PL011_FLAG_TXFF 0x20
 #define PL011_FLAG_RXFE 0x10
 
+/* Interrupt status bits in UARTRIS, UARTMIS, UARTIMSC */
+#define INT_OE (1 << 10)
+#define INT_BE (1 << 9)
+#define INT_PE (1 << 8)
+#define INT_FE (1 << 7)
+#define INT_RT (1 << 6)
+#define INT_TX (1 << 5)
+#define INT_RX (1 << 4)
+#define INT_DSR (1 << 3)
+#define INT_DCD (1 << 2)
+#define INT_CTS (1 << 1)
+#define INT_RI (1 << 0)
+#define INT_E (INT_OE | INT_BE | INT_PE | INT_FE)
+#define INT_MS (INT_RI | INT_DSR | INT_DCD | INT_CTS)
+
 static const unsigned char pl011_id_arm[8] =
   { 0x11, 0x10, 0x14, 0x00, 0x0d, 0xf0, 0x05, 0xb1 };
 static const unsigned char pl011_id_luminary[8] =
   { 0x11, 0x00, 0x18, 0x01, 0x0d, 0xf0, 0x05, 0xb1 };
 
+/* Which bits in the interrupt status matter for each outbound IRQ line ? */
+static const uint32_t irqmask[] = {
+    INT_E | INT_MS | INT_RT | INT_TX | INT_RX, /* combined IRQ */
+    INT_RX,
+    INT_TX,
+    INT_RT,
+    INT_MS,
+    INT_E,
+};
+
 static void pl011_update(PL011State *s)
 {
     uint32_t flags;
+    int i;
 
     flags = s->int_level & s->int_enabled;
     trace_pl011_irq_state(flags != 0);
-    qemu_set_irq(s->irq, flags != 0);
+    for (i = 0; i < ARRAY_SIZE(s->irq); i++) {
+        qemu_set_irq(s->irq[i], (flags & irqmask[i]) != 0);
+    }
 }
 
 static uint64_t pl011_read(void *opaque, hwaddr offset,
@@ -284,10 +323,13 @@ static void pl011_init(Object *obj)
 {
     SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
     PL011State *s = PL011(obj);
+    int i;
 
     memory_region_init_io(&s->iomem, OBJECT(s), &pl011_ops, s, "pl011", 0x1000);
     sysbus_init_mmio(sbd, &s->iomem);
-    sysbus_init_irq(sbd, &s->irq);
+    for (i = 0; i < ARRAY_SIZE(s->irq); i++) {
+        sysbus_init_irq(sbd, &s->irq[i]);
+    }
 
     s->read_trigger = 1;
     s->ifl = 0x12;
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 13/21] hw/char/pl011: Use '0x' prefix when logging hex numbers
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (11 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 12/21] hw/char/pl011: Support all interrupt lines Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 14/21] hw/arm/armsse: Document SRAM_ADDR_WIDTH property in header comment Peter Maydell
                   ` (8 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The pl011 logs when the guest makes a bad access. It prints
the address offset in hex but confusingly omits the '0x'
prefix; add it.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/char/pl011.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/hw/char/pl011.c b/hw/char/pl011.c
index 29f4e5eb224..e5dd448f854 100644
--- a/hw/char/pl011.c
+++ b/hw/char/pl011.c
@@ -143,7 +143,7 @@ static uint64_t pl011_read(void *opaque, hwaddr offset,
         break;
     default:
         qemu_log_mask(LOG_GUEST_ERROR,
-                      "pl011_read: Bad offset %x\n", (int)offset);
+                      "pl011_read: Bad offset 0x%x\n", (int)offset);
         r = 0;
         break;
     }
@@ -232,7 +232,7 @@ static void pl011_write(void *opaque, hwaddr offset,
         break;
     default:
         qemu_log_mask(LOG_GUEST_ERROR,
-                      "pl011_write: Bad offset %x\n", (int)offset);
+                      "pl011_write: Bad offset 0x%x\n", (int)offset);
     }
 }
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 14/21] hw/arm/armsse: Document SRAM_ADDR_WIDTH property in header comment
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (12 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 13/21] hw/char/pl011: Use '0x' prefix when logging hex numbers Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 15/21] hw/arm/armsse: Allow boards to specify init-svtor Peter Maydell
                   ` (7 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

In commit 4b635cf7a95e501211 we added a QOM property to the ARMSSE
object, but forgot to add it to the documentation comment in the
header. Correct the omission.

Fixes: 4b635cf7a95e501211 ("hw/arm/armsse: Make SRAM bank size configurable")
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/arm/armsse.h | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/include/hw/arm/armsse.h b/include/hw/arm/armsse.h
index f800bafb14a..444605b44dc 100644
--- a/include/hw/arm/armsse.h
+++ b/include/hw/arm/armsse.h
@@ -46,6 +46,8 @@
  *    being the same for both, to avoid having to have separate Property
  *    lists for different variants. This restriction can be relaxed later
  *    if necessary.)
+ *  + QOM property "SRAM_ADDR_WIDTH" sets the number of bits used for the
+ *    address of each SRAM bank (and thus the total amount of internal SRAM)
  *  + Named GPIO inputs "EXP_IRQ" 0..n are the expansion interrupts for CPU 0,
  *    which are wired to its NVIC lines 32 .. n+32
  *  + Named GPIO inputs "EXP_CPU1_IRQ" 0..n are the expansion interrupts for
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 15/21] hw/arm/armsse: Allow boards to specify init-svtor
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (13 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 14/21] hw/arm/armsse: Document SRAM_ADDR_WIDTH property in header comment Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 16/21] hw/arm/musca.c: Implement models of the Musca-A and -B1 boards Peter Maydell
                   ` (6 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The Musca boards have DAPLink firmware that sets the initial
secure VTOR value (the location of the vector table) differently
depending on the boot mode (from flash, from RAM, etc). Export
the init-svtor as a QOM property of the ARMSSE object so that
the board can change it.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 include/hw/arm/armsse.h | 3 +++
 hw/arm/armsse.c         | 8 ++++----
 2 files changed, 7 insertions(+), 4 deletions(-)

diff --git a/include/hw/arm/armsse.h b/include/hw/arm/armsse.h
index 444605b44dc..84879f40dd8 100644
--- a/include/hw/arm/armsse.h
+++ b/include/hw/arm/armsse.h
@@ -48,6 +48,8 @@
  *    if necessary.)
  *  + QOM property "SRAM_ADDR_WIDTH" sets the number of bits used for the
  *    address of each SRAM bank (and thus the total amount of internal SRAM)
+ *  + QOM property "init-svtor" sets the initial value of the CPU SVTOR register
+ *    (where it expects to load the PC and SP from the vector table on reset)
  *  + Named GPIO inputs "EXP_IRQ" 0..n are the expansion interrupts for CPU 0,
  *    which are wired to its NVIC lines 32 .. n+32
  *  + Named GPIO inputs "EXP_CPU1_IRQ" 0..n are the expansion interrupts for
@@ -204,6 +206,7 @@ typedef struct ARMSSE {
     uint32_t exp_numirq;
     uint32_t mainclk_frq;
     uint32_t sram_addr_width;
+    uint32_t init_svtor;
 } ARMSSE;
 
 typedef struct ARMSSEInfo ARMSSEInfo;
diff --git a/hw/arm/armsse.c b/hw/arm/armsse.c
index d0207dbabc7..50da41f64c5 100644
--- a/hw/arm/armsse.c
+++ b/hw/arm/armsse.c
@@ -505,11 +505,10 @@ static void armsse_realize(DeviceState *dev, Error **errp)
          * the INITSVTOR* registers before powering up the CPUs in any case,
          * so the hardware's default value doesn't matter. QEMU doesn't emulate
          * the control processor, so instead we behave in the way that the
-         * firmware does. All boards currently known about have firmware that
-         * sets the INITSVTOR0 and INITSVTOR1 registers to 0x10000000, like the
-         * IoTKit default. We can make this more configurable if necessary.
+         * firmware does. The initial value is configurable by the board code
+         * to match whatever its firmware does.
          */
-        qdev_prop_set_uint32(cpudev, "init-svtor", 0x10000000);
+        qdev_prop_set_uint32(cpudev, "init-svtor", s->init_svtor);
         /*
          * Start all CPUs except CPU0 powered down. In real hardware it is
          * a configurable property of the SSE-200 which CPUs start powered up
@@ -1187,6 +1186,7 @@ static Property armsse_properties[] = {
     DEFINE_PROP_UINT32("EXP_NUMIRQ", ARMSSE, exp_numirq, 64),
     DEFINE_PROP_UINT32("MAINCLK", ARMSSE, mainclk_frq, 0),
     DEFINE_PROP_UINT32("SRAM_ADDR_WIDTH", ARMSSE, sram_addr_width, 15),
+    DEFINE_PROP_UINT32("init-svtor", ARMSSE, init_svtor, 0x10000000),
     DEFINE_PROP_END_OF_LIST()
 };
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 16/21] hw/arm/musca.c: Implement models of the Musca-A and -B1 boards
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (14 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 15/21] hw/arm/armsse: Allow boards to specify init-svtor Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 17/21] hw/arm/musca: Add PPCs Peter Maydell
                   ` (5 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The Musca-A and Musca-B1 development boards are based on the
SSE-200 subsystem for embedded. Implement an initial skeleton
model of these boards, which are similar but not identical.

This commit creates the board model with the SSE and the IRQ
splitters to wire IRQs up to its two CPUs. As yet there
are no devices and no memory: these will be added later.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/arm/Makefile.objs            |   1 +
 hw/arm/musca.c                  | 197 ++++++++++++++++++++++++++++++++
 MAINTAINERS                     |   6 +
 default-configs/arm-softmmu.mak |   1 +
 4 files changed, 205 insertions(+)
 create mode 100644 hw/arm/musca.c

diff --git a/hw/arm/Makefile.objs b/hw/arm/Makefile.objs
index fa40e8d6412..fa57c7c7704 100644
--- a/hw/arm/Makefile.objs
+++ b/hw/arm/Makefile.objs
@@ -35,6 +35,7 @@ obj-$(CONFIG_ASPEED_SOC) += aspeed_soc.o aspeed.o
 obj-$(CONFIG_MPS2) += mps2.o
 obj-$(CONFIG_MPS2) += mps2-tz.o
 obj-$(CONFIG_MSF2) += msf2-soc.o msf2-som.o
+obj-$(CONFIG_MUSCA) += musca.o
 obj-$(CONFIG_ARMSSE) += armsse.o
 obj-$(CONFIG_FSL_IMX7) += fsl-imx7.o mcimx7d-sabre.o
 obj-$(CONFIG_ARM_SMMUV3) += smmu-common.o smmuv3.o
diff --git a/hw/arm/musca.c b/hw/arm/musca.c
new file mode 100644
index 00000000000..cc624c7d160
--- /dev/null
+++ b/hw/arm/musca.c
@@ -0,0 +1,197 @@
+/*
+ * Arm Musca-B1 test chip board emulation
+ *
+ * Copyright (c) 2019 Linaro Limited
+ * Written by Peter Maydell
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License version 2 or
+ *  (at your option) any later version.
+ */
+
+/*
+ * The Musca boards are a reference implementation of a system using
+ * the SSE-200 subsystem for embedded:
+ * https://developer.arm.com/products/system-design/development-boards/iot-test-chips-and-boards/musca-a-test-chip-board
+ * https://developer.arm.com/products/system-design/development-boards/iot-test-chips-and-boards/musca-b-test-chip-board
+ * We model the A and B1 variants of this board, as described in the TRMs:
+ * http://infocenter.arm.com/help/topic/com.arm.doc.101107_0000_00_en/index.html
+ * http://infocenter.arm.com/help/topic/com.arm.doc.101312_0000_00_en/index.html
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/error-report.h"
+#include "qapi/error.h"
+#include "exec/address-spaces.h"
+#include "hw/arm/arm.h"
+#include "hw/arm/armsse.h"
+#include "hw/boards.h"
+#include "hw/core/split-irq.h"
+
+#define MUSCA_NUMIRQ_MAX 96
+
+typedef enum MuscaType {
+    MUSCA_A,
+    MUSCA_B1,
+} MuscaType;
+
+typedef struct {
+    MachineClass parent;
+    MuscaType type;
+    uint32_t init_svtor;
+    int sram_addr_width;
+    int num_irqs;
+} MuscaMachineClass;
+
+typedef struct {
+    MachineState parent;
+
+    ARMSSE sse;
+    SplitIRQ cpu_irq_splitter[MUSCA_NUMIRQ_MAX];
+} MuscaMachineState;
+
+#define TYPE_MUSCA_MACHINE "musca"
+#define TYPE_MUSCA_A_MACHINE MACHINE_TYPE_NAME("musca-a")
+#define TYPE_MUSCA_B1_MACHINE MACHINE_TYPE_NAME("musca-b1")
+
+#define MUSCA_MACHINE(obj) \
+    OBJECT_CHECK(MuscaMachineState, obj, TYPE_MUSCA_MACHINE)
+#define MUSCA_MACHINE_GET_CLASS(obj) \
+    OBJECT_GET_CLASS(MuscaMachineClass, obj, TYPE_MUSCA_MACHINE)
+#define MUSCA_MACHINE_CLASS(klass) \
+    OBJECT_CLASS_CHECK(MuscaMachineClass, klass, TYPE_MUSCA_MACHINE)
+
+/*
+ * Main SYSCLK frequency in Hz
+ * TODO this should really be different for the two cores, but we
+ * don't model that in our SSE-200 model yet.
+ */
+#define SYSCLK_FRQ 40000000
+
+static void musca_init(MachineState *machine)
+{
+    MuscaMachineState *mms = MUSCA_MACHINE(machine);
+    MuscaMachineClass *mmc = MUSCA_MACHINE_GET_CLASS(mms);
+    MachineClass *mc = MACHINE_GET_CLASS(machine);
+    MemoryRegion *system_memory = get_system_memory();
+    DeviceState *ssedev;
+    int i;
+
+    assert(mmc->num_irqs <= MUSCA_NUMIRQ_MAX);
+
+    if (strcmp(machine->cpu_type, mc->default_cpu_type) != 0) {
+        error_report("This board can only be used with CPU %s",
+                     mc->default_cpu_type);
+        exit(1);
+    }
+
+    sysbus_init_child_obj(OBJECT(machine), "sse-200", &mms->sse,
+                          sizeof(mms->sse), TYPE_SSE200);
+    ssedev = DEVICE(&mms->sse);
+    object_property_set_link(OBJECT(&mms->sse), OBJECT(system_memory),
+                             "memory", &error_fatal);
+    qdev_prop_set_uint32(ssedev, "EXP_NUMIRQ", mmc->num_irqs);
+    qdev_prop_set_uint32(ssedev, "init-svtor", mmc->init_svtor);
+    qdev_prop_set_uint32(ssedev, "SRAM_ADDR_WIDTH", mmc->sram_addr_width);
+    qdev_prop_set_uint32(ssedev, "MAINCLK", SYSCLK_FRQ);
+    object_property_set_bool(OBJECT(&mms->sse), true, "realized",
+                             &error_fatal);
+
+    /*
+     * We need to create splitters to feed the IRQ inputs
+     * for each CPU in the SSE-200 from each device in the board.
+     */
+    for (i = 0; i < mmc->num_irqs; i++) {
+        char *name = g_strdup_printf("musca-irq-splitter%d", i);
+        SplitIRQ *splitter = &mms->cpu_irq_splitter[i];
+
+        object_initialize_child(OBJECT(machine), name,
+                                splitter, sizeof(*splitter),
+                                TYPE_SPLIT_IRQ, &error_fatal, NULL);
+        g_free(name);
+
+        object_property_set_int(OBJECT(splitter), 2, "num-lines",
+                                &error_fatal);
+        object_property_set_bool(OBJECT(splitter), true, "realized",
+                                 &error_fatal);
+        qdev_connect_gpio_out(DEVICE(splitter), 0,
+                              qdev_get_gpio_in_named(ssedev, "EXP_IRQ", i));
+        qdev_connect_gpio_out(DEVICE(splitter), 1,
+                              qdev_get_gpio_in_named(ssedev,
+                                                     "EXP_CPU1_IRQ", i));
+    }
+
+    armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename, 0x2000000);
+}
+
+static void musca_class_init(ObjectClass *oc, void *data)
+{
+    MachineClass *mc = MACHINE_CLASS(oc);
+
+    mc->default_cpus = 2;
+    mc->min_cpus = mc->default_cpus;
+    mc->max_cpus = mc->default_cpus;
+    mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-m33");
+    mc->init = musca_init;
+}
+
+static void musca_a_class_init(ObjectClass *oc, void *data)
+{
+    MachineClass *mc = MACHINE_CLASS(oc);
+    MuscaMachineClass *mmc = MUSCA_MACHINE_CLASS(oc);
+
+    mc->desc = "ARM Musca-A board (dual Cortex-M33)";
+    mmc->type = MUSCA_A;
+    mmc->init_svtor = 0x10200000;
+    mmc->sram_addr_width = 15;
+    mmc->num_irqs = 64;
+}
+
+static void musca_b1_class_init(ObjectClass *oc, void *data)
+{
+    MachineClass *mc = MACHINE_CLASS(oc);
+    MuscaMachineClass *mmc = MUSCA_MACHINE_CLASS(oc);
+
+    mc->desc = "ARM Musca-B1 board (dual Cortex-M33)";
+    mmc->type = MUSCA_B1;
+    /*
+     * This matches the DAPlink firmware which boots from QSPI. There
+     * is also a firmware blob which boots from the eFlash, which
+     * uses init_svtor = 0x1A000000. QEMU doesn't currently support that,
+     * though we could in theory expose a machine property on the command
+     * line to allow the user to request eFlash boot.
+     */
+    mmc->init_svtor = 0x10000000;
+    mmc->sram_addr_width = 17;
+    mmc->num_irqs = 96;
+}
+
+static const TypeInfo musca_info = {
+    .name = TYPE_MUSCA_MACHINE,
+    .parent = TYPE_MACHINE,
+    .abstract = true,
+    .instance_size = sizeof(MuscaMachineState),
+    .class_size = sizeof(MuscaMachineClass),
+    .class_init = musca_class_init,
+};
+
+static const TypeInfo musca_a_info = {
+    .name = TYPE_MUSCA_A_MACHINE,
+    .parent = TYPE_MUSCA_MACHINE,
+    .class_init = musca_a_class_init,
+};
+
+static const TypeInfo musca_b1_info = {
+    .name = TYPE_MUSCA_B1_MACHINE,
+    .parent = TYPE_MUSCA_MACHINE,
+    .class_init = musca_b1_class_init,
+};
+
+static void musca_machine_init(void)
+{
+    type_register_static(&musca_info);
+    type_register_static(&musca_a_info);
+    type_register_static(&musca_b1_info);
+}
+
+type_init(musca_machine_init);
diff --git a/MAINTAINERS b/MAINTAINERS
index db31bc4486c..6ae55ff7323 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -634,6 +634,12 @@ F: include/hw/misc/iotkit-sysinfo.h
 F: hw/misc/armsse-cpuid.c
 F: include/hw/misc/armsse-cpuid.h
 
+Musca
+M: Peter Maydell <peter.maydell@linaro.org>
+L: qemu-arm@nongnu.org
+S: Maintained
+F: hw/arm/musca.c
+
 Musicpal
 M: Jan Kiszka <jan.kiszka@web.de>
 M: Peter Maydell <peter.maydell@linaro.org>
diff --git a/default-configs/arm-softmmu.mak b/default-configs/arm-softmmu.mak
index 734ca721e9e..87ad2674946 100644
--- a/default-configs/arm-softmmu.mak
+++ b/default-configs/arm-softmmu.mak
@@ -89,6 +89,7 @@ CONFIG_TUSB6010=y
 CONFIG_IMX=y
 CONFIG_MAINSTONE=y
 CONFIG_MPS2=y
+CONFIG_MUSCA=y
 CONFIG_NSERIES=y
 CONFIG_RASPI=y
 CONFIG_REALVIEW=y
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 17/21] hw/arm/musca: Add PPCs
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (15 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 16/21] hw/arm/musca.c: Implement models of the Musca-A and -B1 boards Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 18/21] hw/arm/musca: Add MPCs Peter Maydell
                   ` (4 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Many of the devices on the Musca board live behind TrustZone
Peripheral Protection Controllers (PPCs); add models of the
PPCs, using a similar scheme to the MPS2 board models.
This commit wires up the PPCs with "unimplemented device"
stubs behind them in the correct places in the address map.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/arm/musca.c | 289 +++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 289 insertions(+)

diff --git a/hw/arm/musca.c b/hw/arm/musca.c
index cc624c7d160..8774e0b87b7 100644
--- a/hw/arm/musca.c
+++ b/hw/arm/musca.c
@@ -27,8 +27,11 @@
 #include "hw/arm/armsse.h"
 #include "hw/boards.h"
 #include "hw/core/split-irq.h"
+#include "hw/misc/tz-ppc.h"
+#include "hw/misc/unimp.h"
 
 #define MUSCA_NUMIRQ_MAX 96
+#define MUSCA_PPC_MAX 3
 
 typedef enum MuscaType {
     MUSCA_A,
@@ -48,6 +51,24 @@ typedef struct {
 
     ARMSSE sse;
     SplitIRQ cpu_irq_splitter[MUSCA_NUMIRQ_MAX];
+    SplitIRQ sec_resp_splitter;
+    TZPPC ppc[MUSCA_PPC_MAX];
+    MemoryRegion container;
+    UnimplementedDeviceState eflash[2];
+    UnimplementedDeviceState qspi;
+    UnimplementedDeviceState mpc[5];
+    UnimplementedDeviceState mhu[2];
+    UnimplementedDeviceState pwm[3];
+    UnimplementedDeviceState i2s;
+    UnimplementedDeviceState uart[2];
+    UnimplementedDeviceState i2c[2];
+    UnimplementedDeviceState spi;
+    UnimplementedDeviceState scc;
+    UnimplementedDeviceState timer;
+    UnimplementedDeviceState rtc;
+    UnimplementedDeviceState pvt;
+    UnimplementedDeviceState sdio;
+    UnimplementedDeviceState gpio;
 } MuscaMachineState;
 
 #define TYPE_MUSCA_MACHINE "musca"
@@ -68,6 +89,94 @@ typedef struct {
  */
 #define SYSCLK_FRQ 40000000
 
+/*
+ * Most of the devices in the Musca board sit behind Peripheral Protection
+ * Controllers. These data structures define the layout of which devices
+ * sit behind which PPCs.
+ * The devfn for each port is a function which creates, configures
+ * and initializes the device, returning the MemoryRegion which
+ * needs to be plugged into the downstream end of the PPC port.
+ */
+typedef MemoryRegion *MakeDevFn(MuscaMachineState *mms, void *opaque,
+                                const char *name, hwaddr size);
+
+typedef struct PPCPortInfo {
+    const char *name;
+    MakeDevFn *devfn;
+    void *opaque;
+    hwaddr addr;
+    hwaddr size;
+} PPCPortInfo;
+
+typedef struct PPCInfo {
+    const char *name;
+    PPCPortInfo ports[TZ_NUM_PORTS];
+} PPCInfo;
+
+static MemoryRegion *make_unimp_dev(MuscaMachineState *mms,
+                                    void *opaque, const char *name, hwaddr size)
+{
+    /*
+     * Initialize, configure and realize a TYPE_UNIMPLEMENTED_DEVICE,
+     * and return a pointer to its MemoryRegion.
+     */
+    UnimplementedDeviceState *uds = opaque;
+
+    sysbus_init_child_obj(OBJECT(mms), name, uds,
+                          sizeof(UnimplementedDeviceState),
+                          TYPE_UNIMPLEMENTED_DEVICE);
+    qdev_prop_set_string(DEVICE(uds), "name", name);
+    qdev_prop_set_uint64(DEVICE(uds), "size", size);
+    object_property_set_bool(OBJECT(uds), true, "realized", &error_fatal);
+    return sysbus_mmio_get_region(SYS_BUS_DEVICE(uds), 0);
+}
+
+static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
+                                       const char *name, hwaddr size)
+{
+    /*
+     * Create the container MemoryRegion for all the devices that live
+     * behind the Musca-A PPC's single port. These devices don't have a PPC
+     * port each, but we use the PPCPortInfo struct as a convenient way
+     * to describe them. Note that addresses here are relative to the base
+     * address of the PPC port region: 0x40100000, and devices appear both
+     * at the 0x4... NS region and the 0x5... S region.
+     */
+    int i;
+    MemoryRegion *container = &mms->container;
+
+    const PPCPortInfo devices[] = {
+        { "uart0", make_unimp_dev, &mms->uart[0], 0x1000, 0x1000 },
+        { "uart1", make_unimp_dev, &mms->uart[1], 0x2000, 0x1000 },
+        { "spi", make_unimp_dev, &mms->spi, 0x3000, 0x1000 },
+        { "i2c0", make_unimp_dev, &mms->i2c[0], 0x4000, 0x1000 },
+        { "i2c1", make_unimp_dev, &mms->i2c[1], 0x5000, 0x1000 },
+        { "i2s", make_unimp_dev, &mms->i2s, 0x6000, 0x1000 },
+        { "pwm0", make_unimp_dev, &mms->pwm[0], 0x7000, 0x1000 },
+        { "rtc", make_unimp_dev, &mms->rtc, 0x8000, 0x1000 },
+        { "qspi", make_unimp_dev, &mms->qspi, 0xa000, 0x1000 },
+        { "timer", make_unimp_dev, &mms->timer, 0xb000, 0x1000 },
+        { "scc", make_unimp_dev, &mms->scc, 0xc000, 0x1000 },
+        { "pwm1", make_unimp_dev, &mms->pwm[1], 0xe000, 0x1000 },
+        { "pwm2", make_unimp_dev, &mms->pwm[2], 0xf000, 0x1000 },
+        { "gpio", make_unimp_dev, &mms->gpio, 0x10000, 0x1000 },
+        { "mpc0", make_unimp_dev, &mms->mpc[0], 0x12000, 0x1000 },
+        { "mpc1", make_unimp_dev, &mms->mpc[1], 0x13000, 0x1000 },
+    };
+
+    memory_region_init(container, OBJECT(mms), "musca-device-container", size);
+
+    for (i = 0; i < ARRAY_SIZE(devices); i++) {
+        const PPCPortInfo *pinfo = &devices[i];
+        MemoryRegion *mr;
+
+        mr = pinfo->devfn(mms, pinfo->opaque, pinfo->name, pinfo->size);
+        memory_region_add_subregion(container, pinfo->addr, mr);
+    }
+
+    return &mms->container;
+}
+
 static void musca_init(MachineState *machine)
 {
     MuscaMachineState *mms = MUSCA_MACHINE(machine);
@@ -75,6 +184,9 @@ static void musca_init(MachineState *machine)
     MachineClass *mc = MACHINE_GET_CLASS(machine);
     MemoryRegion *system_memory = get_system_memory();
     DeviceState *ssedev;
+    DeviceState *dev_splitter;
+    const PPCInfo *ppcs;
+    int num_ppcs;
     int i;
 
     assert(mmc->num_irqs <= MUSCA_NUMIRQ_MAX);
@@ -121,6 +233,183 @@ static void musca_init(MachineState *machine)
                                                      "EXP_CPU1_IRQ", i));
     }
 
+    /*
+     * The sec_resp_cfg output from the SSE-200 must be split into multiple
+     * lines, one for each of the PPCs we create here.
+     */
+    object_initialize(&mms->sec_resp_splitter, sizeof(mms->sec_resp_splitter),
+                      TYPE_SPLIT_IRQ);
+    object_property_add_child(OBJECT(machine), "sec-resp-splitter",
+                              OBJECT(&mms->sec_resp_splitter), &error_fatal);
+    object_property_set_int(OBJECT(&mms->sec_resp_splitter),
+                            ARRAY_SIZE(mms->ppc), "num-lines", &error_fatal);
+    object_property_set_bool(OBJECT(&mms->sec_resp_splitter), true,
+                             "realized", &error_fatal);
+    dev_splitter = DEVICE(&mms->sec_resp_splitter);
+    qdev_connect_gpio_out_named(ssedev, "sec_resp_cfg", 0,
+                                qdev_get_gpio_in(dev_splitter, 0));
+
+    /*
+     * Most of the devices in the board are behind Peripheral Protection
+     * Controllers. The required order for initializing things is:
+     *  + initialize the PPC
+     *  + initialize, configure and realize downstream devices
+     *  + connect downstream device MemoryRegions to the PPC
+     *  + realize the PPC
+     *  + map the PPC's MemoryRegions to the places in the address map
+     *    where the downstream devices should appear
+     *  + wire up the PPC's control lines to the SSE object
+     *
+     * The PPC mapping differs for the -A and -B1 variants; the -A version
+     * is much simpler, using only a single port of a single PPC and putting
+     * all the devices behind that.
+     */
+    const PPCInfo a_ppcs[] = { {
+            .name = "ahb_ppcexp0",
+            .ports = {
+                { "musca-devices", make_musca_a_devs, 0, 0x40100000, 0x100000 },
+            },
+        },
+    };
+
+    /*
+     * Devices listed with an 0x4.. address appear in both the NS 0x4.. region
+     * and the 0x5.. S region. Devices listed with an 0x5.. address appear
+     * only in the S region.
+     */
+    const PPCInfo b1_ppcs[] = { {
+            .name = "apb_ppcexp0",
+            .ports = {
+                { "eflash0", make_unimp_dev, &mms->eflash[0],
+                  0x52400000, 0x1000 },
+                { "eflash1", make_unimp_dev, &mms->eflash[1],
+                  0x52500000, 0x1000 },
+                { "qspi", make_unimp_dev, &mms->qspi, 0x42800000, 0x100000 },
+                { "mpc0", make_unimp_dev, &mms->mpc[0], 0x52000000, 0x1000 },
+                { "mpc1", make_unimp_dev, &mms->mpc[1], 0x52100000, 0x1000 },
+                { "mpc2", make_unimp_dev, &mms->mpc[2], 0x52200000, 0x1000 },
+                { "mpc3", make_unimp_dev, &mms->mpc[3], 0x52300000, 0x1000 },
+                { "mhu0", make_unimp_dev, &mms->mhu[0], 0x42600000, 0x100000 },
+                { "mhu1", make_unimp_dev, &mms->mhu[1], 0x42700000, 0x100000 },
+                { }, /* port 9: unused */
+                { }, /* port 10: unused */
+                { }, /* port 11: unused */
+                { }, /* port 12: unused */
+                { }, /* port 13: unused */
+                { "mpc4", make_unimp_dev, &mms->mpc[4], 0x52e00000, 0x1000 },
+            },
+        }, {
+            .name = "apb_ppcexp1",
+            .ports = {
+                { "pwm0", make_unimp_dev, &mms->pwm[0], 0x40101000, 0x1000 },
+                { "pwm1", make_unimp_dev, &mms->pwm[1], 0x40102000, 0x1000 },
+                { "pwm2", make_unimp_dev, &mms->pwm[2], 0x40103000, 0x1000 },
+                { "i2s", make_unimp_dev, &mms->i2s, 0x40104000, 0x1000 },
+                { "uart0", make_unimp_dev, &mms->uart[0], 0x40105000, 0x1000 },
+                { "uart1", make_unimp_dev, &mms->uart[1], 0x40106000, 0x1000 },
+                { "i2c0", make_unimp_dev, &mms->i2c[0], 0x40108000, 0x1000 },
+                { "i2c1", make_unimp_dev, &mms->i2c[1], 0x40109000, 0x1000 },
+                { "spi", make_unimp_dev, &mms->spi, 0x4010a000, 0x1000 },
+                { "scc", make_unimp_dev, &mms->scc, 0x5010b000, 0x1000 },
+                { "timer", make_unimp_dev, &mms->timer, 0x4010c000, 0x1000 },
+                { "rtc", make_unimp_dev, &mms->rtc, 0x4010d000, 0x1000 },
+                { "pvt", make_unimp_dev, &mms->pvt, 0x4010e000, 0x1000 },
+                { "sdio", make_unimp_dev, &mms->sdio, 0x4010f000, 0x1000 },
+            },
+        }, {
+            .name = "ahb_ppcexp0",
+            .ports = {
+                { }, /* port 0: unused */
+                { "gpio", make_unimp_dev, &mms->gpio, 0x41000000, 0x1000 },
+            },
+        },
+    };
+
+    switch (mmc->type) {
+    case MUSCA_A:
+        ppcs = a_ppcs;
+        num_ppcs = ARRAY_SIZE(a_ppcs);
+        break;
+    case MUSCA_B1:
+        ppcs = b1_ppcs;
+        num_ppcs = ARRAY_SIZE(b1_ppcs);
+        break;
+    default:
+        g_assert_not_reached();
+    }
+    assert(num_ppcs <= MUSCA_PPC_MAX);
+
+    for (i = 0; i < num_ppcs; i++) {
+        const PPCInfo *ppcinfo = &ppcs[i];
+        TZPPC *ppc = &mms->ppc[i];
+        DeviceState *ppcdev;
+        int port;
+        char *gpioname;
+
+        sysbus_init_child_obj(OBJECT(machine), ppcinfo->name, ppc,
+                              sizeof(TZPPC), TYPE_TZ_PPC);
+        ppcdev = DEVICE(ppc);
+
+        for (port = 0; port < TZ_NUM_PORTS; port++) {
+            const PPCPortInfo *pinfo = &ppcinfo->ports[port];
+            MemoryRegion *mr;
+            char *portname;
+
+            if (!pinfo->devfn) {
+                continue;
+            }
+
+            mr = pinfo->devfn(mms, pinfo->opaque, pinfo->name, pinfo->size);
+            portname = g_strdup_printf("port[%d]", port);
+            object_property_set_link(OBJECT(ppc), OBJECT(mr),
+                                     portname, &error_fatal);
+            g_free(portname);
+        }
+
+        object_property_set_bool(OBJECT(ppc), true, "realized", &error_fatal);
+
+        for (port = 0; port < TZ_NUM_PORTS; port++) {
+            const PPCPortInfo *pinfo = &ppcinfo->ports[port];
+
+            if (!pinfo->devfn) {
+                continue;
+            }
+            sysbus_mmio_map(SYS_BUS_DEVICE(ppc), port, pinfo->addr);
+
+            gpioname = g_strdup_printf("%s_nonsec", ppcinfo->name);
+            qdev_connect_gpio_out_named(ssedev, gpioname, port,
+                                        qdev_get_gpio_in_named(ppcdev,
+                                                               "cfg_nonsec",
+                                                               port));
+            g_free(gpioname);
+            gpioname = g_strdup_printf("%s_ap", ppcinfo->name);
+            qdev_connect_gpio_out_named(ssedev, gpioname, port,
+                                        qdev_get_gpio_in_named(ppcdev,
+                                                               "cfg_ap", port));
+            g_free(gpioname);
+        }
+
+        gpioname = g_strdup_printf("%s_irq_enable", ppcinfo->name);
+        qdev_connect_gpio_out_named(ssedev, gpioname, 0,
+                                    qdev_get_gpio_in_named(ppcdev,
+                                                           "irq_enable", 0));
+        g_free(gpioname);
+        gpioname = g_strdup_printf("%s_irq_clear", ppcinfo->name);
+        qdev_connect_gpio_out_named(ssedev, gpioname, 0,
+                                    qdev_get_gpio_in_named(ppcdev,
+                                                           "irq_clear", 0));
+        g_free(gpioname);
+        gpioname = g_strdup_printf("%s_irq_status", ppcinfo->name);
+        qdev_connect_gpio_out_named(ppcdev, "irq", 0,
+                                    qdev_get_gpio_in_named(ssedev,
+                                                           gpioname, 0));
+        g_free(gpioname);
+
+        qdev_connect_gpio_out(dev_splitter, i,
+                              qdev_get_gpio_in_named(ppcdev,
+                                                     "cfg_sec_resp", 0));
+    }
+
     armv7m_load_kernel(ARM_CPU(first_cpu), machine->kernel_filename, 0x2000000);
 }
 
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 18/21] hw/arm/musca: Add MPCs
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (16 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 17/21] hw/arm/musca: Add PPCs Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 19/21] hw/arm/musca: Wire up PL031 RTC Peter Maydell
                   ` (3 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The Musca board puts its SRAM and flash behind TrustZone
Memory Protection Controllers (MPCs). Each MPC sits between
the CPU and the RAM/flash, and also has a set of memory mapped
control registers. Wire up the MPCs, and the memory behind them.
For the moment we implement the flash as simple ROM, which
cannot be reprogrammed by the guest.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/arm/musca.c | 155 ++++++++++++++++++++++++++++++++++++++++++++++---
 1 file changed, 147 insertions(+), 8 deletions(-)

diff --git a/hw/arm/musca.c b/hw/arm/musca.c
index 8774e0b87b7..c4095c4579b 100644
--- a/hw/arm/musca.c
+++ b/hw/arm/musca.c
@@ -27,11 +27,15 @@
 #include "hw/arm/armsse.h"
 #include "hw/boards.h"
 #include "hw/core/split-irq.h"
+#include "hw/misc/tz-mpc.h"
 #include "hw/misc/tz-ppc.h"
 #include "hw/misc/unimp.h"
 
 #define MUSCA_NUMIRQ_MAX 96
 #define MUSCA_PPC_MAX 3
+#define MUSCA_MPC_MAX 5
+
+typedef struct MPCInfo MPCInfo;
 
 typedef enum MuscaType {
     MUSCA_A,
@@ -44,19 +48,23 @@ typedef struct {
     uint32_t init_svtor;
     int sram_addr_width;
     int num_irqs;
+    const MPCInfo *mpc_info;
+    int num_mpcs;
 } MuscaMachineClass;
 
 typedef struct {
     MachineState parent;
 
     ARMSSE sse;
+    /* RAM and flash */
+    MemoryRegion ram[MUSCA_MPC_MAX];
     SplitIRQ cpu_irq_splitter[MUSCA_NUMIRQ_MAX];
     SplitIRQ sec_resp_splitter;
     TZPPC ppc[MUSCA_PPC_MAX];
     MemoryRegion container;
     UnimplementedDeviceState eflash[2];
     UnimplementedDeviceState qspi;
-    UnimplementedDeviceState mpc[5];
+    TZMPC mpc[MUSCA_MPC_MAX];
     UnimplementedDeviceState mhu[2];
     UnimplementedDeviceState pwm[3];
     UnimplementedDeviceState i2s;
@@ -69,6 +77,7 @@ typedef struct {
     UnimplementedDeviceState pvt;
     UnimplementedDeviceState sdio;
     UnimplementedDeviceState gpio;
+    UnimplementedDeviceState cryptoisland;
 } MuscaMachineState;
 
 #define TYPE_MUSCA_MACHINE "musca"
@@ -131,6 +140,131 @@ static MemoryRegion *make_unimp_dev(MuscaMachineState *mms,
     return sysbus_mmio_get_region(SYS_BUS_DEVICE(uds), 0);
 }
 
+typedef enum MPCInfoType {
+    MPC_RAM,
+    MPC_ROM,
+    MPC_CRYPTOISLAND,
+} MPCInfoType;
+
+struct MPCInfo {
+    const char *name;
+    hwaddr addr;
+    hwaddr size;
+    MPCInfoType type;
+};
+
+/* Order of the MPCs here must match the order of the bits in SECMPCINTSTATUS */
+static const MPCInfo a_mpc_info[] = { {
+        .name = "qspi",
+        .type = MPC_ROM,
+        .addr = 0x00200000,
+        .size = 0x00800000,
+    }, {
+        .name = "sram",
+        .type = MPC_RAM,
+        .addr = 0x00000000,
+        .size = 0x00200000,
+    }
+};
+
+static const MPCInfo b1_mpc_info[] = { {
+        .name = "qspi",
+        .type = MPC_ROM,
+        .addr = 0x00000000,
+        .size = 0x02000000,
+    }, {
+        .name = "sram",
+        .type = MPC_RAM,
+        .addr = 0x0a400000,
+        .size = 0x00080000,
+    }, {
+        .name = "eflash0",
+        .type = MPC_ROM,
+        .addr = 0x0a000000,
+        .size = 0x00200000,
+    }, {
+        .name = "eflash1",
+        .type = MPC_ROM,
+        .addr = 0x0a200000,
+        .size = 0x00200000,
+    }, {
+        .name = "cryptoisland",
+        .type = MPC_CRYPTOISLAND,
+        .addr = 0x0a000000,
+        .size = 0x00200000,
+    }
+};
+
+static MemoryRegion *make_mpc(MuscaMachineState *mms, void *opaque,
+                              const char *name, hwaddr size)
+{
+    /*
+     * Create an MPC and the RAM or flash behind it.
+     * MPC 0: eFlash 0
+     * MPC 1: eFlash 1
+     * MPC 2: SRAM
+     * MPC 3: QSPI flash
+     * MPC 4: CryptoIsland
+     * For now we implement the flash regions as ROM (ie not programmable)
+     * (with their control interface memory regions being unimplemented
+     * stubs behind the PPCs).
+     * The whole CryptoIsland region behind its MPC is an unimplemented stub.
+     */
+    MuscaMachineClass *mmc = MUSCA_MACHINE_GET_CLASS(mms);
+    TZMPC *mpc = opaque;
+    int i = mpc - &mms->mpc[0];
+    MemoryRegion *downstream;
+    MemoryRegion *upstream;
+    UnimplementedDeviceState *uds;
+    char *mpcname;
+    const MPCInfo *mpcinfo = mmc->mpc_info;
+
+    mpcname = g_strdup_printf("%s-mpc", mpcinfo[i].name);
+
+    switch (mpcinfo[i].type) {
+    case MPC_ROM:
+        downstream = &mms->ram[i];
+        memory_region_init_rom(downstream, NULL, mpcinfo[i].name,
+                               mpcinfo[i].size, &error_fatal);
+        break;
+    case MPC_RAM:
+        downstream = &mms->ram[i];
+        memory_region_init_ram(downstream, NULL, mpcinfo[i].name,
+                               mpcinfo[i].size, &error_fatal);
+        break;
+    case MPC_CRYPTOISLAND:
+        /* We don't implement the CryptoIsland yet */
+        uds = &mms->cryptoisland;
+        sysbus_init_child_obj(OBJECT(mms), name, uds,
+                              sizeof(UnimplementedDeviceState),
+                              TYPE_UNIMPLEMENTED_DEVICE);
+        qdev_prop_set_string(DEVICE(uds), "name", mpcinfo[i].name);
+        qdev_prop_set_uint64(DEVICE(uds), "size", mpcinfo[i].size);
+        object_property_set_bool(OBJECT(uds), true, "realized", &error_fatal);
+        downstream = sysbus_mmio_get_region(SYS_BUS_DEVICE(uds), 0);
+        break;
+    default:
+        g_assert_not_reached();
+    }
+
+    sysbus_init_child_obj(OBJECT(mms), mpcname, mpc, sizeof(mms->mpc[0]),
+                          TYPE_TZ_MPC);
+    object_property_set_link(OBJECT(mpc), OBJECT(downstream),
+                             "downstream", &error_fatal);
+    object_property_set_bool(OBJECT(mpc), true, "realized", &error_fatal);
+    /* Map the upstream end of the MPC into system memory */
+    upstream = sysbus_mmio_get_region(SYS_BUS_DEVICE(mpc), 1);
+    memory_region_add_subregion(get_system_memory(), mpcinfo[i].addr, upstream);
+    /* and connect its interrupt to the SSE-200 */
+    qdev_connect_gpio_out_named(DEVICE(mpc), "irq", 0,
+                                qdev_get_gpio_in_named(DEVICE(&mms->sse),
+                                                       "mpcexp_status", i));
+
+    g_free(mpcname);
+    /* Return the register interface MR for our caller to map behind the PPC */
+    return sysbus_mmio_get_region(SYS_BUS_DEVICE(mpc), 0);
+}
+
 static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
                                        const char *name, hwaddr size)
 {
@@ -160,8 +294,8 @@ static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
         { "pwm1", make_unimp_dev, &mms->pwm[1], 0xe000, 0x1000 },
         { "pwm2", make_unimp_dev, &mms->pwm[2], 0xf000, 0x1000 },
         { "gpio", make_unimp_dev, &mms->gpio, 0x10000, 0x1000 },
-        { "mpc0", make_unimp_dev, &mms->mpc[0], 0x12000, 0x1000 },
-        { "mpc1", make_unimp_dev, &mms->mpc[1], 0x13000, 0x1000 },
+        { "mpc0", make_mpc, &mms->mpc[0], 0x12000, 0x1000 },
+        { "mpc1", make_mpc, &mms->mpc[1], 0x13000, 0x1000 },
     };
 
     memory_region_init(container, OBJECT(mms), "musca-device-container", size);
@@ -190,6 +324,7 @@ static void musca_init(MachineState *machine)
     int i;
 
     assert(mmc->num_irqs <= MUSCA_NUMIRQ_MAX);
+    assert(mmc->num_mpcs <= MUSCA_MPC_MAX);
 
     if (strcmp(machine->cpu_type, mc->default_cpu_type) != 0) {
         error_report("This board can only be used with CPU %s",
@@ -285,10 +420,10 @@ static void musca_init(MachineState *machine)
                 { "eflash1", make_unimp_dev, &mms->eflash[1],
                   0x52500000, 0x1000 },
                 { "qspi", make_unimp_dev, &mms->qspi, 0x42800000, 0x100000 },
-                { "mpc0", make_unimp_dev, &mms->mpc[0], 0x52000000, 0x1000 },
-                { "mpc1", make_unimp_dev, &mms->mpc[1], 0x52100000, 0x1000 },
-                { "mpc2", make_unimp_dev, &mms->mpc[2], 0x52200000, 0x1000 },
-                { "mpc3", make_unimp_dev, &mms->mpc[3], 0x52300000, 0x1000 },
+                { "mpc0", make_mpc, &mms->mpc[0], 0x52000000, 0x1000 },
+                { "mpc1", make_mpc, &mms->mpc[1], 0x52100000, 0x1000 },
+                { "mpc2", make_mpc, &mms->mpc[2], 0x52200000, 0x1000 },
+                { "mpc3", make_mpc, &mms->mpc[3], 0x52300000, 0x1000 },
                 { "mhu0", make_unimp_dev, &mms->mhu[0], 0x42600000, 0x100000 },
                 { "mhu1", make_unimp_dev, &mms->mhu[1], 0x42700000, 0x100000 },
                 { }, /* port 9: unused */
@@ -296,7 +431,7 @@ static void musca_init(MachineState *machine)
                 { }, /* port 11: unused */
                 { }, /* port 12: unused */
                 { }, /* port 13: unused */
-                { "mpc4", make_unimp_dev, &mms->mpc[4], 0x52e00000, 0x1000 },
+                { "mpc4", make_mpc, &mms->mpc[4], 0x52e00000, 0x1000 },
             },
         }, {
             .name = "apb_ppcexp1",
@@ -434,6 +569,8 @@ static void musca_a_class_init(ObjectClass *oc, void *data)
     mmc->init_svtor = 0x10200000;
     mmc->sram_addr_width = 15;
     mmc->num_irqs = 64;
+    mmc->mpc_info = a_mpc_info;
+    mmc->num_mpcs = ARRAY_SIZE(a_mpc_info);
 }
 
 static void musca_b1_class_init(ObjectClass *oc, void *data)
@@ -453,6 +590,8 @@ static void musca_b1_class_init(ObjectClass *oc, void *data)
     mmc->init_svtor = 0x10000000;
     mmc->sram_addr_width = 17;
     mmc->num_irqs = 96;
+    mmc->mpc_info = b1_mpc_info;
+    mmc->num_mpcs = ARRAY_SIZE(b1_mpc_info);
 }
 
 static const TypeInfo musca_info = {
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 19/21] hw/arm/musca: Wire up PL031 RTC
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (17 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 18/21] hw/arm/musca: Add MPCs Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 20/21] hw/arm/musca: Wire up PL011 UARTs Peter Maydell
                   ` (2 subsequent siblings)
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Wire up the PL031 RTC for the Musca board.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/arm/musca.c | 26 +++++++++++++++++++++++---
 1 file changed, 23 insertions(+), 3 deletions(-)

diff --git a/hw/arm/musca.c b/hw/arm/musca.c
index c4095c4579b..378912b7385 100644
--- a/hw/arm/musca.c
+++ b/hw/arm/musca.c
@@ -30,6 +30,7 @@
 #include "hw/misc/tz-mpc.h"
 #include "hw/misc/tz-ppc.h"
 #include "hw/misc/unimp.h"
+#include "hw/timer/pl031.h"
 
 #define MUSCA_NUMIRQ_MAX 96
 #define MUSCA_PPC_MAX 3
@@ -73,7 +74,7 @@ typedef struct {
     UnimplementedDeviceState spi;
     UnimplementedDeviceState scc;
     UnimplementedDeviceState timer;
-    UnimplementedDeviceState rtc;
+    PL031State rtc;
     UnimplementedDeviceState pvt;
     UnimplementedDeviceState sdio;
     UnimplementedDeviceState gpio;
@@ -98,6 +99,14 @@ typedef struct {
  */
 #define SYSCLK_FRQ 40000000
 
+static qemu_irq get_sse_irq_in(MuscaMachineState *mms, int irqno)
+{
+    /* Return a qemu_irq which will signal IRQ n to all CPUs in the SSE. */
+    assert(irqno < MUSCA_NUMIRQ_MAX);
+
+    return qdev_get_gpio_in(DEVICE(&mms->cpu_irq_splitter[irqno]), 0);
+}
+
 /*
  * Most of the devices in the Musca board sit behind Peripheral Protection
  * Controllers. These data structures define the layout of which devices
@@ -265,6 +274,17 @@ static MemoryRegion *make_mpc(MuscaMachineState *mms, void *opaque,
     return sysbus_mmio_get_region(SYS_BUS_DEVICE(mpc), 0);
 }
 
+static MemoryRegion *make_rtc(MuscaMachineState *mms, void *opaque,
+                              const char *name, hwaddr size)
+{
+    PL031State *rtc = opaque;
+
+    sysbus_init_child_obj(OBJECT(mms), name, rtc, sizeof(mms->rtc), TYPE_PL031);
+    object_property_set_bool(OBJECT(rtc), true, "realized", &error_fatal);
+    sysbus_connect_irq(SYS_BUS_DEVICE(rtc), 0, get_sse_irq_in(mms, 39));
+    return sysbus_mmio_get_region(SYS_BUS_DEVICE(rtc), 0);
+}
+
 static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
                                        const char *name, hwaddr size)
 {
@@ -287,7 +307,7 @@ static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
         { "i2c1", make_unimp_dev, &mms->i2c[1], 0x5000, 0x1000 },
         { "i2s", make_unimp_dev, &mms->i2s, 0x6000, 0x1000 },
         { "pwm0", make_unimp_dev, &mms->pwm[0], 0x7000, 0x1000 },
-        { "rtc", make_unimp_dev, &mms->rtc, 0x8000, 0x1000 },
+        { "rtc", make_rtc, &mms->rtc, 0x8000, 0x1000 },
         { "qspi", make_unimp_dev, &mms->qspi, 0xa000, 0x1000 },
         { "timer", make_unimp_dev, &mms->timer, 0xb000, 0x1000 },
         { "scc", make_unimp_dev, &mms->scc, 0xc000, 0x1000 },
@@ -447,7 +467,7 @@ static void musca_init(MachineState *machine)
                 { "spi", make_unimp_dev, &mms->spi, 0x4010a000, 0x1000 },
                 { "scc", make_unimp_dev, &mms->scc, 0x5010b000, 0x1000 },
                 { "timer", make_unimp_dev, &mms->timer, 0x4010c000, 0x1000 },
-                { "rtc", make_unimp_dev, &mms->rtc, 0x4010d000, 0x1000 },
+                { "rtc", make_rtc, &mms->rtc, 0x4010d000, 0x1000 },
                 { "pvt", make_unimp_dev, &mms->pvt, 0x4010e000, 0x1000 },
                 { "sdio", make_unimp_dev, &mms->sdio, 0x4010f000, 0x1000 },
             },
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 20/21] hw/arm/musca: Wire up PL011 UARTs
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (18 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 19/21] hw/arm/musca: Wire up PL031 RTC Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-21 18:57 ` [Qemu-devel] [PULL 21/21] hw/arm/armsse: Make 0x5... alias region work for per-CPU devices Peter Maydell
  2019-02-22 11:24 ` [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

Wire up the two PL011 UARTs in the Musca board.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
---
 hw/arm/musca.c | 34 +++++++++++++++++++++++++++++-----
 1 file changed, 29 insertions(+), 5 deletions(-)

diff --git a/hw/arm/musca.c b/hw/arm/musca.c
index 378912b7385..23aff43f4bc 100644
--- a/hw/arm/musca.c
+++ b/hw/arm/musca.c
@@ -23,9 +23,11 @@
 #include "qemu/error-report.h"
 #include "qapi/error.h"
 #include "exec/address-spaces.h"
+#include "sysemu/sysemu.h"
 #include "hw/arm/arm.h"
 #include "hw/arm/armsse.h"
 #include "hw/boards.h"
+#include "hw/char/pl011.h"
 #include "hw/core/split-irq.h"
 #include "hw/misc/tz-mpc.h"
 #include "hw/misc/tz-ppc.h"
@@ -69,7 +71,7 @@ typedef struct {
     UnimplementedDeviceState mhu[2];
     UnimplementedDeviceState pwm[3];
     UnimplementedDeviceState i2s;
-    UnimplementedDeviceState uart[2];
+    PL011State uart[2];
     UnimplementedDeviceState i2c[2];
     UnimplementedDeviceState spi;
     UnimplementedDeviceState scc;
@@ -285,6 +287,28 @@ static MemoryRegion *make_rtc(MuscaMachineState *mms, void *opaque,
     return sysbus_mmio_get_region(SYS_BUS_DEVICE(rtc), 0);
 }
 
+static MemoryRegion *make_uart(MuscaMachineState *mms, void *opaque,
+                               const char *name, hwaddr size)
+{
+    PL011State *uart = opaque;
+    int i = uart - &mms->uart[0];
+    int irqbase = 7 + i * 6;
+    SysBusDevice *s;
+
+    sysbus_init_child_obj(OBJECT(mms), name, uart, sizeof(mms->uart[0]),
+                          TYPE_PL011);
+    qdev_prop_set_chr(DEVICE(uart), "chardev", serial_hd(i));
+    object_property_set_bool(OBJECT(uart), true, "realized", &error_fatal);
+    s = SYS_BUS_DEVICE(uart);
+    sysbus_connect_irq(s, 0, get_sse_irq_in(mms, irqbase + 5)); /* combined */
+    sysbus_connect_irq(s, 1, get_sse_irq_in(mms, irqbase + 0)); /* RX */
+    sysbus_connect_irq(s, 2, get_sse_irq_in(mms, irqbase + 1)); /* TX */
+    sysbus_connect_irq(s, 3, get_sse_irq_in(mms, irqbase + 2)); /* RT */
+    sysbus_connect_irq(s, 4, get_sse_irq_in(mms, irqbase + 3)); /* MS */
+    sysbus_connect_irq(s, 5, get_sse_irq_in(mms, irqbase + 4)); /* E */
+    return sysbus_mmio_get_region(SYS_BUS_DEVICE(uart), 0);
+}
+
 static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
                                        const char *name, hwaddr size)
 {
@@ -300,8 +324,8 @@ static MemoryRegion *make_musca_a_devs(MuscaMachineState *mms, void *opaque,
     MemoryRegion *container = &mms->container;
 
     const PPCPortInfo devices[] = {
-        { "uart0", make_unimp_dev, &mms->uart[0], 0x1000, 0x1000 },
-        { "uart1", make_unimp_dev, &mms->uart[1], 0x2000, 0x1000 },
+        { "uart0", make_uart, &mms->uart[0], 0x1000, 0x1000 },
+        { "uart1", make_uart, &mms->uart[1], 0x2000, 0x1000 },
         { "spi", make_unimp_dev, &mms->spi, 0x3000, 0x1000 },
         { "i2c0", make_unimp_dev, &mms->i2c[0], 0x4000, 0x1000 },
         { "i2c1", make_unimp_dev, &mms->i2c[1], 0x5000, 0x1000 },
@@ -460,8 +484,8 @@ static void musca_init(MachineState *machine)
                 { "pwm1", make_unimp_dev, &mms->pwm[1], 0x40102000, 0x1000 },
                 { "pwm2", make_unimp_dev, &mms->pwm[2], 0x40103000, 0x1000 },
                 { "i2s", make_unimp_dev, &mms->i2s, 0x40104000, 0x1000 },
-                { "uart0", make_unimp_dev, &mms->uart[0], 0x40105000, 0x1000 },
-                { "uart1", make_unimp_dev, &mms->uart[1], 0x40106000, 0x1000 },
+                { "uart0", make_uart, &mms->uart[0], 0x40105000, 0x1000 },
+                { "uart1", make_uart, &mms->uart[1], 0x40106000, 0x1000 },
                 { "i2c0", make_unimp_dev, &mms->i2c[0], 0x40108000, 0x1000 },
                 { "i2c1", make_unimp_dev, &mms->i2c[1], 0x40109000, 0x1000 },
                 { "spi", make_unimp_dev, &mms->spi, 0x4010a000, 0x1000 },
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 21/21] hw/arm/armsse: Make 0x5... alias region work for per-CPU devices
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (19 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 20/21] hw/arm/musca: Wire up PL011 UARTs Peter Maydell
@ 2019-02-21 18:57 ` Peter Maydell
  2019-02-22 11:24 ` [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-21 18:57 UTC (permalink / raw)
  To: qemu-devel

The region 0x40010000 .. 0x4001ffff and its secure-only alias
at 0x50010000... are for per-CPU devices. We implement this by
giving each CPU its own container memory region, where the
per-CPU devices live. Unfortunately, the alias region which
makes devices mapped at 0x4... addresses also appear at 0x5...
is only implemented in the overall "all CPUs" container. The
effect of this bug is that the CPU_IDENTITY register block appears
only at 0x4001f000, but not at the 0x5001f000 alias where it should
also appear. Guests (like very recent Arm Trusted Firmware-M)
which try to access it at 0x5001f000 will crash.

Fix this by moving the handling for this alias from the "all CPUs"
container to the per-CPU container. (We leave the aliases for
0x1... and 0x3... in the overall container, because there are
no per-CPU devices there.)

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Message-id: 20190215180500.6906-1-peter.maydell@linaro.org
Reviewed-by: Alex Bennée <alex.bennee@linaro.org>
---
 include/hw/arm/armsse.h |  2 +-
 hw/arm/armsse.c         | 26 ++++++++++++++++----------
 2 files changed, 17 insertions(+), 11 deletions(-)

diff --git a/include/hw/arm/armsse.h b/include/hw/arm/armsse.h
index 84879f40dd8..7ef871c7dfe 100644
--- a/include/hw/arm/armsse.h
+++ b/include/hw/arm/armsse.h
@@ -186,7 +186,7 @@ typedef struct ARMSSE {
     MemoryRegion cpu_container[SSE_MAX_CPUS];
     MemoryRegion alias1;
     MemoryRegion alias2;
-    MemoryRegion alias3;
+    MemoryRegion alias3[SSE_MAX_CPUS];
     MemoryRegion sram[MAX_SRAM_BANKS];
 
     qemu_irq *exp_irqs[SSE_MAX_CPUS];
diff --git a/hw/arm/armsse.c b/hw/arm/armsse.c
index 50da41f64c5..129e7ea7fe0 100644
--- a/hw/arm/armsse.c
+++ b/hw/arm/armsse.c
@@ -110,15 +110,16 @@ static bool irq_is_common[32] = {
     /* 30, 31: reserved */
 };
 
-/* Create an alias region of @size bytes starting at @base
+/*
+ * Create an alias region in @container of @size bytes starting at @base
  * which mirrors the memory starting at @orig.
  */
-static void make_alias(ARMSSE *s, MemoryRegion *mr, const char *name,
-                       hwaddr base, hwaddr size, hwaddr orig)
+static void make_alias(ARMSSE *s, MemoryRegion *mr, MemoryRegion *container,
+                       const char *name, hwaddr base, hwaddr size, hwaddr orig)
 {
-    memory_region_init_alias(mr, NULL, name, &s->container, orig, size);
+    memory_region_init_alias(mr, NULL, name, container, orig, size);
     /* The alias is even lower priority than unimplemented_device regions */
-    memory_region_add_subregion_overlap(&s->container, base, mr, -1500);
+    memory_region_add_subregion_overlap(container, base, mr, -1500);
 }
 
 static void irq_status_forwarder(void *opaque, int n, int level)
@@ -607,16 +608,21 @@ static void armsse_realize(DeviceState *dev, Error **errp)
     }
 
     /* Set up the big aliases first */
-    make_alias(s, &s->alias1, "alias 1", 0x10000000, 0x10000000, 0x00000000);
-    make_alias(s, &s->alias2, "alias 2", 0x30000000, 0x10000000, 0x20000000);
+    make_alias(s, &s->alias1, &s->container, "alias 1",
+               0x10000000, 0x10000000, 0x00000000);
+    make_alias(s, &s->alias2, &s->container,
+               "alias 2", 0x30000000, 0x10000000, 0x20000000);
     /* The 0x50000000..0x5fffffff region is not a pure alias: it has
      * a few extra devices that only appear there (generally the
      * control interfaces for the protection controllers).
      * We implement this by mapping those devices over the top of this
-     * alias MR at a higher priority.
+     * alias MR at a higher priority. Some of the devices in this range
+     * are per-CPU, so we must put this alias in the per-cpu containers.
      */
-    make_alias(s, &s->alias3, "alias 3", 0x50000000, 0x10000000, 0x40000000);
-
+    for (i = 0; i < info->num_cpus; i++) {
+        make_alias(s, &s->alias3[i], &s->cpu_container[i],
+                   "alias 3", 0x50000000, 0x10000000, 0x40000000);
+    }
 
     /* Security controller */
     object_property_set_bool(OBJECT(&s->secctl), true, "realized", &err);
-- 
2.20.1

^ permalink raw reply related	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
                   ` (20 preceding siblings ...)
  2019-02-21 18:57 ` [Qemu-devel] [PULL 21/21] hw/arm/armsse: Make 0x5... alias region work for per-CPU devices Peter Maydell
@ 2019-02-22 11:24 ` Peter Maydell
  21 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-02-22 11:24 UTC (permalink / raw)
  To: QEMU Developers

On Thu, 21 Feb 2019 at 18:57, Peter Maydell <peter.maydell@linaro.org> wrote:
>
> Arm queue -- mostly the first slice of my Musca patches.
>
> thanks
> -- PMM
>
> The following changes since commit fc3dbb90f2eb069801bfb4cfe9cbc83cf9c5f4a9:
>
>   Merge remote-tracking branch 'remotes/jnsnow/tags/bitmaps-pull-request' into staging (2019-02-21 13:09:33 +0000)
>
> are available in the Git repository at:
>
>   https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20190221
>
> for you to fetch changes up to 3733f80308d2a7f23f5e39b039e0547aba6c07f1:
>
>   hw/arm/armsse: Make 0x5... alias region work for per-CPU devices (2019-02-21 18:17:48 +0000)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * Model the Arm "Musca" development boards: "musca-a" and "musca-b1"
>  * Implement the ARMv8.3-JSConv extension
>  * v8M MPU should use background region as default, not always
>  * Stop unintentional sign extension in pmu_init
>
> ----------------------------------------------------------------

Applied, thanks.

Please update the changelog at https://wiki.qemu.org/ChangeLog/4.0
for any user-visible changes.

-- PMM

^ permalink raw reply	[flat|nested] 42+ messages in thread

* [Qemu-devel] [PULL 00/21] target-arm queue
@ 2019-09-03 15:36 Peter Maydell
  2019-09-04 13:44 ` Peter Maydell
  0 siblings, 1 reply; 42+ messages in thread
From: Peter Maydell @ 2019-09-03 15:36 UTC (permalink / raw)
  To: qemu-devel

target-arm queue: this time around is all small fixes
and changes.

thanks
-- PMM

The following changes since commit fec105c2abda8567ec15230429c41429b5ee307c:

  Merge remote-tracking branch 'remotes/kraxel/tags/audio-20190828-pull-request' into staging (2019-09-03 14:03:15 +0100)

are available in the Git repository at:

  https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20190903

for you to fetch changes up to 5e5584c89f36b302c666bc6db535fd3f7ff35ad2:

  target/arm: Don't abort on M-profile exception return in linux-user mode (2019-09-03 16:20:35 +0100)

----------------------------------------------------------------
target-arm queue:
 * Revert and correctly fix refactoring of unallocated_encoding()
 * Take exceptions on ATS instructions when needed
 * aspeed/timer: Provide back-pressure information for short periods
 * memory: Remove unused memory_region_iommu_replay_all()
 * hw/arm/smmuv3: Log a guest error when decoding an invalid STE
 * hw/arm/smmuv3: Remove spurious error messages on IOVA invalidations
 * target/arm: Fix SMMLS argument order
 * hw/arm: Use ARM_CPU_TYPE_NAME() macro when appropriate
 * hw/arm: Correct reference counting for creation of various objects
 * includes: remove stale [smp|max]_cpus externs
 * tcg/README: fix typo
 * atomic_template: fix indentation in GEN_ATOMIC_HELPER
 * include/exec/cpu-defs.h: fix typo
 * target/arm: Free TCG temps in trans_VMOV_64_sp()
 * target/arm: Don't abort on M-profile exception return in linux-user mode

----------------------------------------------------------------
Alex Bennée (2):
      includes: remove stale [smp|max]_cpus externs
      include/exec/cpu-defs.h: fix typo

Andrew Jeffery (1):
      aspeed/timer: Provide back-pressure information for short periods

Emilio G. Cota (2):
      tcg/README: fix typo s/afterwise/afterwards/
      atomic_template: fix indentation in GEN_ATOMIC_HELPER

Eric Auger (3):
      memory: Remove unused memory_region_iommu_replay_all()
      hw/arm/smmuv3: Log a guest error when decoding an invalid STE
      hw/arm/smmuv3: Remove spurious error messages on IOVA invalidations

Peter Maydell (4):
      target/arm: Allow ARMCPRegInfo read/write functions to throw exceptions
      target/arm: Take exceptions on ATS instructions when needed
      target/arm: Free TCG temps in trans_VMOV_64_sp()
      target/arm: Don't abort on M-profile exception return in linux-user mode

Philippe Mathieu-Daudé (6):
      hw/arm: Use ARM_CPU_TYPE_NAME() macro when appropriate
      hw/arm: Use object_initialize_child for correct reference counting
      hw/arm: Use sysbus_init_child_obj for correct reference counting
      hw/arm/fsl-imx: Add the cpu as child of the SoC object
      hw/dma/xilinx_axi: Use object_initialize_child for correct ref. counting
      hw/net/xilinx_axi: Use object_initialize_child for correct ref. counting

Richard Henderson (3):
      Revert "target/arm: Use unallocated_encoding for aarch32"
      target/arm: Factor out unallocated_encoding for aarch32
      target/arm: Fix SMMLS argument order

 accel/tcg/atomic_template.h    |   2 +-
 hw/arm/smmuv3-internal.h       |   1 +
 include/exec/cpu-defs.h        |   2 +-
 include/exec/memory.h          |  10 ----
 include/sysemu/sysemu.h        |   2 -
 target/arm/cpu.h               |   6 ++-
 target/arm/translate-a64.h     |   2 +
 target/arm/translate.h         |   2 -
 hw/arm/allwinner-a10.c         |   3 +-
 hw/arm/cubieboard.c            |   3 +-
 hw/arm/digic.c                 |   3 +-
 hw/arm/exynos4_boards.c        |   4 +-
 hw/arm/fsl-imx25.c             |   4 +-
 hw/arm/fsl-imx31.c             |   4 +-
 hw/arm/fsl-imx6.c              |   3 +-
 hw/arm/fsl-imx6ul.c            |   2 +-
 hw/arm/mcimx7d-sabre.c         |   9 ++--
 hw/arm/mps2-tz.c               |  15 +++---
 hw/arm/musca.c                 |   9 ++--
 hw/arm/smmuv3.c                |  18 ++++---
 hw/arm/xlnx-zynqmp.c           |   8 +--
 hw/dma/xilinx_axidma.c         |  16 +++---
 hw/net/xilinx_axienet.c        |  17 +++----
 hw/timer/aspeed_timer.c        |  17 ++++++-
 memory.c                       |   9 ----
 target/arm/helper.c            | 107 +++++++++++++++++++++++++++++++++++------
 target/arm/translate-a64.c     |  13 +++++
 target/arm/translate-vfp.inc.c |   2 +
 target/arm/translate.c         |  50 +++++++++++++++++--
 tcg/README                     |   2 +-
 30 files changed, 244 insertions(+), 101 deletions(-)


^ permalink raw reply	[flat|nested] 42+ messages in thread

* Re: [Qemu-devel] [PULL 00/21] target-arm queue
  2019-09-03 15:36 Peter Maydell
@ 2019-09-04 13:44 ` Peter Maydell
  0 siblings, 0 replies; 42+ messages in thread
From: Peter Maydell @ 2019-09-04 13:44 UTC (permalink / raw)
  To: QEMU Developers

On Tue, 3 Sep 2019 at 16:36, Peter Maydell <peter.maydell@linaro.org> wrote:
>
> target-arm queue: this time around is all small fixes
> and changes.
>
> thanks
> -- PMM
>
> The following changes since commit fec105c2abda8567ec15230429c41429b5ee307c:
>
>   Merge remote-tracking branch 'remotes/kraxel/tags/audio-20190828-pull-request' into staging (2019-09-03 14:03:15 +0100)
>
> are available in the Git repository at:
>
>   https://git.linaro.org/people/pmaydell/qemu-arm.git tags/pull-target-arm-20190903
>
> for you to fetch changes up to 5e5584c89f36b302c666bc6db535fd3f7ff35ad2:
>
>   target/arm: Don't abort on M-profile exception return in linux-user mode (2019-09-03 16:20:35 +0100)
>
> ----------------------------------------------------------------
> target-arm queue:
>  * Revert and correctly fix refactoring of unallocated_encoding()
>  * Take exceptions on ATS instructions when needed
>  * aspeed/timer: Provide back-pressure information for short periods
>  * memory: Remove unused memory_region_iommu_replay_all()
>  * hw/arm/smmuv3: Log a guest error when decoding an invalid STE
>  * hw/arm/smmuv3: Remove spurious error messages on IOVA invalidations
>  * target/arm: Fix SMMLS argument order
>  * hw/arm: Use ARM_CPU_TYPE_NAME() macro when appropriate
>  * hw/arm: Correct reference counting for creation of various objects
>  * includes: remove stale [smp|max]_cpus externs
>  * tcg/README: fix typo
>  * atomic_template: fix indentation in GEN_ATOMIC_HELPER
>  * include/exec/cpu-defs.h: fix typo
>  * target/arm: Free TCG temps in trans_VMOV_64_sp()
>  * target/arm: Don't abort on M-profile exception return in linux-user mode
>
> ----------------------------------------------------------------


Applied, thanks.

Please update the changelog at https://wiki.qemu.org/ChangeLog/4.2
for any user-visible changes.

-- PMM


^ permalink raw reply	[flat|nested] 42+ messages in thread

end of thread, other threads:[~2019-09-04 13:46 UTC | newest]

Thread overview: 42+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2019-02-21 18:57 [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 01/21] hw/arm/armsse: Fix memory leak in error-exit path Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 02/21] target/arm: v8M MPU should use background region as default, not always Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 03/21] target/arm: Stop unintentional sign extension in pmu_init Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 04/21] target/arm: Restructure disas_fp_int_conv Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 05/21] target/arm: Split out vfp_helper.c Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 06/21] target/arm: Rearrange Floating-point data-processing (2 regs) Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 07/21] target/arm: Implement ARMv8.3-JSConv Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 08/21] hw/misc/tz-ppc: Support having unused ports in the middle of the range Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 09/21] hw/timer/pl031: Allow use as an embedded-struct device Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 10/21] hw/timer/pl031: Convert to using trace events Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 11/21] hw/char/pl011: Allow use as an embedded-struct device Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 12/21] hw/char/pl011: Support all interrupt lines Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 13/21] hw/char/pl011: Use '0x' prefix when logging hex numbers Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 14/21] hw/arm/armsse: Document SRAM_ADDR_WIDTH property in header comment Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 15/21] hw/arm/armsse: Allow boards to specify init-svtor Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 16/21] hw/arm/musca.c: Implement models of the Musca-A and -B1 boards Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 17/21] hw/arm/musca: Add PPCs Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 18/21] hw/arm/musca: Add MPCs Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 19/21] hw/arm/musca: Wire up PL031 RTC Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 20/21] hw/arm/musca: Wire up PL011 UARTs Peter Maydell
2019-02-21 18:57 ` [Qemu-devel] [PULL 21/21] hw/arm/armsse: Make 0x5... alias region work for per-CPU devices Peter Maydell
2019-02-22 11:24 ` [Qemu-devel] [PULL 00/21] target-arm queue Peter Maydell
  -- strict thread matches above, loose matches on Subject: below --
2019-09-03 15:36 Peter Maydell
2019-09-04 13:44 ` Peter Maydell
2018-05-10 17:44 Peter Maydell
2018-05-10 18:06 ` no-reply
2018-05-14  8:46 ` Peter Maydell
2018-02-15 13:56 Peter Maydell
2018-01-25 13:43 Peter Maydell
2018-01-25 14:18 ` no-reply
2018-01-25 18:06 ` Peter Maydell
2017-02-28 17:15 Peter Maydell
2017-03-01 19:28 ` Peter Maydell
2017-01-09 11:53 Peter Maydell
2017-01-09 13:44 ` Peter Maydell
2016-03-16 17:18 Peter Maydell
2016-03-16 17:42 ` Peter Maydell
2016-03-16 18:19 ` Peter Maydell
2015-05-18 19:15 Peter Maydell
2015-05-19  7:57 ` Peter Maydell
2013-08-20 14:07 Peter Maydell

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).