[PATCH qemu 1/1] [meson.build] Add conditional dependency for libkeyutils

2023-05-21 Thread ~_6d6178667269747a
From: Max Fritz 

This modification enables better control over the inclusion of libkeyutils
based on the configuration, enhancing the flexibility of the build system.

Signed-off-by: Max Fritz 
---
 meson.build | 7 +--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/meson.build b/meson.build
index 0a5cdefd4d..206d4033bf 100644
--- a/meson.build
+++ b/meson.build
@@ -1764,8 +1764,11 @@ if gnutls.found()
   tasn1 = dependency('libtasn1',
  method: 'pkg-config')
 endif
-keyutils = dependency('libkeyutils', required: false,
-  method: 'pkg-config')
+keyutils = not_found
+if get_option('keyring').enabled()
+  keyutils = dependency('libkeyutils', required: false,
+method: 'pkg-config', kwargs: static_kwargs)
+endif
 
 has_gettid = cc.has_function('gettid')
 
-- 
2.38.4



[PATCH qemu 0/1] [meson.build] Add conditional dependency for libkeyutils

2023-05-21 Thread ~_6d6178667269747a
I have a patch that adds a conditional dependency for 'libkeyutils' in
the meson.build file to enhance the build system's flexibility. The
patch addresses the following issue:

If the dynamic library 'libkeyutils' is found by pkg-config, but one
attempts to build with static linkage, the build will fail, even if the
keyring feature is disabled and, therefore, the library is not needed.

Max Fritz (1):
  [meson.build] Add conditional dependency for libkeyutils

 meson.build | 7 +--
 1 file changed, 5 insertions(+), 2 deletions(-)

-- 
2.38.4



Re: [PATCH 1/4] hw/intc/loongarch_ipi: Bring back all 4 IPI mailboxes

2023-05-21 Thread Huacai Chen
Hi, Jiaxun,

Rename loongarch_ipi to loongson_ipi? It will be shared by both MIPS
and LoongArch in your series.


Huacai

On Sun, May 21, 2023 at 6:24 PM Jiaxun Yang  wrote:
>
> As per "Loongson 3A5000/3B5000 Processor Reference Manual",
> Loongson 3A5000's IPI implementation have 4 mailboxes per
> core.
>
> However, in 78464f023b54 ("hw/loongarch/virt: Modify ipi as
> percpu device"), the number of IPI mailboxes was reduced to
> one, which mismatches actual hardware.
>
> It won't affect LoongArch based system as LoongArch boot code
> only uses the first mailbox, however MIPS based Loongson boot
> code uses all 4 mailboxes.
>
> Fixes: 78464f023b54 ("hw/loongarch/virt: Modify ipi as percpu device")
> Signed-off-by: Jiaxun Yang 
> ---
>  hw/intc/loongarch_ipi.c | 6 +++---
>  include/hw/intc/loongarch_ipi.h | 4 +++-
>  2 files changed, 6 insertions(+), 4 deletions(-)
>
> diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
> index d6ab91721ea1..3e453816524e 100644
> --- a/hw/intc/loongarch_ipi.c
> +++ b/hw/intc/loongarch_ipi.c
> @@ -238,14 +238,14 @@ static void loongarch_ipi_init(Object *obj)
>
>  static const VMStateDescription vmstate_ipi_core = {
>  .name = "ipi-single",
> -.version_id = 1,
> -.minimum_version_id = 1,
> +.version_id = 2,
> +.minimum_version_id = 2,
>  .fields = (VMStateField[]) {
>  VMSTATE_UINT32(status, IPICore),
>  VMSTATE_UINT32(en, IPICore),
>  VMSTATE_UINT32(set, IPICore),
>  VMSTATE_UINT32(clear, IPICore),
> -VMSTATE_UINT32_ARRAY(buf, IPICore, 2),
> +VMSTATE_UINT32_ARRAY(buf, IPICore, IPI_MBX_NUM * 2),
>  VMSTATE_END_OF_LIST()
>  }
>  };
> diff --git a/include/hw/intc/loongarch_ipi.h b/include/hw/intc/loongarch_ipi.h
> index 664e050b926e..6c6194786e80 100644
> --- a/include/hw/intc/loongarch_ipi.h
> +++ b/include/hw/intc/loongarch_ipi.h
> @@ -28,6 +28,8 @@
>  #define MAIL_SEND_OFFSET  0
>  #define ANY_SEND_OFFSET   (IOCSR_ANY_SEND - IOCSR_MAIL_SEND)
>
> +#define IPI_MBX_NUM   4
> +
>  #define TYPE_LOONGARCH_IPI "loongarch_ipi"
>  OBJECT_DECLARE_SIMPLE_TYPE(LoongArchIPI, LOONGARCH_IPI)
>
> @@ -37,7 +39,7 @@ typedef struct IPICore {
>  uint32_t set;
>  uint32_t clear;
>  /* 64bit buf divide into 2 32bit buf */
> -uint32_t buf[2];
> +uint32_t buf[IPI_MBX_NUM * 2];
>  qemu_irq irq;
>  } IPICore;
>
> --
> 2.39.2 (Apple Git-143)
>



Re: [PATCH 2/4] hw/intc/loongarch_ipi: Guard LoongArch only features with ifdef

2023-05-21 Thread Song Gao

Hi,

在 2023/5/21 下午6:23, Jiaxun Yang 写道:

IOCSR based send features are tied to LoongArch's CPU implmentation,
ifdef them for LoongArch only so we can build loongarch_ipi on MIPS.

Note that Loongson-3A4000 have IOCSR as well, so we may implement
those features for MIPS in future.

Signed-off-by: Jiaxun Yang 
---
  hw/intc/loongarch_ipi.c | 20 
  1 file changed, 20 insertions(+)

diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
index 3e453816524e..895a2ee96e1e 100644
--- a/hw/intc/loongarch_ipi.c
+++ b/hw/intc/loongarch_ipi.c
@@ -50,6 +50,7 @@ static uint64_t loongarch_ipi_readl(void *opaque, hwaddr 
addr, unsigned size)
  return ret;
  }
  
+#ifdef TARGET_LOONGARCH64


How about adding one or three properties to LoongArchIPI?
and set these properties when starting the device.

This patch conflicts with patch [1], will it affect your patch?

[1]: 
https://patchew.org/QEMU/20230518014115.117869-1-gaos...@loongson.cn/20230518014115.117869-3-gaos...@loongson.cn/


Thanks.
Song Gao

  static void send_ipi_data(CPULoongArchState *env, uint64_t val, hwaddr addr)
  {
  int i, mask = 0, data = 0;
@@ -140,6 +141,25 @@ static void any_send(uint64_t val)
  env = >env;
  send_ipi_data(env, val, addr);
  }
+#else
+static void ipi_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+
+static void mail_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+
+static void any_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+#endif
  
  static void loongarch_ipi_writel(void *opaque, hwaddr addr, uint64_t val,

   unsigned size)





[PATCH 0/2] MIPS: Enable Loongson-3A4000 TCG for system emulation

2023-05-21 Thread Jiaxun Yang
Hi there,

This series enables Loongson-3A4000 TCG for system emulation.
It Implemented Loongson CSR insertions which is required for
Linux Kernel to probe CPU features and removed CPU type restrictions
for loongson3_virt board.

This series is based on two of my previous series[1] [2]. However it's
just a soft dependency for me to do boot test, feel free to apply this
series without them.

Note that loongarch_ipi is still not hooked up in IOCSR. I've sucessfully
done it locally but I just want to confirm some details on hardware.

Thanks
- Jiaxun

[1]: 
https://lore.kernel.org/qemu-devel/20230521102307.87081-1-jiaxun.y...@flygoat.com/T/#t
[2]: 
https://lore.kernel.org/qemu-devel/0bb0cded-8450-536e-b90f-1a9d33311...@linaro.org/T/#t

Jiaxun Yang (2):
  target/mips: Implement Loongson CSR instructions
  hw/mips/loongson3_virt: Remove CPU restrictions for TCG

 hw/mips/loongson3_virt.c |  4 --
 target/mips/cpu-defs.c.inc   |  9 
 target/mips/cpu.c|  8 
 target/mips/cpu.h| 40 
 target/mips/helper.h |  4 ++
 target/mips/internal.h   |  2 +
 target/mips/tcg/lcsr.decode  | 17 +++
 target/mips/tcg/lcsr_translate.c | 69 
 target/mips/tcg/meson.build  |  2 +
 target/mips/tcg/op_helper.c  | 16 +++
 target/mips/tcg/sysemu/lcsr_helper.c | 45 ++
 target/mips/tcg/sysemu/meson.build   |  4 ++
 target/mips/tcg/sysemu_helper.h.inc  |  8 
 target/mips/tcg/translate.c  |  3 ++
 target/mips/tcg/translate.h  |  7 +++
 15 files changed, 234 insertions(+), 4 deletions(-)
 create mode 100644 target/mips/tcg/lcsr.decode
 create mode 100644 target/mips/tcg/lcsr_translate.c
 create mode 100644 target/mips/tcg/sysemu/lcsr_helper.c

-- 
2.39.2 (Apple Git-143)




[PATCH 2/2] hw/mips/loongson3_virt: Remove CPU restrictions for TCG

2023-05-21 Thread Jiaxun Yang
After implemented CPUCFG and CSR, we are now able to boot Linux
kernel with Loongson-3A4000 CPU, so there is no point to restrict
CPU type for TCG.

Signed-off-by: Jiaxun Yang 
---
 hw/mips/loongson3_virt.c | 4 
 1 file changed, 4 deletions(-)

diff --git a/hw/mips/loongson3_virt.c b/hw/mips/loongson3_virt.c
index a57245012598..47289fb6bf85 100644
--- a/hw/mips/loongson3_virt.c
+++ b/hw/mips/loongson3_virt.c
@@ -488,10 +488,6 @@ static void mips_loongson3_virt_init(MachineState *machine)
 if (!machine->cpu_type) {
 machine->cpu_type = MIPS_CPU_TYPE_NAME("Loongson-3A1000");
 }
-if (!strstr(machine->cpu_type, "Loongson-3A1000")) {
-error_report("Loongson-3/TCG needs cpu type Loongson-3A1000");
-exit(1);
-}
 } else {
 if (!machine->cpu_type) {
 machine->cpu_type = MIPS_CPU_TYPE_NAME("Loongson-3A4000");
-- 
2.39.2 (Apple Git-143)




[PATCH 1/2] target/mips: Implement Loongson CSR instructions

2023-05-21 Thread Jiaxun Yang
Loongson introduced CSR instructions since 3A4000, which looks
similar to IOCSR and CPUCFG instructions we seen in LoongArch.

Unfortunately we don't have much document about those instructions,
bit fields of CPUCFG instructions and IOCSR registers can be found
at 3A4000's user manual, while instruction encodings can be found
at arch/mips/include/asm/mach-loongson64/loongson_regs.h from
Linux Kernel.

Our predefined CPUCFG bits are differ from actual 3A4000, since
we can't emulate all CPUCFG features present in 3A4000 for now,
we just enable bits for what we have in TCG.

Signed-off-by: Jiaxun Yang 
---
 target/mips/cpu-defs.c.inc   |  9 
 target/mips/cpu.c|  8 
 target/mips/cpu.h| 40 
 target/mips/helper.h |  4 ++
 target/mips/internal.h   |  2 +
 target/mips/tcg/lcsr.decode  | 17 +++
 target/mips/tcg/lcsr_translate.c | 69 
 target/mips/tcg/meson.build  |  2 +
 target/mips/tcg/op_helper.c  | 16 +++
 target/mips/tcg/sysemu/lcsr_helper.c | 45 ++
 target/mips/tcg/sysemu/meson.build   |  4 ++
 target/mips/tcg/sysemu_helper.h.inc  |  8 
 target/mips/tcg/translate.c  |  3 ++
 target/mips/tcg/translate.h  |  7 +++
 14 files changed, 234 insertions(+)
 create mode 100644 target/mips/tcg/lcsr.decode
 create mode 100644 target/mips/tcg/lcsr_translate.c
 create mode 100644 target/mips/tcg/sysemu/lcsr_helper.c

diff --git a/target/mips/cpu-defs.c.inc b/target/mips/cpu-defs.c.inc
index d45f245a6718..167c96cb2748 100644
--- a/target/mips/cpu-defs.c.inc
+++ b/target/mips/cpu-defs.c.inc
@@ -895,6 +895,15 @@ const mips_def_t mips_defs[] =
 .CP1_fcr31 = 0,
 .CP1_fcr31_rw_bitmask = 0xFF83,
 .MSAIR = (0x01 << MSAIR_ProcID) | (0x40 << MSAIR_Rev),
+.lcsr_cpucfg1 = (1 << CPUCFG1_FP) | (2 << CPUCFG1_FPREV) |
+(1 << CPUCFG1_MSA1) | (1 << CPUCFG1_LSLDR0) |
+(1 << CPUCFG1_LSPERF) | (1 << CPUCFG1_LSPERFX) |
+(1 << CPUCFG1_LSSYNCI) | (1 << CPUCFG1_LLEXC) |
+(1 << CPUCFG1_SCRAND) | (1 << CPUCFG1_MUALP) |
+(1 << CPUCFG1_KMUALEN) | (1 << CPUCFG1_ITLBT) |
+(1 << CPUCFG1_SFBP) | (1 << CPUCFG1_CDMAP),
+.lcsr_cpucfg2 = (1 << CPUCFG2_LEXT1) | (1 << CPUCFG2_LCSRP) |
+(1 << CPUCFG2_LDISBLIKELY),
 .SEGBITS = 48,
 .PABITS = 48,
 .insn_flags = CPU_MIPS64R2 | INSN_LOONGSON3A |
diff --git a/target/mips/cpu.c b/target/mips/cpu.c
index b7119cbbb459..e675b9178192 100644
--- a/target/mips/cpu.c
+++ b/target/mips/cpu.c
@@ -244,6 +244,8 @@ static void mips_cpu_reset_hold(Object *obj)
 env->CP0_PageGrain_rw_bitmask = env->cpu_model->CP0_PageGrain_rw_bitmask;
 env->CP0_PageGrain = env->cpu_model->CP0_PageGrain;
 env->CP0_EBaseWG_rw_bitmask = env->cpu_model->CP0_EBaseWG_rw_bitmask;
+env->lcsr_cpucfg1 = env->cpu_model->lcsr_cpucfg1;
+env->lcsr_cpucfg2 = env->cpu_model->lcsr_cpucfg2;
 env->active_fpu.fcr0 = env->cpu_model->CP1_fcr0;
 env->active_fpu.fcr31_rw_bitmask = env->cpu_model->CP1_fcr31_rw_bitmask;
 env->active_fpu.fcr31 = env->cpu_model->CP1_fcr31;
@@ -507,6 +509,12 @@ static void mips_cpu_initfn(Object *obj)
 cpu->count_div = clock_new(OBJECT(obj), "clk-div-count");
 env->count_clock = clock_new(OBJECT(obj), "clk-count");
 env->cpu_model = mcc->cpu_def;
+if (mcc->cpu_def->lcsr_cpucfg2 & (1 << CPUCFG2_LCSRP)) {
+memory_region_init_io(>system_iocsr, OBJECT(cpu), NULL,
+env, "iocsr", UINT64_MAX);
+address_space_init(>address_space_iocsr,
+>system_iocsr, "IOCSR");
+}
 }
 
 static char *mips_cpu_type_name(const char *cpu_model)
diff --git a/target/mips/cpu.h b/target/mips/cpu.h
index 1b8107b0af86..f63b128ff3d3 100644
--- a/target/mips/cpu.h
+++ b/target/mips/cpu.h
@@ -3,6 +3,9 @@
 
 #include "cpu-qom.h"
 #include "exec/cpu-defs.h"
+#ifndef CONFIG_USER_ONLY
+#include "exec/memory.h"
+#endif
 #include "fpu/softfloat-types.h"
 #include "hw/clock.h"
 #include "mips-defs.h"
@@ -1068,6 +1071,33 @@ typedef struct CPUArchState {
  */
 int32_t CP0_DESAVE;
 target_ulong CP0_KScratch[MIPS_KSCRATCH_NUM];
+/*
+ * Loongson CSR CPUCFG registers
+ */
+uint32_t lcsr_cpucfg1;
+#define CPUCFG1_FP 0
+#define CPUCFG1_FPREV  1
+#define CPUCFG1_MMI4
+#define CPUCFG1_MSA1   5
+#define CPUCFG1_MSA2   6
+#define CPUCFG1_LSLDR0 16
+#define CPUCFG1_LSPERF 17
+#define CPUCFG1_LSPERFX 18
+#define CPUCFG1_LSSYNCI 19
+#define CPUCFG1_LLEXC   20
+#define CPUCFG1_SCRAND  21
+#define CPUCFG1_MUALP   25
+#define CPUCFG1_KMUALEN 26
+#define CPUCFG1_ITLBT   27
+#define CPUCFG1_SFBP29
+#define CPUCFG1_CDMAP   30
+uint32_t lcsr_cpucfg2;
+#define CPUCFG2_LEXT1   0
+#define CPUCFG2_LEXT2   1
+#define CPUCFG2_LEXT3   2
+#define CPUCFG2_LSPW

Re: [PATCH 2/6] hw/ide/via: Wire up IDE legacy interrupts in host device

2023-05-21 Thread BALATON Zoltan

On Sun, 21 May 2023, BALATON Zoltan wrote:

On Sun, 21 May 2023, Bernhard Beschow wrote:

Resolves circular depencency between IDE function and south bridge.

Signed-off-by: Bernhard Beschow 
Reviewed-by: Mark Cave-Ayland 
---
hw/ide/via.c  | 6 --
hw/isa/vt82c686.c | 5 +
2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/hw/ide/via.c b/hw/ide/via.c
index 177baea9a7..0caae52276 100644
--- a/hw/ide/via.c
+++ b/hw/ide/via.c
@@ -31,6 +31,7 @@
#include "sysemu/dma.h"
#include "hw/isa/vt82c686.h"
#include "hw/ide/pci.h"
+#include "hw/irq.h"
#include "trace.h"

static uint64_t bmdma_read(void *opaque, hwaddr addr,
@@ -104,7 +105,8 @@ static void bmdma_setup_bar(PCIIDEState *d)

static void via_ide_set_irq(void *opaque, int n, int level)
{
-PCIDevice *d = PCI_DEVICE(opaque);
+PCIIDEState *s = opaque;
+PCIDevice *d = PCI_DEVICE(s);


These are the same structure so can be cast into each other but for 
consistency it's better to also change


qdev_init_gpio_in(ds, via_ide_set_irq, ARRAY_SIZE(d->bus));

to pass the PCIIDEState so d instead of ds in via_ide_realize().


Ignore this. That function takes a DeviceState and seems no separate 
argument for the opaque pointer so no change is needed.


Regards,
BALATON Zoltan



Re: [PATCH 6/6] hw/ide/piix: Move registration of VMStateDescription to DeviceClass

2023-05-21 Thread BALATON Zoltan

On Sun, 21 May 2023, Bernhard Beschow wrote:

The modern, declarative way to set up VM state handling is to assign to
DeviceClass::vmsd attribute.

There shouldn't be any change in behavior since dc->vmsd causes
vmstate_register_with_alias_id() to be called on the instance during
the instance init phase. vmstate_register() was also called during the
instance init phase which forwards to vmstate_register_with_alias_id()
internally. Checking the migration schema before and after this patch confirms:

before:

qemu-system-x86_64 -S
qemu > migrate -d exec:cat>before.mig


after:

qemu-system-x86_64 -S
qemu > migrate -d exec:cat>after.mig



analyze-migration.py -d desc -f before.mig > before.json
analyze-migration.py -d desc -f after.mig > after.json
diff before.json after.json

-> empty


Missing Signed-off-by line.

Regards,
BALATON Zoltah


---
hw/ide/piix.c | 5 ++---
1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/hw/ide/piix.c b/hw/ide/piix.c
index 47e0b474c3..151f206046 100644
--- a/hw/ide/piix.c
+++ b/hw/ide/piix.c
@@ -28,7 +28,6 @@
 */

#include "qemu/osdep.h"
-#include "migration/vmstate.h"
#include "qapi/error.h"
#include "hw/pci/pci.h"
#include "hw/ide/piix.h"
@@ -159,8 +158,6 @@ static void pci_piix_ide_realize(PCIDevice *dev, Error 
**errp)
bmdma_setup_bar(d);
pci_register_bar(dev, 4, PCI_BASE_ADDRESS_SPACE_IO, >bmdma_bar);

-vmstate_register(VMSTATE_IF(dev), 0, _ide_pci, d);
-
for (unsigned i = 0; i < 2; i++) {
if (!pci_piix_init_bus(d, i, errp)) {
return;
@@ -186,6 +183,7 @@ static void piix3_ide_class_init(ObjectClass *klass, void 
*data)
PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);

dc->reset = piix_ide_reset;
+dc->vmsd = _ide_pci;
k->realize = pci_piix_ide_realize;
k->exit = pci_piix_ide_exitfn;
k->vendor_id = PCI_VENDOR_ID_INTEL;
@@ -208,6 +206,7 @@ static void piix4_ide_class_init(ObjectClass *klass, void 
*data)
PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);

dc->reset = piix_ide_reset;
+dc->vmsd = _ide_pci;
k->realize = pci_piix_ide_realize;
k->exit = pci_piix_ide_exitfn;
k->vendor_id = PCI_VENDOR_ID_INTEL;






[PATCH v3 0/7] migration: Add switchover ack capability and VFIO precopy support

2023-05-21 Thread Avihai Horon
Hello everyone,

This is v3 of the switchover ack series (previously called precopy
initial data).

Changes from v2 [4]:
* Rebased on latest master branch.
* Changed the capability name to "switchover-ack" and the related
  code/docs accordingly. (Peter)
* Added a counter for the number of switchover ack users in the source
  and used it to skip switchover ack if there are no users (instead of
  setting the switchover acked flag to true). (Peter)
* Added R-bs.

Changes from v1 [3]:
* Rebased on latest master branch.
* Updated to latest QAPI doc comment conventions and refined
  QAPI docs and capability error message. (Markus)
* Followed Peter/Juan suggestion and removed the handshake between
  source and destination.
  Now the capability must be set on both source and destination.
  Compatibility of this feature between different QEMU versions or
  different host capabilities (i.e., kernel) is achieved in the regular
  way of device properties and hw_comapt_x_y.
* Replaced is_initial_data_active() and initial_data_loaded()
  SaveVMHandlers handlers with a notification mechanism. (Peter)
* Set the capability also in destination in the migration test.
* Added VFIO device property x-allow-pre-copy to be able to preserve
  compatibility between different QEMU versions or different host
  capabilities (i.e., kernel).
* Changed VFIO precopy initial data implementation according to the
  above changes.
* Documented VFIO precopy initial data support in VFIO migration
  documentation.
* Added R-bs.

===

This series adds a new migration capability called "switchover ack". The
purpose of this capability is to reduce migration downtime in cases
where loading of migration data in the destination can take a lot of
time, such as with VFIO migration data.

The series then moves to add precopy support and switchover ack support
for VFIO migration.

Switchover ack is used by VFIO migration, but other migrated devices can
add support for it and use it as well.

=== Background ===

Migration downtime estimation is calculated based on bandwidth and
remaining migration data. This assumes that loading of migration data in
the destination takes a negligible amount of time and that downtime
depends only on network speed.

While this may be true for RAM, it's not necessarily true for other
migrated devices. For example, loading the data of a VFIO device in the
destination might require from the device to allocate resources and
prepare internal data structures which can take a significant amount of
time to do.

This poses a problem, as the source may think that the remaining
migration data is small enough to meet the downtime limit, so it will
stop the VM and complete the migration, but in fact sending and loading
the data in the destination may take longer than the downtime limit.

To solve this, VFIO migration uAPI defines "initial bytes" as part of
its precopy stream [1]. Initial bytes can be used in various ways to
improve VFIO migration performance. For example, it can be used to
transfer device metadata to pre-allocate resources in the destination.
However, for this to work we need to make sure that all initial bytes
are sent and loaded in the destination before the source VM is stopped.

The new switchover ack migration capability helps us achieve this.
It prevents the source from stopping the VM and completing the migration
until an ACK is received from the destination that it's OK to do so.
Thus, a VFIO device can make sure that its initial bytes were sent
and loaded in the destination before the source VM is stopped.

Note that this relies on the return path capability to communicate from
the destination back to the source.

=== Flow of operation ===

To use switchover ack, the capability must be enabled in both the source
and the destination.

During migration setup, migration code calls the switchover_ack_needed()
SaveVMHandlers handler of the migrated devices, both in the source and
the destination, to check if switchover ack is used by them. In the
destination, a "switchover_ack_pending_num" counter is increased for
each migrated device that supports this feature. It will be used later
to mark when an ACK should be sent to the source.

Migration is active and the source starts to send precopy data as usual.
In the destination, when a migrated device thinks it's OK to do
switchover, it notifies the migration code about it and the
"switchover_ack_pending_num" counter is decreased. For example, for a
VFIO device it's when the device receives and loads its initial bytes.

When the "switchover_ack_pending_num" counter reaches zero, it means
that all devices agree to do switchover and an ACK is sent to the
source, which will now be able to complete the migration when
appropriate.

=== Test results ===

The below table shows the downtime of two identical migrations. In the
first migration swithcover ack is disabled and in the second it is
enabled. The migrated VM is assigned with a mlx5 VFIO device which has
300MB of device 

Re: [PATCH 5/6] hw/ide: Extract bmdma_status_writeb()

2023-05-21 Thread BALATON Zoltan

On Sun, 21 May 2023, Bernhard Beschow wrote:

Every TYPE_PCI_IDE device performs the same not-so-trivial bit manipulation by
copy'n'paste code. Extract this into bmdma_status_writeb(), mirroring
bmdma_cmd_writeb().

Signed-off-by: Bernhard Beschow 


Reviewed-by: BALATON Zoltan 



[PATCH v3 5/7] vfio/migration: Refactor vfio_save_block() to return saved data size

2023-05-21 Thread Avihai Horon
Refactor vfio_save_block() to return the size of saved data on success
and -errno on error.

This will be used in next patch to implement VFIO migration pre-copy
support.

Signed-off-by: Avihai Horon 
Reviewed-by: Cédric Le Goater 
Reviewed-by: Juan Quintela 
---
 hw/vfio/migration.c | 17 +
 1 file changed, 9 insertions(+), 8 deletions(-)

diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
index 6b58dddb88..235978fd68 100644
--- a/hw/vfio/migration.c
+++ b/hw/vfio/migration.c
@@ -241,8 +241,8 @@ static int vfio_query_stop_copy_size(VFIODevice *vbasedev,
 return 0;
 }
 
-/* Returns 1 if end-of-stream is reached, 0 if more data and -errno if error */
-static int vfio_save_block(QEMUFile *f, VFIOMigration *migration)
+/* Returns the size of saved data on success and -errno on error */
+static ssize_t vfio_save_block(QEMUFile *f, VFIOMigration *migration)
 {
 ssize_t data_size;
 
@@ -252,7 +252,7 @@ static int vfio_save_block(QEMUFile *f, VFIOMigration 
*migration)
 return -errno;
 }
 if (data_size == 0) {
-return 1;
+return 0;
 }
 
 qemu_put_be64(f, VFIO_MIG_FLAG_DEV_DATA_STATE);
@@ -262,7 +262,7 @@ static int vfio_save_block(QEMUFile *f, VFIOMigration 
*migration)
 
 trace_vfio_save_block(migration->vbasedev->name, data_size);
 
-return qemu_file_get_error(f);
+return qemu_file_get_error(f) ?: data_size;
 }
 
 /* -- */
@@ -335,6 +335,7 @@ static void vfio_state_pending_exact(void *opaque, uint64_t 
*must_precopy,
 static int vfio_save_complete_precopy(QEMUFile *f, void *opaque)
 {
 VFIODevice *vbasedev = opaque;
+ssize_t data_size;
 int ret;
 
 /* We reach here with device state STOP only */
@@ -345,11 +346,11 @@ static int vfio_save_complete_precopy(QEMUFile *f, void 
*opaque)
 }
 
 do {
-ret = vfio_save_block(f, vbasedev->migration);
-if (ret < 0) {
-return ret;
+data_size = vfio_save_block(f, vbasedev->migration);
+if (data_size < 0) {
+return data_size;
 }
-} while (!ret);
+} while (data_size);
 
 qemu_put_be64(f, VFIO_MIG_FLAG_END_OF_STATE);
 ret = qemu_file_get_error(f);
-- 
2.26.3




[PATCH v3 4/7] tests: Add migration switchover ack capability test

2023-05-21 Thread Avihai Horon
Add migration switchover ack capability test. The test runs without
devices that support this capability, but is still useful to make sure
it didn't break anything.

Signed-off-by: Avihai Horon 
Reviewed-by: Juan Quintela 
Reviewed-by: Peter Xu 
---
 tests/qtest/migration-test.c | 26 ++
 1 file changed, 26 insertions(+)

diff --git a/tests/qtest/migration-test.c b/tests/qtest/migration-test.c
index b99b49a314..d246a5bbc5 100644
--- a/tests/qtest/migration-test.c
+++ b/tests/qtest/migration-test.c
@@ -1648,6 +1648,28 @@ static void test_precopy_tcp_plain(void)
 test_precopy_common();
 }
 
+static void *test_migrate_switchover_ack_start(QTestState *from, QTestState 
*to)
+{
+
+migrate_set_capability(from, "return-path", true);
+migrate_set_capability(to, "return-path", true);
+
+migrate_set_capability(from, "switchover-ack", true);
+migrate_set_capability(to, "switchover-ack", true);
+
+return NULL;
+}
+
+static void test_precopy_tcp_switchover_ack(void)
+{
+MigrateCommon args = {
+.listen_uri = "tcp:127.0.0.1:0",
+.start_hook = test_migrate_switchover_ack_start,
+};
+
+test_precopy_common();
+}
+
 #ifdef CONFIG_GNUTLS
 static void test_precopy_tcp_tls_psk_match(void)
 {
@@ -2695,6 +2717,10 @@ int main(int argc, char **argv)
 #endif /* CONFIG_GNUTLS */
 
 qtest_add_func("/migration/precopy/tcp/plain", test_precopy_tcp_plain);
+
+qtest_add_func("/migration/precopy/tcp/plain/switchover-ack",
+   test_precopy_tcp_switchover_ack);
+
 #ifdef CONFIG_GNUTLS
 qtest_add_func("/migration/precopy/tcp/tls/psk/match",
test_precopy_tcp_tls_psk_match);
-- 
2.26.3




[PATCH v3 7/7] vfio/migration: Add support for switchover ack capability

2023-05-21 Thread Avihai Horon
Loading of a VFIO device's data can take a substantial amount of time as
the device may need to allocate resources, prepare internal data
structures, etc. This can increase migration downtime, especially for
VFIO devices with a lot of resources.

To solve this, VFIO migration uAPI defines "initial bytes" as part of
its precopy data stream. Initial bytes can be used in various ways to
improve VFIO migration performance. For example, it can be used to
transfer device metadata to pre-allocate resources in the destination.
However, for this to work we need to make sure that all initial bytes
are sent and loaded in the destination before the source VM is stopped.

Use migration switchover ack capability to make sure a VFIO device's
initial bytes are sent and loaded in the destination before the source
stops the VM and attempts to complete the migration.
This can significantly reduce migration downtime for some devices.

As precopy support and precopy initial bytes support come together in
VFIO migration, use x-allow-pre-copy device property to control usage of
this feature as well.

Signed-off-by: Avihai Horon 
---
 docs/devel/vfio-migration.rst | 10 +
 include/hw/vfio/vfio-common.h |  2 ++
 hw/vfio/migration.c   | 42 ++-
 3 files changed, 53 insertions(+), 1 deletion(-)

diff --git a/docs/devel/vfio-migration.rst b/docs/devel/vfio-migration.rst
index e896b2a673..e75793b76a 100644
--- a/docs/devel/vfio-migration.rst
+++ b/docs/devel/vfio-migration.rst
@@ -16,6 +16,13 @@ helps to reduce the total downtime of the VM. VFIO devices 
opt-in to pre-copy
 support by reporting the VFIO_MIGRATION_PRE_COPY flag in the
 VFIO_DEVICE_FEATURE_MIGRATION ioctl.
 
+When pre-copy is supported, it's possible to further reduce downtime by
+enabling "switchover-ack" migration capability.
+VFIO migration uAPI defines "initial bytes" as part of its pre-copy data stream
+and recommends that the initial bytes are sent and loaded in the destination
+before stopping the source VM. Enabling this migration capability will
+guarantee that and thus, can potentially reduce downtime even further.
+
 Note that currently VFIO migration is supported only for a single device. This
 is due to VFIO migration's lack of P2P support. However, P2P support is planned
 to be added later on.
@@ -45,6 +52,9 @@ VFIO implements the device hooks for the iterative approach 
as follows:
 * A ``save_live_iterate`` function that reads the VFIO device's data from the
   vendor driver during iterative pre-copy phase.
 
+* A ``switchover_ack_needed`` function that checks if the VFIO device uses
+  "switchover-ack" migration capability when this capability is enabled.
+
 * A ``save_state`` function to save the device config space if it is present.
 
 * A ``save_live_complete_precopy`` function that sets the VFIO device in
diff --git a/include/hw/vfio/vfio-common.h b/include/hw/vfio/vfio-common.h
index 5ce7a01d56..b4a7eb0f9a 100644
--- a/include/hw/vfio/vfio-common.h
+++ b/include/hw/vfio/vfio-common.h
@@ -69,6 +69,8 @@ typedef struct VFIOMigration {
 uint64_t precopy_init_size;
 uint64_t precopy_dirty_size;
 uint64_t mig_flags;
+bool switchover_ack_needed;
+bool initial_data_sent;
 } VFIOMigration;
 
 typedef struct VFIOAddressSpace {
diff --git a/hw/vfio/migration.c b/hw/vfio/migration.c
index 418efed019..09c669c1d8 100644
--- a/hw/vfio/migration.c
+++ b/hw/vfio/migration.c
@@ -18,6 +18,7 @@
 #include "sysemu/runstate.h"
 #include "hw/vfio/vfio-common.h"
 #include "migration/migration.h"
+#include "migration/savevm.h"
 #include "migration/vmstate.h"
 #include "migration/qemu-file.h"
 #include "migration/register.h"
@@ -45,6 +46,7 @@
 #define VFIO_MIG_FLAG_DEV_CONFIG_STATE  (0xef12ULL)
 #define VFIO_MIG_FLAG_DEV_SETUP_STATE   (0xef13ULL)
 #define VFIO_MIG_FLAG_DEV_DATA_STATE(0xef14ULL)
+#define VFIO_MIG_FLAG_DEV_INIT_DATA_SENT (0xef15ULL)
 
 /*
  * This is an arbitrary size based on migration of mlx5 devices, where 
typically
@@ -380,6 +382,8 @@ static void vfio_save_cleanup(void *opaque)
 
 g_free(migration->data_buffer);
 migration->data_buffer = NULL;
+migration->switchover_ack_needed = false;
+migration->initial_data_sent = false;
 vfio_migration_cleanup(vbasedev);
 trace_vfio_save_cleanup(vbasedev->name);
 }
@@ -455,10 +459,17 @@ static int vfio_save_iterate(QEMUFile *f, void *opaque)
 if (data_size < 0) {
 return data_size;
 }
-qemu_put_be64(f, VFIO_MIG_FLAG_END_OF_STATE);
 
 vfio_update_estimated_pending_data(migration, data_size);
 
+if (migration->switchover_ack_needed && !migration->precopy_init_size &&
+!migration->initial_data_sent) {
+qemu_put_be64(f, VFIO_MIG_FLAG_DEV_INIT_DATA_SENT);
+migration->initial_data_sent = true;
+} else {
+qemu_put_be64(f, VFIO_MIG_FLAG_END_OF_STATE);
+}
+
 trace_vfio_save_iterate(vbasedev->name);
 
 /*
@@ 

[PATCH v3 3/7] migration: Enable switchover ack capability

2023-05-21 Thread Avihai Horon
Now that switchover ack logic has been implemented, enable the
capability.

Signed-off-by: Avihai Horon 
Reviewed-by: Juan Quintela 
Reviewed-by: Peter Xu 
---
 migration/options.c | 4 
 1 file changed, 4 deletions(-)

diff --git a/migration/options.c b/migration/options.c
index 16007afca6..5a9505adf7 100644
--- a/migration/options.c
+++ b/migration/options.c
@@ -562,10 +562,6 @@ bool migrate_caps_check(bool *old_caps, bool *new_caps, 
Error **errp)
  "'return-path'");
 return false;
 }
-
-/* Disable this capability until it's implemented */
-error_setg(errp, "'switchover-ack' is not implemented yet");
-return false;
 }
 
 return true;
-- 
2.26.3




[PATCH v3 2/7] migration: Implement switchover ack logic

2023-05-21 Thread Avihai Horon
Implement switchover ack logic. This prevents the source from stopping
the VM and completing the migration until an ACK is received from the
destination that it's OK to do so.

To achieve this, a new SaveVMHandlers handler switchover_ack_needed()
and a new return path message MIG_RP_MSG_SWITCHOVER_ACK are added.

The switchover_ack_needed() handler is called during migration setup
both in the source and the destination to check if switchover ack is
used by the migrated device.

When switchover is approved by all migrated devices in the destination
that support this capability, the MIG_RP_MSG_INITIAL_DATA_LOADED_ACK
return path message is sent to the source to notify it that it's OK to
do switchover.

Signed-off-by: Avihai Horon 
---
 include/migration/register.h |  3 ++
 migration/migration.h| 16 +++
 migration/savevm.h   |  2 ++
 migration/migration.c| 42 +--
 migration/savevm.c   | 56 
 migration/trace-events   |  4 +++
 6 files changed, 121 insertions(+), 2 deletions(-)

diff --git a/include/migration/register.h b/include/migration/register.h
index a8dfd8fefd..cda36d377b 100644
--- a/include/migration/register.h
+++ b/include/migration/register.h
@@ -71,6 +71,9 @@ typedef struct SaveVMHandlers {
 int (*load_cleanup)(void *opaque);
 /* Called when postcopy migration wants to resume from failure */
 int (*resume_prepare)(MigrationState *s, void *opaque);
+
+/* Checks if switchover ack should be used. Called both in src and dest */
+bool (*switchover_ack_needed)(void *opaque);
 } SaveVMHandlers;
 
 int register_savevm_live(const char *idstr,
diff --git a/migration/migration.h b/migration/migration.h
index 48a46123a0..e209860cce 100644
--- a/migration/migration.h
+++ b/migration/migration.h
@@ -209,6 +209,13 @@ struct MigrationIncomingState {
  * contains valid information.
  */
 QemuMutex page_request_mutex;
+
+/*
+ * Number of devices that have yet to approve switchover. When this reaches
+ * zero an ACK that it's OK to do switchover is sent to the source. No lock
+ * is needed as this field is updated serially.
+ */
+unsigned int switchover_ack_pending_num;
 };
 
 MigrationIncomingState *migration_incoming_get_current(void);
@@ -437,6 +444,14 @@ struct MigrationState {
 
 /* QEMU_VM_VMDESCRIPTION content filled for all non-iterable devices. */
 JSONWriter *vmdesc;
+
+/* Number of devices that use switchover ack capability */
+unsigned int switchover_ack_user_num;
+/*
+ * Indicates whether an ACK from the destination that it's OK to do
+ * switchover has been received.
+ */
+bool switchover_acked;
 };
 
 void migrate_set_state(int *state, int old_state, int new_state);
@@ -477,6 +492,7 @@ int 
migrate_send_rp_message_req_pages(MigrationIncomingState *mis,
 void migrate_send_rp_recv_bitmap(MigrationIncomingState *mis,
  char *block_name);
 void migrate_send_rp_resume_ack(MigrationIncomingState *mis, uint32_t value);
+int migrate_send_rp_switchover_ack(MigrationIncomingState *mis);
 
 void dirty_bitmap_mig_before_vm_start(void);
 void dirty_bitmap_mig_cancel_outgoing(void);
diff --git a/migration/savevm.h b/migration/savevm.h
index fb636735f0..5c3e1a026b 100644
--- a/migration/savevm.h
+++ b/migration/savevm.h
@@ -32,6 +32,7 @@
 bool qemu_savevm_state_blocked(Error **errp);
 void qemu_savevm_non_migratable_list(strList **reasons);
 void qemu_savevm_state_setup(QEMUFile *f);
+void qemu_savevm_state_switchover_ack_needed(MigrationState *ms);
 bool qemu_savevm_state_guest_unplug_pending(void);
 int qemu_savevm_state_resume_prepare(MigrationState *s);
 void qemu_savevm_state_header(QEMUFile *f);
@@ -65,6 +66,7 @@ int qemu_loadvm_state(QEMUFile *f);
 void qemu_loadvm_state_cleanup(void);
 int qemu_loadvm_state_main(QEMUFile *f, MigrationIncomingState *mis);
 int qemu_load_device_state(QEMUFile *f);
+int qemu_loadvm_approve_switchover(void);
 int qemu_savevm_state_complete_precopy_non_iterable(QEMUFile *f,
 bool in_postcopy, bool inactivate_disks);
 
diff --git a/migration/migration.c b/migration/migration.c
index 5de7f734b9..87423ec30c 100644
--- a/migration/migration.c
+++ b/migration/migration.c
@@ -78,6 +78,7 @@ enum mig_rp_message_type {
 MIG_RP_MSG_REQ_PAGES,/* data (start: be64, len: be32) */
 MIG_RP_MSG_RECV_BITMAP,  /* send recved_bitmap back to source */
 MIG_RP_MSG_RESUME_ACK,   /* tell source that we are ready to resume */
+MIG_RP_MSG_SWITCHOVER_ACK, /* Tell source it's OK to do switchover */
 
 MIG_RP_MSG_MAX
 };
@@ -760,6 +761,11 @@ bool migration_has_all_channels(void)
 return true;
 }
 
+int migrate_send_rp_switchover_ack(MigrationIncomingState *mis)
+{
+return migrate_send_rp_message(mis, MIG_RP_MSG_SWITCHOVER_ACK, 0, NULL);
+}
+
 /*
  * Send a 'SHUT' message on the return channel with the given value
  * to indicate that we've 

[PATCH v3 6/7] vfio/migration: Add VFIO migration pre-copy support

2023-05-21 Thread Avihai Horon
Pre-copy support allows the VFIO device data to be transferred while the
VM is running. This helps to accommodate VFIO devices that have a large
amount of data that needs to be transferred, and it can reduce migration
downtime.

Pre-copy support is optional in VFIO migration protocol v2.
Implement pre-copy of VFIO migration protocol v2 and use it for devices
that support it. Full description of it can be found here [1].

In addition, add a new VFIO device property x-allow-pre-copy to keep
migration compatibility to/from older QEMU versions that don't have VFIO
pre-copy support.

[1]
https://lore.kernel.org/kvm/20221206083438.37807-3-yish...@nvidia.com/

Signed-off-by: Avihai Horon 
---
 docs/devel/vfio-migration.rst |  35 +---
 include/hw/vfio/vfio-common.h |   4 +
 hw/core/machine.c |   1 +
 hw/vfio/common.c  |   6 +-
 hw/vfio/migration.c   | 163 --
 hw/vfio/pci.c |   2 +
 hw/vfio/trace-events  |   4 +-
 7 files changed, 193 insertions(+), 22 deletions(-)

diff --git a/docs/devel/vfio-migration.rst b/docs/devel/vfio-migration.rst
index 1b68ccf115..e896b2a673 100644
--- a/docs/devel/vfio-migration.rst
+++ b/docs/devel/vfio-migration.rst
@@ -7,12 +7,14 @@ the guest is running on source host and restoring this saved 
state on the
 destination host. This document details how saving and restoring of VFIO
 devices is done in QEMU.
 
-Migration of VFIO devices currently consists of a single stop-and-copy phase.
-During the stop-and-copy phase the guest is stopped and the entire VFIO device
-data is transferred to the destination.
-
-The pre-copy phase of migration is currently not supported for VFIO devices.
-Support for VFIO pre-copy will be added later on.
+Migration of VFIO devices consists of two phases: the optional pre-copy phase,
+and the stop-and-copy phase. The pre-copy phase is iterative and allows to
+accommodate VFIO devices that have a large amount of data that needs to be
+transferred. The iterative pre-copy phase of migration allows for the guest to
+continue whilst the VFIO device state is transferred to the destination, this
+helps to reduce the total downtime of the VM. VFIO devices opt-in to pre-copy
+support by reporting the VFIO_MIGRATION_PRE_COPY flag in the
+VFIO_DEVICE_FEATURE_MIGRATION ioctl.
 
 Note that currently VFIO migration is supported only for a single device. This
 is due to VFIO migration's lack of P2P support. However, P2P support is planned
@@ -29,10 +31,20 @@ VFIO implements the device hooks for the iterative approach 
as follows:
 * A ``load_setup`` function that sets the VFIO device on the destination in
   _RESUMING state.
 
+* A ``state_pending_estimate`` function that reports an estimate of the
+  remaining pre-copy data that the vendor driver has yet to save for the VFIO
+  device.
+
 * A ``state_pending_exact`` function that reads pending_bytes from the vendor
   driver, which indicates the amount of data that the vendor driver has yet to
   save for the VFIO device.
 
+* An ``is_active_iterate`` function that indicates ``save_live_iterate`` is
+  active only when the VFIO device is in pre-copy states.
+
+* A ``save_live_iterate`` function that reads the VFIO device's data from the
+  vendor driver during iterative pre-copy phase.
+
 * A ``save_state`` function to save the device config space if it is present.
 
 * A ``save_live_complete_precopy`` function that sets the VFIO device in
@@ -111,8 +123,10 @@ Flow of state changes during Live migration
 ===
 
 Below is the flow of state change during live migration.
-The values in the brackets represent the VM state, the migration state, and
+The values in the parentheses represent the VM state, the migration state, and
 the VFIO device state, respectively.
+The text in the square brackets represents the flow if the VFIO device supports
+pre-copy.
 
 Live migration save path
 
@@ -124,11 +138,12 @@ Live migration save path
   |
  migrate_init spawns migration_thread
 Migration thread then calls each device's .save_setup()
-   (RUNNING, _SETUP, _RUNNING)
+  (RUNNING, _SETUP, _RUNNING [_PRE_COPY])
   |
-  (RUNNING, _ACTIVE, _RUNNING)
- If device is active, get pending_bytes by .state_pending_exact()
+  (RUNNING, _ACTIVE, _RUNNING [_PRE_COPY])
+  If device is active, get pending_bytes by 
.state_pending_{estimate,exact}()
   If total pending_bytes >= threshold_size, call .save_live_iterate()
+  [Data of VFIO device for pre-copy phase is copied]
 Iterate till total pending bytes converge and are less than threshold
   |
   On migration completion, vCPU stops and calls .save_live_complete_precopy for
diff --git 

[PATCH v3 1/7] migration: Add switchover ack capability

2023-05-21 Thread Avihai Horon
Migration downtime estimation is calculated based on bandwidth and
remaining migration data. This assumes that loading of migration data in
the destination takes a negligible amount of time and that downtime
depends only on network speed.

While this may be true for RAM, it's not necessarily true for other
migration users. For example, loading the data of a VFIO device in the
destination might require from the device to allocate resources, prepare
internal data structures and so on. These operations can take a
significant amount of time which can increase migration downtime.

This patch adds a new capability "switchover ack" that prevents the
source from stopping the VM and completing the migration until an ACK
is received from the destination that it's OK to do so.

This can be used by migrated devices in various ways to reduce downtime.
For example, a device can send initial precopy metadata to pre-allocate
resources in the destination and use this capability to make sure that
the pre-allocation is completed before the source VM is stopped, so it
will have full effect.

This new capability relies on the return path capability to communicate
from the destination back to the source.

The actual implementation of the capability will be added in the
following patches.

Signed-off-by: Avihai Horon 
---
 qapi/migration.json | 12 +++-
 migration/options.h |  1 +
 migration/options.c | 21 +
 3 files changed, 33 insertions(+), 1 deletion(-)

diff --git a/qapi/migration.json b/qapi/migration.json
index 179af0c4d8..061ea512e0 100644
--- a/qapi/migration.json
+++ b/qapi/migration.json
@@ -487,6 +487,16 @@
 # and should not affect the correctness of postcopy migration.
 # (since 7.1)
 #
+# @switchover-ack: If enabled, migration will not stop the source VM
+# and complete the migration until an ACK is received from the
+# destination that it's OK to do so.  Exactly when this ACK is
+# sent depends on the migrated devices that use this feature.
+# For example, a device can use it to make sure some of its data
+# is sent and loaded in the destination before doing switchover.
+# This can reduce downtime if devices that support this capability
+# are present.  'return-path' capability must be enabled to use
+# it.  (since 8.1)
+#
 # Features:
 #
 # @unstable: Members @x-colo and @x-ignore-shared are experimental.
@@ -502,7 +512,7 @@
'dirty-bitmaps', 'postcopy-blocktime', 'late-block-activate',
{ 'name': 'x-ignore-shared', 'features': [ 'unstable' ] },
'validate-uuid', 'background-snapshot',
-   'zero-copy-send', 'postcopy-preempt'] }
+   'zero-copy-send', 'postcopy-preempt', 'switchover-ack'] }
 
 ##
 # @MigrationCapabilityStatus:
diff --git a/migration/options.h b/migration/options.h
index 45991af3c2..9aaf363322 100644
--- a/migration/options.h
+++ b/migration/options.h
@@ -40,6 +40,7 @@ bool migrate_postcopy_ram(void);
 bool migrate_rdma_pin_all(void);
 bool migrate_release_ram(void);
 bool migrate_return_path(void);
+bool migrate_switchover_ack(void);
 bool migrate_validate_uuid(void);
 bool migrate_xbzrle(void);
 bool migrate_zero_blocks(void);
diff --git a/migration/options.c b/migration/options.c
index b62ab30cd5..16007afca6 100644
--- a/migration/options.c
+++ b/migration/options.c
@@ -185,6 +185,8 @@ Property migration_properties[] = {
 DEFINE_PROP_MIG_CAP("x-zero-copy-send",
 MIGRATION_CAPABILITY_ZERO_COPY_SEND),
 #endif
+DEFINE_PROP_MIG_CAP("x-switchover-ack",
+MIGRATION_CAPABILITY_SWITCHOVER_ACK),
 
 DEFINE_PROP_END_OF_LIST(),
 };
@@ -308,6 +310,13 @@ bool migrate_return_path(void)
 return s->capabilities[MIGRATION_CAPABILITY_RETURN_PATH];
 }
 
+bool migrate_switchover_ack(void)
+{
+MigrationState *s = migrate_get_current();
+
+return s->capabilities[MIGRATION_CAPABILITY_SWITCHOVER_ACK];
+}
+
 bool migrate_validate_uuid(void)
 {
 MigrationState *s = migrate_get_current();
@@ -547,6 +556,18 @@ bool migrate_caps_check(bool *old_caps, bool *new_caps, 
Error **errp)
 }
 }
 
+if (new_caps[MIGRATION_CAPABILITY_SWITCHOVER_ACK]) {
+if (!new_caps[MIGRATION_CAPABILITY_RETURN_PATH]) {
+error_setg(errp, "Capability 'switchover-ack' requires capability "
+ "'return-path'");
+return false;
+}
+
+/* Disable this capability until it's implemented */
+error_setg(errp, "'switchover-ack' is not implemented yet");
+return false;
+}
+
 return true;
 }
 
-- 
2.26.3




Re: [PATCH 2/6] hw/ide/via: Wire up IDE legacy interrupts in host device

2023-05-21 Thread BALATON Zoltan

On Sun, 21 May 2023, Bernhard Beschow wrote:

Resolves circular depencency between IDE function and south bridge.

Signed-off-by: Bernhard Beschow 
Reviewed-by: Mark Cave-Ayland 
---
hw/ide/via.c  | 6 --
hw/isa/vt82c686.c | 5 +
2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/hw/ide/via.c b/hw/ide/via.c
index 177baea9a7..0caae52276 100644
--- a/hw/ide/via.c
+++ b/hw/ide/via.c
@@ -31,6 +31,7 @@
#include "sysemu/dma.h"
#include "hw/isa/vt82c686.h"
#include "hw/ide/pci.h"
+#include "hw/irq.h"
#include "trace.h"

static uint64_t bmdma_read(void *opaque, hwaddr addr,
@@ -104,7 +105,8 @@ static void bmdma_setup_bar(PCIIDEState *d)

static void via_ide_set_irq(void *opaque, int n, int level)
{
-PCIDevice *d = PCI_DEVICE(opaque);
+PCIIDEState *s = opaque;
+PCIDevice *d = PCI_DEVICE(s);


These are the same structure so can be cast into each other but for 
consistency it's better to also change


qdev_init_gpio_in(ds, via_ide_set_irq, ARRAY_SIZE(d->bus));

to pass the PCIIDEState so d instead of ds in via_ide_realize().

Regards,
BALATON Zoltan


if (level) {
d->config[0x70 + n * 8] |= 0x80;
@@ -112,7 +114,7 @@ static void via_ide_set_irq(void *opaque, int n, int level)
d->config[0x70 + n * 8] &= ~0x80;
}

-via_isa_set_irq(pci_get_function_0(d), 14 + n, level);
+qemu_set_irq(s->isa_irq[n], level);
}

static void via_ide_reset(DeviceState *dev)
diff --git a/hw/isa/vt82c686.c b/hw/isa/vt82c686.c
index ca89119ce0..8016c71315 100644
--- a/hw/isa/vt82c686.c
+++ b/hw/isa/vt82c686.c
@@ -692,6 +692,10 @@ static void via_isa_realize(PCIDevice *d, Error **errp)
if (!qdev_realize(DEVICE(>ide), BUS(pci_bus), errp)) {
return;
}
+for (i = 0; i < 2; i++) {
+qdev_connect_gpio_out_named(DEVICE(>ide), "isa-irq", i,
+s->isa_irqs_in[14 + i]);
+}

/* Functions 2-3: USB Ports */
for (i = 0; i < ARRAY_SIZE(s->uhci); i++) {
@@ -814,6 +818,7 @@ static void vt8231_isa_reset(DeviceState *dev)
 PCI_COMMAND_MASTER | PCI_COMMAND_SPECIAL);
pci_set_word(pci_conf + PCI_STATUS, PCI_STATUS_DEVSEL_MEDIUM);

+pci_conf[0x4c] = 0x04; /* IDE interrupt Routing */
pci_conf[0x58] = 0x40; /* Miscellaneous Control 0 */
pci_conf[0x67] = 0x08; /* Fast IR Config */
pci_conf[0x6b] = 0x01; /* Fast IR I/O Base */





Re: [PATCH 02/27] util: Add cpuinfo-i386.c

2023-05-21 Thread Richard Henderson

On 5/21/23 04:28, Philippe Mathieu-Daudé wrote:

On 20/5/23 18:26, Richard Henderson wrote:

Add cpuinfo.h for i386 and x86_64, and the initialization
for that in util/.  Populate that with a slightly altered
copy of the tcg host probing code.  Other uses of cpuid.h
will be adjusted one patch at a time.

Reviewed-by: Juan Quintela 
Signed-off-by: Richard Henderson 
---
  host/include/i386/host/cpuinfo.h   | 38 
  host/include/x86_64/host/cpuinfo.h |  1 +
  util/cpuinfo-i386.c    | 97 ++
  util/meson.build   |  4 ++
  4 files changed, 140 insertions(+)
  create mode 100644 host/include/i386/host/cpuinfo.h
  create mode 100644 host/include/x86_64/host/cpuinfo.h
  create mode 100644 util/cpuinfo-i386.c


Missing F: entry in MAINTAINERS file. We probably need new sections.


What would you put there?


r~



Re: [PATCH 17/27] target/s390x: Use cpu_{ld,st}*_mmu in do_csst

2023-05-21 Thread Richard Henderson

On 5/21/23 04:21, Philippe Mathieu-Daudé wrote:

Hi Richard,

On 20/5/23 18:26, Richard Henderson wrote:

Use cpu_ld16_mmu and cpu_st16_mmu to eliminate the special case,
and change all of the *_data_ra functions to match.

Signed-off-by: Richard Henderson 
---
Cc: qemu-s3...@nongnu.org
Cc: David Hildenbrand 
Cc: Ilya Leoshkevich 
---
  target/s390x/tcg/mem_helper.c | 65 ++-
  1 file changed, 26 insertions(+), 39 deletions(-)

diff --git a/target/s390x/tcg/mem_helper.c b/target/s390x/tcg/mem_helper.c
index 0e0d66b3b6..b6cf24403c 100644
--- a/target/s390x/tcg/mem_helper.c
+++ b/target/s390x/tcg/mem_helper.c
@@ -1737,6 +1737,9 @@ static uint32_t do_csst(CPUS390XState *env, uint32_t r3, 
uint64_t a1,
  uint64_t a2, bool parallel)
  {
  uint32_t mem_idx = cpu_mmu_index(env, false);
+    MemOpIdx oi16 = make_memop_idx(MO_TE | MO_128, mem_idx);
+    MemOpIdx oi8 = make_memop_idx(MO_TE | MO_64, mem_idx);




  if (parallel) {
  #ifdef CONFIG_ATOMIC64
-    MemOpIdx oi = make_memop_idx(MO_TEUQ | MO_ALIGN, mem_idx);
-    ov = cpu_atomic_cmpxchgq_be_mmu(env, a1, cv, nv, oi, ra);
+    ov = cpu_atomic_cmpxchgq_be_mmu(env, a1, cv, nv, oi8, ra);


Why is it safe to remove MO_ALIGN here?


Alignment check already done at the start of the function:

/* Sanity check the alignments.  */
if (extract32(a1, 0, fc + 2) || extract32(a2, 0, sc)) {
goto spec_exception;
}


r~



Re: [PATCH 16/27] accel/tcg: Unify cpu_{ld,st}*_{be,le}_mmu

2023-05-21 Thread Richard Henderson

On 5/21/23 04:15, Philippe Mathieu-Daudé wrote:

Hi Richard,

On 20/5/23 18:26, Richard Henderson wrote:

With the current structure of cputlb.c, there is no difference
between the little-endian and big-endian entry points, aside
from the assert.  Unify the pairs of functions.

The only use of the functions with explicit endianness was in
target/sparc64, and that was only to satisfy the assert.


I'm having hard time to follow all the handling of the various
ASI definitions from target/sparc/asi.h. ...


Signed-off-by: Richard Henderson 
---
  include/exec/cpu_ldst.h |  58 ++-
  accel/tcg/cputlb.c  | 122 +++---
  accel/tcg/user-exec.c   | 322 ++--
  target/arm/tcg/m_helper.c   |   4 +-
  target/sparc/ldst_helper.c  |  18 +-
  accel/tcg/ldst_common.c.inc |  24 +--
  6 files changed, 137 insertions(+), 411 deletions(-)




diff --git a/target/sparc/ldst_helper.c b/target/sparc/ldst_helper.c
index 7972d56a72..981a47d8bb 100644
--- a/target/sparc/ldst_helper.c
+++ b/target/sparc/ldst_helper.c
@@ -1334,25 +1334,13 @@ uint64_t helper_ld_asi(CPUSPARCState *env, target_ulong 
addr,



Shouldn't we propagate the ASI endianness?


Already done in translate, get_asi():

/* The little-endian asis all have bit 3 set.  */
if (asi & 8) {
memop ^= MO_BSWAP;
}


r~



Re: [PATCH] acpi/tests/bios-tables-test: add an environment variable for iasl location

2023-05-21 Thread Ani Sinha



> On 21-May-2023, at 2:24 PM, Michael S. Tsirkin  wrote:
> 
> On Wed, May 17, 2023 at 05:37:51PM +0530, Ani Sinha wrote:
>> Currently the meson based QEMU build process locates the iasl binary from the
>> current PATH and other locations [1] and uses that to set CONFIG_IASL which 
>> is
>> then used by the test.
>> 
>> This has two disadvantages:
>> - If iasl was not previously installed in the PATH, one has to install iasl
>>   and rebuild QEMU in order to pick up the iasl location. One cannot simply
>>   use the existing bios-tables-test binary because CONFIG_IASL is only set
>>   during the QEMU build time by meson and then bios-tables-test has to be
>>   rebuilt with CONFIG_IASL set in order to use iasl.
>> - Sometimes, the stock iasl that comes with distributions is simply not good
>>   enough because it does not support the latest ACPI changes - newly
>>   introduced tables or new table attributes etc. In order to test ACPI code
>>   in QEMU, one has to clone the latest acpica upstream repository and
>>   rebuild iasl in order to get support for it. In those cases, one may want
>>   the test to use the iasl binary from a non-standard location.
>> 
>> In order to overcome the above two disadvantages, we introduce a new
>> environment variable IASL_PATH that can be set by the tester pointing to an
>> possibly non-standard iasl binary location. Bios-tables-test then uses this
>> environment variable to set its iasl location, possibly also overriding the
>> location that was pointed to by CONFIG_IASL that was set by meson. This way
>> developers can not only use this new environment variable to set iasl
>> location to quickly run bios-tables-test but also can point the test to a
>> custom iasl if required.
>> 
>> [1] https://mesonbuild.com/Reference-manual_functions.html#find_program
>> 
>> Signed-off-by: Ani Sinha 
> 
> I don't much like it that the default is now a bit harder
> to run. Case of playing with iasl is really esotetic.
> I propose a simpler idea.
> - add config-iasl.h with only CONFIG_IASL set to path
> - include from bios test
> 
> Now if you change path only bios test is rebuilt.
> 
> Hmm?

We can do this. 

If an environment variable CONFIG_IASL is set or a command line is passed (we 
can do one or the other), use that. Else use a default path /usr/bin/iasl. This 
way we do not even need to rebuild the test if the developer wishes to use 
another iasl binary from a different location. 
I prefer env var slightly because its easier to implement from meson. Test 
specific command lines in meson.build would need more work.

> 
> 
>> ---
>> tests/qtest/bios-tables-test.c | 14 ++
>> 1 file changed, 14 insertions(+)
>> 
>> sample runs:
>> 
>> $ QTEST_QEMU_BINARY=./qemu-system-x86_64 V=2 ./tests/qtest/bios-tables-test
>> ...
>> acpi-test: Warning! APIC binary file mismatch. Actual [aml:/tmp/aml-DLHA51], 
>> Expected [aml:tests/data/acpi/pc/APIC].
>> See source file tests/qtest/bios-tables-test.c for instructions on how to 
>> update expected files.
>> Using iasl: /usr/bin/iasl
>> acpi-test: Warning! APIC mismatch. Actual [asl:/tmp/asl-L9GA51.dsl, 
>> aml:/tmp/aml-DLHA51], Expected [asl:/tmp/asl-10EA51.dsl, 
>> aml:tests/data/acpi/pc/APIC].
>> 
>> $ QTEST_QEMU_BINARY=./qemu-system-x86_64 V=2 
>> IASL_PATH=/home/anisinha/workspace/acpica/generate/unix/bin/iasl 
>> ./tests/qtest/bios-tables-test
>> ...
>> acpi-test: Warning! APIC binary file mismatch. Actual [aml:/tmp/aml-5CQ341], 
>> Expected [aml:tests/data/acpi/pc/APIC].
>> See source file tests/qtest/bios-tables-test.c for instructions on how to 
>> update expected files.
>> User has provided an iasl path, using that: 
>> /home/anisinha/workspace/acpica/generate/unix/bin/iasl
>> acpi-test: Warning! APIC mismatch. Actual [asl:/tmp/asl-2GQ341.dsl, 
>> aml:/tmp/aml-5CQ341], Expected [asl:/tmp/asl-IBR341.dsl, 
>> aml:tests/data/acpi/pc/APIC].
>> 
>> diff --git a/tests/qtest/bios-tables-test.c b/tests/qtest/bios-tables-test.c
>> index 7fd88b0e9c..37e8e484cb 100644
>> --- a/tests/qtest/bios-tables-test.c
>> +++ b/tests/qtest/bios-tables-test.c
>> @@ -440,7 +440,12 @@ static void test_acpi_asl(test_data *data)
>> AcpiSdtTable *sdt, *exp_sdt;
>> test_data exp_data = {};
>> gboolean exp_err, err, all_tables_match = true;
>> +const char *user_iasl_path = getenv("IASL_PATH");
>> 
>> +/* if user has provided a path to iasl, use that */
>> +if (user_iasl_path) {
>> +iasl = user_iasl_path;
>> +}
>> exp_data.tables = load_expected_aml(data);
>> dump_aml_files(data, false);
>> for (i = 0; i < data->tables->len; ++i) {
>> @@ -473,6 +478,15 @@ static void test_acpi_asl(test_data *data)
>> continue;
>> }
>> 
>> +if (verbosity_level >= 2) {
>> +if (user_iasl_path) {
>> +fprintf(stderr, "User has provided an iasl path," \
>> +"using that: %s\n", user_iasl_path);
>> +} else {
>> +fprintf(stderr, 

Re: [PATCH v2 4/6] hw/char/parallel: Export ParallelState

2023-05-21 Thread BALATON Zoltan

On Sun, 21 May 2023, Bernhard Beschow wrote:

Exporting ParallelState is a precondition for exporing TYPE_ISA_PARALLEL.


This may need a better commit message. It's not a precondition per coding 
standards I think just a preference for allowing embedding the device in 
other devices but otherwise unnecessary. Or at least fix the typo 
"exporing" -> exporting.


Regards,
BALATON Zoltan


Suggested-by: Mark Cave-Ayland 
---
include/hw/char/parallel.h | 44 ++
hw/char/parallel.c | 42 
2 files changed, 44 insertions(+), 42 deletions(-)

diff --git a/include/hw/char/parallel.h b/include/hw/char/parallel.h
index 0a23c0f57e..2d4907c1fe 100644
--- a/include/hw/char/parallel.h
+++ b/include/hw/char/parallel.h
@@ -1,9 +1,53 @@
#ifndef HW_PARALLEL_H
#define HW_PARALLEL_H

+#include "exec/ioport.h"
+#include "exec/memory.h"
#include "hw/isa/isa.h"
+#include "hw/irq.h"
+#include "chardev/char-fe.h"
#include "chardev/char.h"

+/*
+ * These are the definitions for the Printer Status Register
+ */
+#define PARA_STS_BUSY   0x80/* Busy complement */
+#define PARA_STS_ACK0x40/* Acknowledge */
+#define PARA_STS_PAPER  0x20/* Out of paper */
+#define PARA_STS_ONLINE 0x10/* Online */
+#define PARA_STS_ERROR  0x08/* Error complement */
+#define PARA_STS_TMOUT  0x01/* EPP timeout */
+
+/*
+ * These are the definitions for the Printer Control Register
+ */
+#define PARA_CTR_DIR0x20/* Direction (1=read, 0=write) */
+#define PARA_CTR_INTEN  0x10/* IRQ Enable */
+#define PARA_CTR_SELECT 0x08/* Select In complement */
+#define PARA_CTR_INIT   0x04/* Initialize Printer complement */
+#define PARA_CTR_AUTOLF 0x02/* Auto linefeed complement */
+#define PARA_CTR_STROBE 0x01/* Strobe complement */
+
+#define PARA_CTR_SIGNAL (PARA_CTR_SELECT | PARA_CTR_INIT | PARA_CTR_AUTOLF \
+ | PARA_CTR_STROBE)
+
+typedef struct ParallelState {
+MemoryRegion iomem;
+uint8_t dataw;
+uint8_t datar;
+uint8_t status;
+uint8_t control;
+qemu_irq irq;
+int irq_pending;
+CharBackend chr;
+int hw_driver;
+int epp_timeout;
+uint32_t last_read_offset; /* For debugging */
+/* Memory-mapped interface */
+int it_shift;
+PortioList portio_list;
+} ParallelState;
+
void parallel_hds_isa_init(ISABus *bus, int n);

bool parallel_mm_init(MemoryRegion *address_space,
diff --git a/hw/char/parallel.c b/hw/char/parallel.c
index af551e7864..522301f43a 100644
--- a/hw/char/parallel.c
+++ b/hw/char/parallel.c
@@ -27,10 +27,7 @@
#include "qapi/error.h"
#include "qemu/module.h"
#include "chardev/char-parallel.h"
-#include "chardev/char-fe.h"
#include "hw/acpi/acpi_aml_interface.h"
-#include "hw/irq.h"
-#include "hw/isa/isa.h"
#include "hw/qdev-properties.h"
#include "hw/qdev-properties-system.h"
#include "migration/vmstate.h"
@@ -54,45 +51,6 @@
#define PARA_REG_EPP_ADDR 3
#define PARA_REG_EPP_DATA 4

-/*
- * These are the definitions for the Printer Status Register
- */
-#define PARA_STS_BUSY   0x80/* Busy complement */
-#define PARA_STS_ACK0x40/* Acknowledge */
-#define PARA_STS_PAPER  0x20/* Out of paper */
-#define PARA_STS_ONLINE 0x10/* Online */
-#define PARA_STS_ERROR  0x08/* Error complement */
-#define PARA_STS_TMOUT  0x01/* EPP timeout */
-
-/*
- * These are the definitions for the Printer Control Register
- */
-#define PARA_CTR_DIR0x20/* Direction (1=read, 0=write) */
-#define PARA_CTR_INTEN  0x10/* IRQ Enable */
-#define PARA_CTR_SELECT 0x08/* Select In complement */
-#define PARA_CTR_INIT   0x04/* Initialize Printer complement */
-#define PARA_CTR_AUTOLF 0x02/* Auto linefeed complement */
-#define PARA_CTR_STROBE 0x01/* Strobe complement */
-
-#define PARA_CTR_SIGNAL 
(PARA_CTR_SELECT|PARA_CTR_INIT|PARA_CTR_AUTOLF|PARA_CTR_STROBE)
-
-typedef struct ParallelState {
-MemoryRegion iomem;
-uint8_t dataw;
-uint8_t datar;
-uint8_t status;
-uint8_t control;
-qemu_irq irq;
-int irq_pending;
-CharBackend chr;
-int hw_driver;
-int epp_timeout;
-uint32_t last_read_offset; /* For debugging */
-/* Memory-mapped interface */
-int it_shift;
-PortioList portio_list;
-} ParallelState;
-
#define TYPE_ISA_PARALLEL "isa-parallel"
OBJECT_DECLARE_SIMPLE_TYPE(ISAParallelState, ISA_PARALLEL)






[PATCH v2 3/6] hw/isa/i82378: Remove unused "io" attribute

2023-05-21 Thread Bernhard Beschow
The attribute isn't used since commit 5c9736789b79ea49cd236ac326f0a414f63b1015
"i82378: Cleanup implementation".

Signed-off-by: Bernhard Beschow 
Acked-by: Michael S. Tsirkin 
Reviewed-by: Mark Cave-Ayland 
---
 hw/isa/i82378.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/hw/isa/i82378.c b/hw/isa/i82378.c
index 5432ab5065..63e0857208 100644
--- a/hw/isa/i82378.c
+++ b/hw/isa/i82378.c
@@ -34,7 +34,6 @@ struct I82378State {
 
 qemu_irq cpu_intr;
 qemu_irq *isa_irqs_in;
-MemoryRegion io;
 };
 
 static const VMStateDescription vmstate_i82378 = {
-- 
2.40.1




[PATCH v2 5/6] hw/char/parallel-isa: Export ISAParallelState

2023-05-21 Thread Bernhard Beschow
In order to replace string literals with the TYPE_ISA_PARALLEL macro we need to
export the whole structure as well.

Suggested-by: Mark Cave-Ayland 
---
 include/hw/char/parallel-isa.h | 46 ++
 hw/char/parallel.c | 13 +-
 2 files changed, 47 insertions(+), 12 deletions(-)
 create mode 100644 include/hw/char/parallel-isa.h

diff --git a/include/hw/char/parallel-isa.h b/include/hw/char/parallel-isa.h
new file mode 100644
index 00..27bdacf1a3
--- /dev/null
+++ b/include/hw/char/parallel-isa.h
@@ -0,0 +1,46 @@
+/*
+ * QEMU ISA Parallel PORT emulation
+ *
+ * Copyright (c) 2003-2005 Fabrice Bellard
+ * Copyright (c) 2007 Marko Kohtala
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to 
deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 
FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#ifndef HW_PARALLEL_ISA_H
+#define HW_PARALLEL_ISA_H
+
+#include "parallel.h"
+
+#include "hw/isa/isa.h"
+#include "qom/object.h"
+
+#define TYPE_ISA_PARALLEL "isa-parallel"
+OBJECT_DECLARE_SIMPLE_TYPE(ISAParallelState, ISA_PARALLEL)
+
+struct ISAParallelState {
+ISADevice parent_obj;
+
+uint32_t index;
+uint32_t iobase;
+uint32_t isairq;
+ParallelState state;
+};
+
+#endif /* HW_PARALLEL_ISA_H */
diff --git a/hw/char/parallel.c b/hw/char/parallel.c
index 522301f43a..d89f750cc1 100644
--- a/hw/char/parallel.c
+++ b/hw/char/parallel.c
@@ -31,6 +31,7 @@
 #include "hw/qdev-properties.h"
 #include "hw/qdev-properties-system.h"
 #include "migration/vmstate.h"
+#include "hw/char/parallel-isa.h"
 #include "hw/char/parallel.h"
 #include "sysemu/reset.h"
 #include "sysemu/sysemu.h"
@@ -51,18 +52,6 @@
 #define PARA_REG_EPP_ADDR 3
 #define PARA_REG_EPP_DATA 4
 
-#define TYPE_ISA_PARALLEL "isa-parallel"
-OBJECT_DECLARE_SIMPLE_TYPE(ISAParallelState, ISA_PARALLEL)
-
-struct ISAParallelState {
-ISADevice parent_obj;
-
-uint32_t index;
-uint32_t iobase;
-uint32_t isairq;
-ParallelState state;
-};
-
 static void parallel_update_irq(ParallelState *s)
 {
 if (s->irq_pending)
-- 
2.40.1




[PATCH v2 4/6] hw/char/parallel: Export ParallelState

2023-05-21 Thread Bernhard Beschow
Exporting ParallelState is a precondition for exporing TYPE_ISA_PARALLEL.

Suggested-by: Mark Cave-Ayland 
---
 include/hw/char/parallel.h | 44 ++
 hw/char/parallel.c | 42 
 2 files changed, 44 insertions(+), 42 deletions(-)

diff --git a/include/hw/char/parallel.h b/include/hw/char/parallel.h
index 0a23c0f57e..2d4907c1fe 100644
--- a/include/hw/char/parallel.h
+++ b/include/hw/char/parallel.h
@@ -1,9 +1,53 @@
 #ifndef HW_PARALLEL_H
 #define HW_PARALLEL_H
 
+#include "exec/ioport.h"
+#include "exec/memory.h"
 #include "hw/isa/isa.h"
+#include "hw/irq.h"
+#include "chardev/char-fe.h"
 #include "chardev/char.h"
 
+/*
+ * These are the definitions for the Printer Status Register
+ */
+#define PARA_STS_BUSY   0x80/* Busy complement */
+#define PARA_STS_ACK0x40/* Acknowledge */
+#define PARA_STS_PAPER  0x20/* Out of paper */
+#define PARA_STS_ONLINE 0x10/* Online */
+#define PARA_STS_ERROR  0x08/* Error complement */
+#define PARA_STS_TMOUT  0x01/* EPP timeout */
+
+/*
+ * These are the definitions for the Printer Control Register
+ */
+#define PARA_CTR_DIR0x20/* Direction (1=read, 0=write) */
+#define PARA_CTR_INTEN  0x10/* IRQ Enable */
+#define PARA_CTR_SELECT 0x08/* Select In complement */
+#define PARA_CTR_INIT   0x04/* Initialize Printer complement */
+#define PARA_CTR_AUTOLF 0x02/* Auto linefeed complement */
+#define PARA_CTR_STROBE 0x01/* Strobe complement */
+
+#define PARA_CTR_SIGNAL (PARA_CTR_SELECT | PARA_CTR_INIT | PARA_CTR_AUTOLF \
+ | PARA_CTR_STROBE)
+
+typedef struct ParallelState {
+MemoryRegion iomem;
+uint8_t dataw;
+uint8_t datar;
+uint8_t status;
+uint8_t control;
+qemu_irq irq;
+int irq_pending;
+CharBackend chr;
+int hw_driver;
+int epp_timeout;
+uint32_t last_read_offset; /* For debugging */
+/* Memory-mapped interface */
+int it_shift;
+PortioList portio_list;
+} ParallelState;
+
 void parallel_hds_isa_init(ISABus *bus, int n);
 
 bool parallel_mm_init(MemoryRegion *address_space,
diff --git a/hw/char/parallel.c b/hw/char/parallel.c
index af551e7864..522301f43a 100644
--- a/hw/char/parallel.c
+++ b/hw/char/parallel.c
@@ -27,10 +27,7 @@
 #include "qapi/error.h"
 #include "qemu/module.h"
 #include "chardev/char-parallel.h"
-#include "chardev/char-fe.h"
 #include "hw/acpi/acpi_aml_interface.h"
-#include "hw/irq.h"
-#include "hw/isa/isa.h"
 #include "hw/qdev-properties.h"
 #include "hw/qdev-properties-system.h"
 #include "migration/vmstate.h"
@@ -54,45 +51,6 @@
 #define PARA_REG_EPP_ADDR 3
 #define PARA_REG_EPP_DATA 4
 
-/*
- * These are the definitions for the Printer Status Register
- */
-#define PARA_STS_BUSY   0x80/* Busy complement */
-#define PARA_STS_ACK0x40/* Acknowledge */
-#define PARA_STS_PAPER  0x20/* Out of paper */
-#define PARA_STS_ONLINE 0x10/* Online */
-#define PARA_STS_ERROR  0x08/* Error complement */
-#define PARA_STS_TMOUT  0x01/* EPP timeout */
-
-/*
- * These are the definitions for the Printer Control Register
- */
-#define PARA_CTR_DIR0x20/* Direction (1=read, 0=write) */
-#define PARA_CTR_INTEN  0x10/* IRQ Enable */
-#define PARA_CTR_SELECT 0x08/* Select In complement */
-#define PARA_CTR_INIT   0x04/* Initialize Printer complement */
-#define PARA_CTR_AUTOLF 0x02/* Auto linefeed complement */
-#define PARA_CTR_STROBE 0x01/* Strobe complement */
-
-#define PARA_CTR_SIGNAL 
(PARA_CTR_SELECT|PARA_CTR_INIT|PARA_CTR_AUTOLF|PARA_CTR_STROBE)
-
-typedef struct ParallelState {
-MemoryRegion iomem;
-uint8_t dataw;
-uint8_t datar;
-uint8_t status;
-uint8_t control;
-qemu_irq irq;
-int irq_pending;
-CharBackend chr;
-int hw_driver;
-int epp_timeout;
-uint32_t last_read_offset; /* For debugging */
-/* Memory-mapped interface */
-int it_shift;
-PortioList portio_list;
-} ParallelState;
-
 #define TYPE_ISA_PARALLEL "isa-parallel"
 OBJECT_DECLARE_SIMPLE_TYPE(ISAParallelState, ISA_PARALLEL)
 
-- 
2.40.1




[PATCH v2 1/6] hw/timer/i8254_common: Share "iobase" property via base class

2023-05-21 Thread Bernhard Beschow
Both TYPE_KVM_I8254 and TYPE_I8254 have their own but same implementation of
the "iobase" property. The storage for the property already resides in
PITCommonState, so also move the property definition there.

Signed-off-by: Bernhard Beschow 
Acked-by: Michael S. Tsirkin 
Reviewed-by: Mark Cave-Ayland 
Reviewed-by: Philippe Mathieu-Daudé 
---
 hw/i386/kvm/i8254.c | 1 -
 hw/timer/i8254.c| 6 --
 hw/timer/i8254_common.c | 6 ++
 3 files changed, 6 insertions(+), 7 deletions(-)

diff --git a/hw/i386/kvm/i8254.c b/hw/i386/kvm/i8254.c
index 191a26fa57..6a7383d877 100644
--- a/hw/i386/kvm/i8254.c
+++ b/hw/i386/kvm/i8254.c
@@ -301,7 +301,6 @@ static void kvm_pit_realizefn(DeviceState *dev, Error 
**errp)
 }
 
 static Property kvm_pit_properties[] = {
-DEFINE_PROP_UINT32("iobase", PITCommonState, iobase,  -1),
 DEFINE_PROP_LOSTTICKPOLICY("lost_tick_policy", KVMPITState,
lost_tick_policy, LOST_TICK_POLICY_DELAY),
 DEFINE_PROP_END_OF_LIST(),
diff --git a/hw/timer/i8254.c b/hw/timer/i8254.c
index c8388ea432..c235496fc9 100644
--- a/hw/timer/i8254.c
+++ b/hw/timer/i8254.c
@@ -350,11 +350,6 @@ static void pit_realizefn(DeviceState *dev, Error **errp)
 pc->parent_realize(dev, errp);
 }
 
-static Property pit_properties[] = {
-DEFINE_PROP_UINT32("iobase", PITCommonState, iobase,  -1),
-DEFINE_PROP_END_OF_LIST(),
-};
-
 static void pit_class_initfn(ObjectClass *klass, void *data)
 {
 PITClass *pc = PIT_CLASS(klass);
@@ -366,7 +361,6 @@ static void pit_class_initfn(ObjectClass *klass, void *data)
 k->get_channel_info = pit_get_channel_info_common;
 k->post_load = pit_post_load;
 dc->reset = pit_reset;
-device_class_set_props(dc, pit_properties);
 }
 
 static const TypeInfo pit_info = {
diff --git a/hw/timer/i8254_common.c b/hw/timer/i8254_common.c
index 050875b497..e4093e2904 100644
--- a/hw/timer/i8254_common.c
+++ b/hw/timer/i8254_common.c
@@ -240,6 +240,11 @@ static const VMStateDescription vmstate_pit_common = {
 }
 };
 
+static Property pit_common_properties[] = {
+DEFINE_PROP_UINT32("iobase", PITCommonState, iobase,  -1),
+DEFINE_PROP_END_OF_LIST(),
+};
+
 static void pit_common_class_init(ObjectClass *klass, void *data)
 {
 DeviceClass *dc = DEVICE_CLASS(klass);
@@ -252,6 +257,7 @@ static void pit_common_class_init(ObjectClass *klass, void 
*data)
  * done by board code.
  */
 dc->user_creatable = false;
+device_class_set_props(dc, pit_common_properties);
 }
 
 static const TypeInfo pit_common_type = {
-- 
2.40.1




[PATCH v2 0/6] Trivial cleanups

2023-05-21 Thread Bernhard Beschow
This series:
* Removes dead code from omap_uart and i82378
* Resolves redundant code in the i8254 timer devices
* Exports ParallelState and ISAParallelState in order to replac string literals
  by TYPE_ISA_PARALLEL macro usage

v2:
* Export ParallelState and ISAParallelState (Mark)

Testing done:
* `make check`

Bernhard Beschow (6):
  hw/timer/i8254_common: Share "iobase" property via base class
  hw/arm/omap: Remove unused omap_uart_attach()
  hw/isa/i82378: Remove unused "io" attribute
  hw/char/parallel: Export ParallelState
  hw/char/parallel-isa: Export ISAParallelState
  hw/char/parallel: Replace string literals by TYPE_ISA_PARALLEL macro

 include/hw/arm/omap.h  |  1 -
 include/hw/char/parallel-isa.h | 46 
 include/hw/char/parallel.h | 44 +++
 hw/char/omap_uart.c|  9 --
 hw/char/parallel-isa.c |  3 +-
 hw/char/parallel.c | 55 +-
 hw/i386/kvm/i8254.c|  1 -
 hw/isa/i82378.c|  1 -
 hw/isa/isa-superio.c   |  3 +-
 hw/timer/i8254.c   |  6 
 hw/timer/i8254_common.c|  6 
 11 files changed, 101 insertions(+), 74 deletions(-)
 create mode 100644 include/hw/char/parallel-isa.h

-- 
2.40.1




[PATCH v2 6/6] hw/char/parallel: Replace string literals by TYPE_ISA_PARALLEL macro

2023-05-21 Thread Bernhard Beschow
Rather than using a string literal which is prone to typos let's use a macro
instead which is caught by the compiler if mistyped.

Signed-off-by: Bernhard Beschow 
Acked-by: Michael S. Tsirkin 
---
 hw/char/parallel-isa.c | 3 ++-
 hw/isa/isa-superio.c   | 3 ++-
 2 files changed, 4 insertions(+), 2 deletions(-)

diff --git a/hw/char/parallel-isa.c b/hw/char/parallel-isa.c
index 1ccbb96e70..ab0f879998 100644
--- a/hw/char/parallel-isa.c
+++ b/hw/char/parallel-isa.c
@@ -13,6 +13,7 @@
 #include "sysemu/sysemu.h"
 #include "hw/isa/isa.h"
 #include "hw/qdev-properties.h"
+#include "hw/char/parallel-isa.h"
 #include "hw/char/parallel.h"
 #include "qapi/error.h"
 
@@ -21,7 +22,7 @@ static void parallel_init(ISABus *bus, int index, Chardev 
*chr)
 DeviceState *dev;
 ISADevice *isadev;
 
-isadev = isa_new("isa-parallel");
+isadev = isa_new(TYPE_ISA_PARALLEL);
 dev = DEVICE(isadev);
 qdev_prop_set_uint32(dev, "index", index);
 qdev_prop_set_chr(dev, "chardev", chr);
diff --git a/hw/isa/isa-superio.c b/hw/isa/isa-superio.c
index c81bfe58ef..3baa9777be 100644
--- a/hw/isa/isa-superio.c
+++ b/hw/isa/isa-superio.c
@@ -20,6 +20,7 @@
 #include "hw/isa/superio.h"
 #include "hw/qdev-properties.h"
 #include "hw/input/i8042.h"
+#include "hw/char/parallel-isa.h"
 #include "hw/char/serial.h"
 #include "trace.h"
 
@@ -51,7 +52,7 @@ static void isa_superio_realize(DeviceState *dev, Error 
**errp)
 } else {
 name = g_strdup_printf("parallel%d", i);
 }
-isa = isa_new("isa-parallel");
+isa = isa_new(TYPE_ISA_PARALLEL);
 d = DEVICE(isa);
 qdev_prop_set_uint32(d, "index", i);
 if (k->parallel.get_iobase) {
-- 
2.40.1




[PATCH v2 2/6] hw/arm/omap: Remove unused omap_uart_attach()

2023-05-21 Thread Bernhard Beschow
The function is unused since commit
bdad3654d3c55f478e538037d9eccd204e5fc8ee ('hw/arm/nseries: Remove
invalid/unnecessary n8x0_uart_setup()').

Signed-off-by: Bernhard Beschow 
Acked-by: Michael S. Tsirkin 
Reviewed-by: Mark Cave-Ayland 
Reviewed-by: Philippe Mathieu-Daudé 
---
 include/hw/arm/omap.h | 1 -
 hw/char/omap_uart.c   | 9 -
 2 files changed, 10 deletions(-)

diff --git a/include/hw/arm/omap.h b/include/hw/arm/omap.h
index c275d9b681..067e9419f7 100644
--- a/include/hw/arm/omap.h
+++ b/include/hw/arm/omap.h
@@ -724,7 +724,6 @@ struct omap_uart_s *omap2_uart_init(MemoryRegion *sysmem,
 qemu_irq txdma, qemu_irq rxdma,
 const char *label, Chardev *chr);
 void omap_uart_reset(struct omap_uart_s *s);
-void omap_uart_attach(struct omap_uart_s *s, Chardev *chr);
 
 struct omap_mpuio_s;
 qemu_irq *omap_mpuio_in_get(struct omap_mpuio_s *s);
diff --git a/hw/char/omap_uart.c b/hw/char/omap_uart.c
index 1c890b9201..6848bddb4e 100644
--- a/hw/char/omap_uart.c
+++ b/hw/char/omap_uart.c
@@ -175,12 +175,3 @@ struct omap_uart_s *omap2_uart_init(MemoryRegion *sysmem,
 
 return s;
 }
-
-void omap_uart_attach(struct omap_uart_s *s, Chardev *chr)
-{
-/* TODO: Should reuse or destroy current s->serial */
-s->serial = serial_mm_init(get_system_memory(), s->base, 2, s->irq,
-   omap_clk_getrate(s->fclk) / 16,
-   chr ?: qemu_chr_new("null", "null", NULL),
-   DEVICE_NATIVE_ENDIAN);
-}
-- 
2.40.1




Re: [PATCH] target/mips: Rework cp0_timer with clock API

2023-05-21 Thread Philippe Mathieu-Daudé

On 21/5/23 13:00, Jiaxun Yang wrote:

Previous implementation of MIPS cp0_timer computes a
cp0_count_ns based on input clock. However rounding
error of cp0_count_ns can affect precision of cp0_timer.

Using clock API and a divider for cp0_timer, so we can
use clock_ns_to_ticks/clock_ns_to_ticks to avoid rounding
issue.

Also workaround the situation that in such handler flow:

count = read_c0_count()
write_c0_compare(count)

If timer had not progressed when compare was written, the
interrupt would trigger again.

Signed-off-by: Jiaxun Yang 
---
This seems fixed MTTCG booting issue on malta 5kEc with SMP.
I'm going to do more test and see if we can enable MTTCG for
mips64el.
---
  target/mips/cpu.c  |  8 +---
  target/mips/cpu.h  |  3 ++-
  target/mips/sysemu/cp0_timer.c | 35 ++
  3 files changed, 26 insertions(+), 20 deletions(-)


Nice!

Reviewed-by: Philippe Mathieu-Daudé 




Re: [PATCH 02/27] util: Add cpuinfo-i386.c

2023-05-21 Thread Philippe Mathieu-Daudé

On 20/5/23 18:26, Richard Henderson wrote:

Add cpuinfo.h for i386 and x86_64, and the initialization
for that in util/.  Populate that with a slightly altered
copy of the tcg host probing code.  Other uses of cpuid.h
will be adjusted one patch at a time.

Reviewed-by: Juan Quintela 
Signed-off-by: Richard Henderson 
---
  host/include/i386/host/cpuinfo.h   | 38 
  host/include/x86_64/host/cpuinfo.h |  1 +
  util/cpuinfo-i386.c| 97 ++
  util/meson.build   |  4 ++
  4 files changed, 140 insertions(+)
  create mode 100644 host/include/i386/host/cpuinfo.h
  create mode 100644 host/include/x86_64/host/cpuinfo.h
  create mode 100644 util/cpuinfo-i386.c


Missing F: entry in MAINTAINERS file. We probably need new sections.



Re: [PATCH 24/27] tcg: Split out tcg/debug-assert.h

2023-05-21 Thread Philippe Mathieu-Daudé

On 20/5/23 18:26, Richard Henderson wrote:

Signed-off-by: Richard Henderson 
---
  include/tcg/debug-assert.h | 17 +
  include/tcg/tcg.h  |  9 +
  2 files changed, 18 insertions(+), 8 deletions(-)
  create mode 100644 include/tcg/debug-assert.h


While here:

--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -156,6 +156,7 @@ F: include/exec/target_long.h
 F: include/exec/helper*.h
 F: include/sysemu/cpus.h
 F: include/sysemu/tcg.h
+F: include/tcg/
 F: include/hw/core/tcg-cpu-ops.h

Reviewed-by: Philippe Mathieu-Daudé 




Re: [PATCH 17/27] target/s390x: Use cpu_{ld,st}*_mmu in do_csst

2023-05-21 Thread Philippe Mathieu-Daudé

Hi Richard,

On 20/5/23 18:26, Richard Henderson wrote:

Use cpu_ld16_mmu and cpu_st16_mmu to eliminate the special case,
and change all of the *_data_ra functions to match.

Signed-off-by: Richard Henderson 
---
Cc: qemu-s3...@nongnu.org
Cc: David Hildenbrand 
Cc: Ilya Leoshkevich 
---
  target/s390x/tcg/mem_helper.c | 65 ++-
  1 file changed, 26 insertions(+), 39 deletions(-)

diff --git a/target/s390x/tcg/mem_helper.c b/target/s390x/tcg/mem_helper.c
index 0e0d66b3b6..b6cf24403c 100644
--- a/target/s390x/tcg/mem_helper.c
+++ b/target/s390x/tcg/mem_helper.c
@@ -1737,6 +1737,9 @@ static uint32_t do_csst(CPUS390XState *env, uint32_t r3, 
uint64_t a1,
  uint64_t a2, bool parallel)
  {
  uint32_t mem_idx = cpu_mmu_index(env, false);
+MemOpIdx oi16 = make_memop_idx(MO_TE | MO_128, mem_idx);
+MemOpIdx oi8 = make_memop_idx(MO_TE | MO_64, mem_idx);




  if (parallel) {
  #ifdef CONFIG_ATOMIC64
-MemOpIdx oi = make_memop_idx(MO_TEUQ | MO_ALIGN, mem_idx);
-ov = cpu_atomic_cmpxchgq_be_mmu(env, a1, cv, nv, oi, ra);
+ov = cpu_atomic_cmpxchgq_be_mmu(env, a1, cv, nv, oi8, ra);


Why is it safe to remove MO_ALIGN here?


  #else
  /* Note that we asserted !parallel above.  */
  g_assert_not_reached();
  #endif





[PATCH 5/6] hw/ide: Extract bmdma_status_writeb()

2023-05-21 Thread Bernhard Beschow
Every TYPE_PCI_IDE device performs the same not-so-trivial bit manipulation by
copy'n'paste code. Extract this into bmdma_status_writeb(), mirroring
bmdma_cmd_writeb().

Signed-off-by: Bernhard Beschow 
---
 include/hw/ide/pci.h | 1 +
 hw/ide/cmd646.c  | 2 +-
 hw/ide/pci.c | 5 +
 hw/ide/piix.c| 2 +-
 hw/ide/sii3112.c | 6 ++
 hw/ide/via.c | 2 +-
 6 files changed, 11 insertions(+), 7 deletions(-)

diff --git a/include/hw/ide/pci.h b/include/hw/ide/pci.h
index 74c127e32f..1ff469de87 100644
--- a/include/hw/ide/pci.h
+++ b/include/hw/ide/pci.h
@@ -58,6 +58,7 @@ struct PCIIDEState {
 
 void bmdma_init(IDEBus *bus, BMDMAState *bm, PCIIDEState *d);
 void bmdma_cmd_writeb(BMDMAState *bm, uint32_t val);
+void bmdma_status_writeb(BMDMAState *bm, uint32_t val);
 extern MemoryRegionOps bmdma_addr_ioport_ops;
 void pci_ide_create_devs(PCIDevice *dev);
 
diff --git a/hw/ide/cmd646.c b/hw/ide/cmd646.c
index a094a6e12a..cabe9048b1 100644
--- a/hw/ide/cmd646.c
+++ b/hw/ide/cmd646.c
@@ -144,7 +144,7 @@ static void bmdma_write(void *opaque, hwaddr addr,
 cmd646_update_irq(pci_dev);
 break;
 case 2:
-bm->status = (val & 0x60) | (bm->status & 1) | (bm->status & ~val & 
0x06);
+bmdma_status_writeb(bm, val);
 break;
 case 3:
 if (bm == >pci_dev->bmdma[0]) {
diff --git a/hw/ide/pci.c b/hw/ide/pci.c
index 4cf1e9c679..b258fd2f50 100644
--- a/hw/ide/pci.c
+++ b/hw/ide/pci.c
@@ -318,6 +318,11 @@ void bmdma_cmd_writeb(BMDMAState *bm, uint32_t val)
 bm->cmd = val & 0x09;
 }
 
+void bmdma_status_writeb(BMDMAState *bm, uint32_t val)
+{
+bm->status = (val & 0x60) | (bm->status & BM_STATUS_DMAING) | (bm->status 
& ~val & 0x06);
+}
+
 static uint64_t bmdma_addr_read(void *opaque, hwaddr addr,
 unsigned width)
 {
diff --git a/hw/ide/piix.c b/hw/ide/piix.c
index a32f7ccece..47e0b474c3 100644
--- a/hw/ide/piix.c
+++ b/hw/ide/piix.c
@@ -76,7 +76,7 @@ static void bmdma_write(void *opaque, hwaddr addr,
 bmdma_cmd_writeb(bm, val);
 break;
 case 2:
-bm->status = (val & 0x60) | (bm->status & 1) | (bm->status & ~val & 
0x06);
+bmdma_status_writeb(bm, val);
 break;
 }
 }
diff --git a/hw/ide/sii3112.c b/hw/ide/sii3112.c
index 5dd3d03c29..63dc4a0494 100644
--- a/hw/ide/sii3112.c
+++ b/hw/ide/sii3112.c
@@ -149,8 +149,7 @@ static void sii3112_reg_write(void *opaque, hwaddr addr,
 break;
 case 0x02:
 case 0x12:
-d->i.bmdma[0].status = (val & 0x60) | (d->i.bmdma[0].status & 1) |
-   (d->i.bmdma[0].status & ~val & 6);
+bmdma_status_writeb(>i.bmdma[0], val);
 break;
 case 0x04 ... 0x07:
 bmdma_addr_ioport_ops.write(>i.bmdma[0], addr - 4, val, size);
@@ -165,8 +164,7 @@ static void sii3112_reg_write(void *opaque, hwaddr addr,
 break;
 case 0x0a:
 case 0x1a:
-d->i.bmdma[1].status = (val & 0x60) | (d->i.bmdma[1].status & 1) |
-   (d->i.bmdma[1].status & ~val & 6);
+bmdma_status_writeb(>i.bmdma[1], val);
 break;
 case 0x0c ... 0x0f:
 bmdma_addr_ioport_ops.write(>i.bmdma[1], addr - 12, val, size);
diff --git a/hw/ide/via.c b/hw/ide/via.c
index 91253fa4ef..fff23803a6 100644
--- a/hw/ide/via.c
+++ b/hw/ide/via.c
@@ -75,7 +75,7 @@ static void bmdma_write(void *opaque, hwaddr addr,
 bmdma_cmd_writeb(bm, val);
 break;
 case 2:
-bm->status = (val & 0x60) | (bm->status & 1) | (bm->status & ~val & 
0x06);
+bmdma_status_writeb(bm, val);
 break;
 default:;
 }
-- 
2.40.1




[PATCH 4/6] hw/ide: Extract IDEBus assignment into bmdma_init()

2023-05-21 Thread Bernhard Beschow
Every invocation of bmdma_init() is followed by `d->bmdma[i].bus = >bus[i]`.
Resolve this redundancy by extracting it into bmdma_init().

Signed-off-by: Bernhard Beschow 
Reviewed-by: BALATON Zoltan 
Reviewed-by: Philippe Mathieu-Daudé 
Reviewed-by: Mark Cave-Ayland 
---
 hw/ide/cmd646.c  | 1 -
 hw/ide/pci.c | 1 +
 hw/ide/piix.c| 1 -
 hw/ide/sii3112.c | 1 -
 hw/ide/via.c | 1 -
 5 files changed, 1 insertion(+), 4 deletions(-)

diff --git a/hw/ide/cmd646.c b/hw/ide/cmd646.c
index a68357c1c5..a094a6e12a 100644
--- a/hw/ide/cmd646.c
+++ b/hw/ide/cmd646.c
@@ -297,7 +297,6 @@ static void pci_cmd646_ide_realize(PCIDevice *dev, Error 
**errp)
 ide_bus_init_output_irq(>bus[i], qdev_get_gpio_in(ds, i));
 
 bmdma_init(>bus[i], >bmdma[i], d);
-d->bmdma[i].bus = >bus[i];
 ide_bus_register_restart_cb(>bus[i]);
 }
 }
diff --git a/hw/ide/pci.c b/hw/ide/pci.c
index 9a5a7089d4..4cf1e9c679 100644
--- a/hw/ide/pci.c
+++ b/hw/ide/pci.c
@@ -519,6 +519,7 @@ void bmdma_init(IDEBus *bus, BMDMAState *bm, PCIIDEState *d)
 bus->dma = >dma;
 bm->irq = bus->irq;
 bus->irq = qemu_allocate_irq(bmdma_irq, bm, 0);
+bm->bus = bus;
 bm->pci_dev = d;
 }
 
diff --git a/hw/ide/piix.c b/hw/ide/piix.c
index 41d60921e3..a32f7ccece 100644
--- a/hw/ide/piix.c
+++ b/hw/ide/piix.c
@@ -144,7 +144,6 @@ static bool pci_piix_init_bus(PCIIDEState *d, unsigned i, 
Error **errp)
 ide_bus_init_output_irq(>bus[i], isa_get_irq(NULL, 
port_info[i].isairq));
 
 bmdma_init(>bus[i], >bmdma[i], d);
-d->bmdma[i].bus = >bus[i];
 ide_bus_register_restart_cb(>bus[i]);
 
 return true;
diff --git a/hw/ide/sii3112.c b/hw/ide/sii3112.c
index f9becdff8e..5dd3d03c29 100644
--- a/hw/ide/sii3112.c
+++ b/hw/ide/sii3112.c
@@ -287,7 +287,6 @@ static void sii3112_pci_realize(PCIDevice *dev, Error 
**errp)
 ide_bus_init_output_irq(>bus[i], qdev_get_gpio_in(ds, i));
 
 bmdma_init(>bus[i], >bmdma[i], s);
-s->bmdma[i].bus = >bus[i];
 ide_bus_register_restart_cb(>bus[i]);
 }
 }
diff --git a/hw/ide/via.c b/hw/ide/via.c
index 0caae52276..91253fa4ef 100644
--- a/hw/ide/via.c
+++ b/hw/ide/via.c
@@ -196,7 +196,6 @@ static void via_ide_realize(PCIDevice *dev, Error **errp)
 ide_bus_init_output_irq(>bus[i], qdev_get_gpio_in(ds, i));
 
 bmdma_init(>bus[i], >bmdma[i], d);
-d->bmdma[i].bus = >bus[i];
 ide_bus_register_restart_cb(>bus[i]);
 }
 }
-- 
2.40.1




[PATCH 3/6] hw/isa/vt82c686: Remove via_isa_set_irq()

2023-05-21 Thread Bernhard Beschow
Now that via_isa_set_irq() is unused it can be removed.

Signed-off-by: Bernhard Beschow 
Reviewed-by: Mark Cave-Ayland 
---
 include/hw/isa/vt82c686.h | 2 --
 hw/isa/vt82c686.c | 6 --
 2 files changed, 8 deletions(-)

diff --git a/include/hw/isa/vt82c686.h b/include/hw/isa/vt82c686.h
index da1722daf2..b6e95b2851 100644
--- a/include/hw/isa/vt82c686.h
+++ b/include/hw/isa/vt82c686.h
@@ -34,6 +34,4 @@ struct ViaAC97State {
 uint32_t ac97_cmd;
 };
 
-void via_isa_set_irq(PCIDevice *d, int n, int level);
-
 #endif
diff --git a/hw/isa/vt82c686.c b/hw/isa/vt82c686.c
index 8016c71315..57bdfb4e78 100644
--- a/hw/isa/vt82c686.c
+++ b/hw/isa/vt82c686.c
@@ -592,12 +592,6 @@ static const TypeInfo via_isa_info = {
 },
 };
 
-void via_isa_set_irq(PCIDevice *d, int n, int level)
-{
-ViaISAState *s = VIA_ISA(d);
-qemu_set_irq(s->isa_irqs_in[n], level);
-}
-
 static void via_isa_request_i8259_irq(void *opaque, int irq, int level)
 {
 ViaISAState *s = opaque;
-- 
2.40.1




[PATCH 6/6] hw/ide/piix: Move registration of VMStateDescription to DeviceClass

2023-05-21 Thread Bernhard Beschow
The modern, declarative way to set up VM state handling is to assign to
DeviceClass::vmsd attribute.

There shouldn't be any change in behavior since dc->vmsd causes
vmstate_register_with_alias_id() to be called on the instance during
the instance init phase. vmstate_register() was also called during the
instance init phase which forwards to vmstate_register_with_alias_id()
internally. Checking the migration schema before and after this patch confirms:

before:
> qemu-system-x86_64 -S
> qemu > migrate -d exec:cat>before.mig

after:
> qemu-system-x86_64 -S
> qemu > migrate -d exec:cat>after.mig

> analyze-migration.py -d desc -f before.mig > before.json
> analyze-migration.py -d desc -f after.mig > after.json
> diff before.json after.json
-> empty
---
 hw/ide/piix.c | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)

diff --git a/hw/ide/piix.c b/hw/ide/piix.c
index 47e0b474c3..151f206046 100644
--- a/hw/ide/piix.c
+++ b/hw/ide/piix.c
@@ -28,7 +28,6 @@
  */
 
 #include "qemu/osdep.h"
-#include "migration/vmstate.h"
 #include "qapi/error.h"
 #include "hw/pci/pci.h"
 #include "hw/ide/piix.h"
@@ -159,8 +158,6 @@ static void pci_piix_ide_realize(PCIDevice *dev, Error 
**errp)
 bmdma_setup_bar(d);
 pci_register_bar(dev, 4, PCI_BASE_ADDRESS_SPACE_IO, >bmdma_bar);
 
-vmstate_register(VMSTATE_IF(dev), 0, _ide_pci, d);
-
 for (unsigned i = 0; i < 2; i++) {
 if (!pci_piix_init_bus(d, i, errp)) {
 return;
@@ -186,6 +183,7 @@ static void piix3_ide_class_init(ObjectClass *klass, void 
*data)
 PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);
 
 dc->reset = piix_ide_reset;
+dc->vmsd = _ide_pci;
 k->realize = pci_piix_ide_realize;
 k->exit = pci_piix_ide_exitfn;
 k->vendor_id = PCI_VENDOR_ID_INTEL;
@@ -208,6 +206,7 @@ static void piix4_ide_class_init(ObjectClass *klass, void 
*data)
 PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);
 
 dc->reset = piix_ide_reset;
+dc->vmsd = _ide_pci;
 k->realize = pci_piix_ide_realize;
 k->exit = pci_piix_ide_exitfn;
 k->vendor_id = PCI_VENDOR_ID_INTEL;
-- 
2.40.1




[PATCH 0/6] VIA and general PCI IDE cleanup

2023-05-21 Thread Bernhard Beschow
This series is split off from a more general PCI IDE refactoring aiming for a
common implementation of the PCI IDE controller specification for all
TYPE_PCI_IDE models [1].

The first three patches resolve a circular dependency between the VIA IDE
controller and its south bridge. The next two patches resolves redundant code
accross all TYPE_PCI_IDE models. The last patch modernizes VM state setup in
PIIX IDE.

Testing done:
* `make check`
* `make check-avocado`
* `qemu-system-ppc -machine pegasos2 -rtc base=localtime -device \
   ati-vga,guest_hwcursor=true,romfile="" -cdrom morphos-3.17.iso \
   -bios pegasos2.rom`
   The machine booted successfully and a startup sound was hearable
* `qemu-system-ppc -machine sam460ex -rtc base=localtime -drive \
   if=none,id=cd,file=morphos-3.17.iso,format=raw -device \
   ide-cd,drive=cd,bus=ide.1`
   The machine booted successfully into graphical desktop environment

Changes since [1]:
* Turn legacy IRQs into named GPIOs (Mark)
* Don't make VIA IDE legacy IRQs routable; just wire up in host device (Zoltan)
* Rename extracted bmdma_clear_status() (Zoltan)
   ... to bmdma_status_writeb() (Mark)

[1] 
https://lore.kernel.org/qemu-devel/20230422150728.176512-1-shen...@gmail.com/

Bernhard Beschow (6):
  hw/ide/pci: Expose legacy interrupts as named GPIOs
  hw/ide/via: Wire up IDE legacy interrupts in host device
  hw/isa/vt82c686: Remove via_isa_set_irq()
  hw/ide: Extract IDEBus assignment into bmdma_init()
  hw/ide: Extract bmdma_status_writeb()
  hw/ide/piix: Move registration of VMStateDescription to DeviceClass

 include/hw/ide/pci.h  |  1 +
 include/hw/isa/vt82c686.h |  2 --
 hw/ide/cmd646.c   |  3 +--
 hw/ide/pci.c  | 15 +++
 hw/ide/piix.c |  8 +++-
 hw/ide/sii3112.c  |  7 ++-
 hw/ide/via.c  |  9 +
 hw/isa/vt82c686.c | 11 +--
 8 files changed, 32 insertions(+), 24 deletions(-)

-- 
2.40.1




[PATCH 2/6] hw/ide/via: Wire up IDE legacy interrupts in host device

2023-05-21 Thread Bernhard Beschow
Resolves circular depencency between IDE function and south bridge.

Signed-off-by: Bernhard Beschow 
Reviewed-by: Mark Cave-Ayland 
---
 hw/ide/via.c  | 6 --
 hw/isa/vt82c686.c | 5 +
 2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/hw/ide/via.c b/hw/ide/via.c
index 177baea9a7..0caae52276 100644
--- a/hw/ide/via.c
+++ b/hw/ide/via.c
@@ -31,6 +31,7 @@
 #include "sysemu/dma.h"
 #include "hw/isa/vt82c686.h"
 #include "hw/ide/pci.h"
+#include "hw/irq.h"
 #include "trace.h"
 
 static uint64_t bmdma_read(void *opaque, hwaddr addr,
@@ -104,7 +105,8 @@ static void bmdma_setup_bar(PCIIDEState *d)
 
 static void via_ide_set_irq(void *opaque, int n, int level)
 {
-PCIDevice *d = PCI_DEVICE(opaque);
+PCIIDEState *s = opaque;
+PCIDevice *d = PCI_DEVICE(s);
 
 if (level) {
 d->config[0x70 + n * 8] |= 0x80;
@@ -112,7 +114,7 @@ static void via_ide_set_irq(void *opaque, int n, int level)
 d->config[0x70 + n * 8] &= ~0x80;
 }
 
-via_isa_set_irq(pci_get_function_0(d), 14 + n, level);
+qemu_set_irq(s->isa_irq[n], level);
 }
 
 static void via_ide_reset(DeviceState *dev)
diff --git a/hw/isa/vt82c686.c b/hw/isa/vt82c686.c
index ca89119ce0..8016c71315 100644
--- a/hw/isa/vt82c686.c
+++ b/hw/isa/vt82c686.c
@@ -692,6 +692,10 @@ static void via_isa_realize(PCIDevice *d, Error **errp)
 if (!qdev_realize(DEVICE(>ide), BUS(pci_bus), errp)) {
 return;
 }
+for (i = 0; i < 2; i++) {
+qdev_connect_gpio_out_named(DEVICE(>ide), "isa-irq", i,
+s->isa_irqs_in[14 + i]);
+}
 
 /* Functions 2-3: USB Ports */
 for (i = 0; i < ARRAY_SIZE(s->uhci); i++) {
@@ -814,6 +818,7 @@ static void vt8231_isa_reset(DeviceState *dev)
  PCI_COMMAND_MASTER | PCI_COMMAND_SPECIAL);
 pci_set_word(pci_conf + PCI_STATUS, PCI_STATUS_DEVSEL_MEDIUM);
 
+pci_conf[0x4c] = 0x04; /* IDE interrupt Routing */
 pci_conf[0x58] = 0x40; /* Miscellaneous Control 0 */
 pci_conf[0x67] = 0x08; /* Fast IR Config */
 pci_conf[0x6b] = 0x01; /* Fast IR I/O Base */
-- 
2.40.1




[PATCH 1/6] hw/ide/pci: Expose legacy interrupts as named GPIOs

2023-05-21 Thread Bernhard Beschow
Exposing the legacy IDE interrupts as GPIOs allows them to be connected in the
parent device through qdev_connect_gpio_out(), i.e. without accessing private
data of TYPE_PCI_IDE.

Signed-off-by: Bernhard Beschow 
Reviewed-by: Mark Cave-Ayland 
---
 hw/ide/pci.c | 9 +
 1 file changed, 9 insertions(+)

diff --git a/hw/ide/pci.c b/hw/ide/pci.c
index fc9224bbc9..9a5a7089d4 100644
--- a/hw/ide/pci.c
+++ b/hw/ide/pci.c
@@ -522,10 +522,19 @@ void bmdma_init(IDEBus *bus, BMDMAState *bm, PCIIDEState 
*d)
 bm->pci_dev = d;
 }
 
+static void pci_ide_init(Object *obj)
+{
+PCIIDEState *d = PCI_IDE(obj);
+
+qdev_init_gpio_out_named(DEVICE(d), d->isa_irq, "isa-irq",
+ ARRAY_SIZE(d->isa_irq));
+}
+
 static const TypeInfo pci_ide_type_info = {
 .name = TYPE_PCI_IDE,
 .parent = TYPE_PCI_DEVICE,
 .instance_size = sizeof(PCIIDEState),
+.instance_init = pci_ide_init,
 .abstract = true,
 .interfaces = (InterfaceInfo[]) {
 { INTERFACE_CONVENTIONAL_PCI_DEVICE },
-- 
2.40.1




Re: [PATCH 16/27] accel/tcg: Unify cpu_{ld,st}*_{be,le}_mmu

2023-05-21 Thread Philippe Mathieu-Daudé

Hi Richard,

On 20/5/23 18:26, Richard Henderson wrote:

With the current structure of cputlb.c, there is no difference
between the little-endian and big-endian entry points, aside
from the assert.  Unify the pairs of functions.

The only use of the functions with explicit endianness was in
target/sparc64, and that was only to satisfy the assert.


I'm having hard time to follow all the handling of the various
ASI definitions from target/sparc/asi.h. ...


Signed-off-by: Richard Henderson 
---
  include/exec/cpu_ldst.h |  58 ++-
  accel/tcg/cputlb.c  | 122 +++---
  accel/tcg/user-exec.c   | 322 ++--
  target/arm/tcg/m_helper.c   |   4 +-
  target/sparc/ldst_helper.c  |  18 +-
  accel/tcg/ldst_common.c.inc |  24 +--
  6 files changed, 137 insertions(+), 411 deletions(-)




diff --git a/target/sparc/ldst_helper.c b/target/sparc/ldst_helper.c
index 7972d56a72..981a47d8bb 100644
--- a/target/sparc/ldst_helper.c
+++ b/target/sparc/ldst_helper.c
@@ -1334,25 +1334,13 @@ uint64_t helper_ld_asi(CPUSPARCState *env, target_ulong 
addr,



Shouldn't we propagate the ASI endianness?

...
  + memop |= (asi & 8) ? MO_LE : MO_BE;
oi = make_memop_idx(memop, idx);
switch (size) {
case 1:


  ret = cpu_ldb_mmu(env, addr, oi, GETPC());
  break;
  case 2:
-if (asi & 8) {
-ret = cpu_ldw_le_mmu(env, addr, oi, GETPC());
-} else {
-ret = cpu_ldw_be_mmu(env, addr, oi, GETPC());
-}
+ret = cpu_ldw_mmu(env, addr, oi, GETPC());
  break;
  case 4:
-if (asi & 8) {
-ret = cpu_ldl_le_mmu(env, addr, oi, GETPC());
-} else {
-ret = cpu_ldl_be_mmu(env, addr, oi, GETPC());
-}
+ret = cpu_ldl_mmu(env, addr, oi, GETPC());
  break;
  case 8:
-if (asi & 8) {
-ret = cpu_ldq_le_mmu(env, addr, oi, GETPC());
-} else {
-ret = cpu_ldq_be_mmu(env, addr, oi, GETPC());
-}
+ret = cpu_ldq_mmu(env, addr, oi, GETPC());
  break;
  default:
  g_assert_not_reached();

Otherwise great simplification!



[PATCH] target/mips: Rework cp0_timer with clock API

2023-05-21 Thread Jiaxun Yang
Previous implementation of MIPS cp0_timer computes a
cp0_count_ns based on input clock. However rounding
error of cp0_count_ns can affect precision of cp0_timer.

Using clock API and a divider for cp0_timer, so we can
use clock_ns_to_ticks/clock_ns_to_ticks to avoid rounding
issue.

Also workaround the situation that in such handler flow:

count = read_c0_count()
write_c0_compare(count)

If timer had not progressed when compare was written, the
interrupt would trigger again.

Signed-off-by: Jiaxun Yang 
---
This seems fixed MTTCG booting issue on malta 5kEc with SMP.
I'm going to do more test and see if we can enable MTTCG for
mips64el.
---
 target/mips/cpu.c  |  8 +---
 target/mips/cpu.h  |  3 ++-
 target/mips/sysemu/cp0_timer.c | 35 ++
 3 files changed, 26 insertions(+), 20 deletions(-)

diff --git a/target/mips/cpu.c b/target/mips/cpu.c
index 01e0fbe10db2..b7119cbbb459 100644
--- a/target/mips/cpu.c
+++ b/target/mips/cpu.c
@@ -449,9 +449,9 @@ static void mips_cp0_period_set(MIPSCPU *cpu)
 {
 CPUMIPSState *env = >env;
 
-env->cp0_count_ns = clock_ticks_to_ns(MIPS_CPU(cpu)->clock,
-  env->cpu_model->CCRes);
-assert(env->cp0_count_ns);
+clock_set_mul_div(cpu->count_div, env->cpu_model->CCRes, 1);
+clock_set_source(cpu->count_div, cpu->clock);
+clock_set_source(env->count_clock, cpu->count_div);
 }
 
 static void mips_cpu_realizefn(DeviceState *dev, Error **errp)
@@ -504,6 +504,8 @@ static void mips_cpu_initfn(Object *obj)
 
 cpu_set_cpustate_pointers(cpu);
 cpu->clock = qdev_init_clock_in(DEVICE(obj), "clk-in", NULL, cpu, 0);
+cpu->count_div = clock_new(OBJECT(obj), "clk-div-count");
+env->count_clock = clock_new(OBJECT(obj), "clk-count");
 env->cpu_model = mcc->cpu_def;
 }
 
diff --git a/target/mips/cpu.h b/target/mips/cpu.h
index 142c55af478b..1b8107b0af86 100644
--- a/target/mips/cpu.h
+++ b/target/mips/cpu.h
@@ -1160,8 +1160,8 @@ typedef struct CPUArchState {
 
 const mips_def_t *cpu_model;
 QEMUTimer *timer; /* Internal timer */
+Clock *count_clock; /* CP0_Count clock */
 target_ulong exception_base; /* ExceptionBase input to the core */
-uint64_t cp0_count_ns; /* CP0_Count clock period (in nanoseconds) */
 } CPUMIPSState;
 
 /**
@@ -1178,6 +1178,7 @@ struct ArchCPU {
 /*< public >*/
 
 Clock *clock;
+Clock *count_div; /* Divider for CP0_Count clock */
 CPUNegativeOffsetState neg;
 CPUMIPSState env;
 };
diff --git a/target/mips/sysemu/cp0_timer.c b/target/mips/sysemu/cp0_timer.c
index 70de95d338f8..9d2bcb0dea21 100644
--- a/target/mips/sysemu/cp0_timer.c
+++ b/target/mips/sysemu/cp0_timer.c
@@ -28,15 +28,26 @@
 #include "internal.h"
 
 /* MIPS R4K timer */
+static uint32_t cpu_mips_get_count_val(CPUMIPSState *env)
+{
+int64_t now_ns;
+now_ns = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
+return env->CP0_Count +
+(uint32_t)clock_ns_to_ticks(env->count_clock, now_ns);
+}
+
 static void cpu_mips_timer_update(CPUMIPSState *env)
 {
 uint64_t now_ns, next_ns;
 uint32_t wait;
 
 now_ns = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
-wait = env->CP0_Compare - env->CP0_Count -
-   (uint32_t)(now_ns / env->cp0_count_ns);
-next_ns = now_ns + (uint64_t)wait * env->cp0_count_ns;
+wait = env->CP0_Compare - cpu_mips_get_count_val(env);
+/* Clamp interval to overflow if virtual time had not progressed */
+if (!wait) {
+wait = UINT32_MAX;
+}
+next_ns = now_ns + clock_ticks_to_ns(env->count_clock, wait);
 timer_mod(env->timer, next_ns);
 }
 
@@ -64,7 +75,7 @@ uint32_t cpu_mips_get_count(CPUMIPSState *env)
 cpu_mips_timer_expire(env);
 }
 
-return env->CP0_Count + (uint32_t)(now_ns / env->cp0_count_ns);
+return cpu_mips_get_count_val(env);
 }
 }
 
@@ -79,9 +90,8 @@ void cpu_mips_store_count(CPUMIPSState *env, uint32_t count)
 env->CP0_Count = count;
 } else {
 /* Store new count register */
-env->CP0_Count = count -
-   (uint32_t)(qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) /
-  env->cp0_count_ns);
+env->CP0_Count = count - (uint32_t)clock_ns_to_ticks(env->count_clock,
+qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL));
 /* Update timer timer */
 cpu_mips_timer_update(env);
 }
@@ -107,8 +117,8 @@ void cpu_mips_start_count(CPUMIPSState *env)
 void cpu_mips_stop_count(CPUMIPSState *env)
 {
 /* Store the current value */
-env->CP0_Count += (uint32_t)(qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) /
- env->cp0_count_ns);
+env->CP0_Count += (uint32_t)clock_ns_to_ticks(env->count_clock,
+qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL));
 }
 
 static void mips_timer_cb(void *opaque)
@@ -121,14 +131,7 @@ static void mips_timer_cb(void *opaque)
 return;
 }
 
-/*
- * ??? 

Re: [PATCH 12/27] meson: Fix detect atomic128 support with optimization

2023-05-21 Thread Philippe Mathieu-Daudé

On 20/5/23 18:26, Richard Henderson wrote:

Silly typo: sizeof(16) != 16.

Fixes: e61f1efeb730 ("meson: Detect atomic128 support with optimization")
Signed-off-by: Richard Henderson 
---
  meson.build | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/meson.build b/meson.build
index 4ffc0d3e59..5e7fc6345f 100644
--- a/meson.build
+++ b/meson.build
@@ -2555,7 +2555,7 @@ if has_int128
# __alignof(unsigned __int128) for the host.
atomic_test_128 = '''
  int main(int ac, char **av) {
-  unsigned __int128 *p = __builtin_assume_aligned(av[ac - 1], sizeof(16));
+  unsigned __int128 *p = __builtin_assume_aligned(av[ac - 1], 16);


Reviewed-by: Philippe Mathieu-Daudé 




Re: [PATCH 01/27] util: Introduce host-specific cpuinfo.h

2023-05-21 Thread Philippe Mathieu-Daudé

On 20/5/23 18:26, Richard Henderson wrote:

The entire contents of the header is host-specific, but the
existence of such a header is not, which could prevent some
host specific ifdefs at the top of the file for the include.

Add host/include/{arch,generic} to the project arguments.

Reviewed-by: Juan Quintela 
Signed-off-by: Richard Henderson 
---
  host/include/generic/host/cpuinfo.h | 4 
  meson.build | 8 
  2 files changed, 12 insertions(+)
  create mode 100644 host/include/generic/host/cpuinfo.h

diff --git a/host/include/generic/host/cpuinfo.h 
b/host/include/generic/host/cpuinfo.h
new file mode 100644
index 00..eca672064a
--- /dev/null
+++ b/host/include/generic/host/cpuinfo.h
@@ -0,0 +1,4 @@
+/*
+ * No host specific cpu indentification.
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ */
diff --git a/meson.build b/meson.build
index 0a5cdefd4d..4ffc0d3e59 100644
--- a/meson.build
+++ b/meson.build
@@ -512,6 +512,14 @@ add_project_arguments('-iquote', '.',
'-iquote', meson.current_source_dir() / 'include',
language: all_languages)
  
+host_include = meson.current_source_dir() / 'host/include/'

+if fs.is_dir(host_include / host_arch)
+  add_project_arguments('-iquote', host_include / host_arch,
+language: all_languages)
+endif


Maybe add a comment "generic include path must come last, after
host specific include path".


+add_project_arguments('-iquote', host_include / 'generic',
+  language: all_languages)
+
  sparse = find_program('cgcc', required: get_option('sparse'))
  if sparse.found()
run_target('sparse',


Reviewed-by: Philippe Mathieu-Daudé 




Re: [PATCH 10/27] include/host: Split out atomic128-cas.h

2023-05-21 Thread Philippe Mathieu-Daudé

On 20/5/23 18:26, Richard Henderson wrote:

Separates the aarch64-specific portion into its own file.

Signed-off-by: Richard Henderson 
---
  host/include/aarch64/host/atomic128-cas.h | 43 ++
  host/include/generic/host/atomic128-cas.h | 43 ++
  include/qemu/atomic128.h  | 55 +--
  3 files changed, 87 insertions(+), 54 deletions(-)
  create mode 100644 host/include/aarch64/host/atomic128-cas.h
  create mode 100644 host/include/generic/host/atomic128-cas.h

diff --git a/host/include/aarch64/host/atomic128-cas.h 
b/host/include/aarch64/host/atomic128-cas.h
new file mode 100644
index 00..1247995419
--- /dev/null
+++ b/host/include/aarch64/host/atomic128-cas.h
@@ -0,0 +1,43 @@
+/*
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ * Compare-and-swap for 128-bit atomic operations, generic version.


"Aarch64 specific"


+ *
+ * Copyright (C) 2018, 2023 Linaro, Ltd.
+ *
+ * See docs/devel/atomics.rst for discussion about the guarantees each
+ * atomic primitive is meant to provide.
+ */
+
+#ifndef AARCH64_ATOMIC128_CAS_H
+#define AARCH64_ATOMIC128_CAS_H
+
+/* Through gcc 10, aarch64 has no support for 128-bit atomics.  */





[PATCH 4/4] tests/avocado: Add boot_linux_console test for loongson3-virt

2023-05-21 Thread Jiaxun Yang
Test loongson3-virt machine againt debian kernel and cpio rootfs.

Signed-off-by: Jiaxun Yang 
---
 tests/avocado/boot_linux_console.py | 46 +
 1 file changed, 46 insertions(+)

diff --git a/tests/avocado/boot_linux_console.py 
b/tests/avocado/boot_linux_console.py
index c0675809e641..fdb479448e47 100644
--- a/tests/avocado/boot_linux_console.py
+++ b/tests/avocado/boot_linux_console.py
@@ -191,6 +191,52 @@ def test_mips64el_fuloong2e(self):
 console_pattern = 'Kernel command line: %s' % kernel_command_line
 self.wait_for_console_pattern(console_pattern)
 
+def test_mips64el_loongson3_virt_cpio(self):
+"""
+:avocado: tags=arch:mips64el
+:avocado: tags=endian:little
+:avocado: tags=machine:loongson3-virt
+:avocado: tags=cpu:Loongson-3A1000
+:avocado: tags=device:liointc
+:avocado: tags=device:loongarch_ipi
+:avocado: tags=device:goldfish_rtc
+"""
+deb_url = ('http://snapshot.debian.org/archive/debian/'
+   '20230501T024743Z/pool/main/l/linux/'
+   'linux-image-5.10.0-22-loongson-3_5.10.178-3_mips64el.deb')
+deb_hash = 'af4fcc721b727df0bef31057325e4cc02725ae0c'
+deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
+kernel_path = self.extract_from_deb(deb_path,
+'/boot/vmlinuz-5.10.0-22-loongson-3')
+initrd_url = ('https://github.com/groeck/linux-build-test/'
+  'raw/8584a59e/rootfs/'
+  'mipsel64/rootfs.mipsel64r1.cpio.gz')
+initrd_hash = '1dbb8a396e916847325284dbe2151167'
+initrd_path_gz = self.fetch_asset(initrd_url, algorithm='md5',
+  asset_hash=initrd_hash)
+initrd_path = self.workdir + "rootfs.cpio"
+archive.gzip_uncompress(initrd_path_gz, initrd_path)
+
+self.vm.set_console()
+kernel_command_line = (self.KERNEL_COMMON_COMMAND_LINE
+   + 'console=ttyS0,115200 '
+   + 'rdinit=/sbin/init noreboot')
+self.vm.add_args('-kernel', kernel_path,
+ '-initrd', initrd_path,
+ '-append', kernel_command_line,
+ '-no-reboot')
+self.vm.launch()
+wait_for_console_pattern(self, 'Boot successful.')
+
+exec_command_and_wait_for_pattern(self, 'cat /proc/cpuinfo',
+'ICT Loongson-3')
+exec_command_and_wait_for_pattern(self, 'uname -a',
+'5.10.0-22-loongson-3')
+exec_command_and_wait_for_pattern(self, 'reboot',
+'reboot: Restarting system')
+# Wait for VM to shut down gracefully
+self.vm.wait()
+
 def test_mips_malta_cpio(self):
 """
 :avocado: tags=arch:mips
-- 
2.39.2 (Apple Git-143)




[PATCH 2/4] hw/intc/loongarch_ipi: Guard LoongArch only features with ifdef

2023-05-21 Thread Jiaxun Yang
IOCSR based send features are tied to LoongArch's CPU implmentation,
ifdef them for LoongArch only so we can build loongarch_ipi on MIPS.

Note that Loongson-3A4000 have IOCSR as well, so we may implement
those features for MIPS in future.

Signed-off-by: Jiaxun Yang 
---
 hw/intc/loongarch_ipi.c | 20 
 1 file changed, 20 insertions(+)

diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
index 3e453816524e..895a2ee96e1e 100644
--- a/hw/intc/loongarch_ipi.c
+++ b/hw/intc/loongarch_ipi.c
@@ -50,6 +50,7 @@ static uint64_t loongarch_ipi_readl(void *opaque, hwaddr 
addr, unsigned size)
 return ret;
 }
 
+#ifdef TARGET_LOONGARCH64
 static void send_ipi_data(CPULoongArchState *env, uint64_t val, hwaddr addr)
 {
 int i, mask = 0, data = 0;
@@ -140,6 +141,25 @@ static void any_send(uint64_t val)
 env = >env;
 send_ipi_data(env, val, addr);
 }
+#else
+static void ipi_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+
+static void mail_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+
+static void any_send(uint64_t val)
+{
+qemu_log_mask(LOG_UNIMP, "%s: Unimplemented send 0x%" PRIx64 "\n",
+__func__, val);
+}
+#endif
 
 static void loongarch_ipi_writel(void *opaque, hwaddr addr, uint64_t val,
  unsigned size)
-- 
2.39.2 (Apple Git-143)




[PATCH 0/4] hw/mips/loongson3_virt: Wire up loongarch_ipi device

2023-05-21 Thread Jiaxun Yang
Hi all,

This series wires up loongarch_ipi device for loongson3-virt,
which is required for SMP support.

We also add a new test for loongson3-virt for acceptance harness.

Thanks
- Jiaxun

Jiaxun Yang (4):
  hw/intc/loongarch_ipi: Bring back all 4 IPI mailboxes
  hw/intc/loongarch_ipi: Guard LoongArch only features with ifdef
  hw/mips/loongson3_virt: Wire up loongarch_ipi device
  tests/avocado: Add boot_linux_console test for loongson3-virt

 hw/intc/loongarch_ipi.c | 26 ++--
 hw/mips/Kconfig |  1 +
 hw/mips/loongson3_bootp.c   |  2 --
 hw/mips/loongson3_bootp.h   |  3 ++
 hw/mips/loongson3_virt.c| 20 +++--
 include/hw/intc/loongarch_ipi.h |  4 ++-
 tests/avocado/boot_linux_console.py | 46 +
 7 files changed, 94 insertions(+), 8 deletions(-)

-- 
2.39.2 (Apple Git-143)




[PATCH 3/4] hw/mips/loongson3_virt: Wire up loongarch_ipi device

2023-05-21 Thread Jiaxun Yang
Wire up loongarch_ipi device for loongson3_virt machine, so we
can have SMP support for TCG backend as well.

Signed-off-by: Jiaxun Yang 
---
 hw/mips/Kconfig   |  1 +
 hw/mips/loongson3_bootp.c |  2 --
 hw/mips/loongson3_bootp.h |  3 +++
 hw/mips/loongson3_virt.c  | 20 ++--
 4 files changed, 22 insertions(+), 4 deletions(-)

diff --git a/hw/mips/Kconfig b/hw/mips/Kconfig
index da3a37e215ec..7cb6c1def16c 100644
--- a/hw/mips/Kconfig
+++ b/hw/mips/Kconfig
@@ -40,6 +40,7 @@ config LOONGSON3V
 imply QXL if SPICE
 select SERIAL
 select GOLDFISH_RTC
+select LOONGARCH_IPI
 select LOONGSON_LIOINTC
 select PCI_DEVICES
 select PCI_EXPRESS_GENERIC_BRIDGE
diff --git a/hw/mips/loongson3_bootp.c b/hw/mips/loongson3_bootp.c
index f99af229327a..474d3556b2e5 100644
--- a/hw/mips/loongson3_bootp.c
+++ b/hw/mips/loongson3_bootp.c
@@ -25,8 +25,6 @@
 #include "hw/boards.h"
 #include "hw/mips/loongson3_bootp.h"
 
-#define LOONGSON3_CORE_PER_NODE 4
-
 static void init_cpu_info(void *g_cpuinfo, uint64_t cpu_freq)
 {
 struct efi_cpuinfo_loongson *c = g_cpuinfo;
diff --git a/hw/mips/loongson3_bootp.h b/hw/mips/loongson3_bootp.h
index d525ab745a69..55f98858a5f4 100644
--- a/hw/mips/loongson3_bootp.h
+++ b/hw/mips/loongson3_bootp.h
@@ -200,6 +200,8 @@ struct boot_params {
 struct efi_reset_system_t reset_system;
 };
 
+#define LOONGSON3_CORE_PER_NODE 4
+
 /* Overall MMIO & Memory layout */
 enum {
 VIRT_LOWMEM,
@@ -211,6 +213,7 @@ enum {
 VIRT_BIOS_ROM,
 VIRT_UART,
 VIRT_LIOINTC,
+VIRT_IPI,
 VIRT_PCIE_MMIO,
 VIRT_HIGHMEM
 };
diff --git a/hw/mips/loongson3_virt.c b/hw/mips/loongson3_virt.c
index 25534288dd81..a57245012598 100644
--- a/hw/mips/loongson3_virt.c
+++ b/hw/mips/loongson3_virt.c
@@ -38,6 +38,7 @@
 #include "hw/mips/loongson3_bootp.h"
 #include "hw/misc/unimp.h"
 #include "hw/intc/i8259.h"
+#include "hw/intc/loongarch_ipi.h"
 #include "hw/loader.h"
 #include "hw/isa/superio.h"
 #include "hw/pci/msi.h"
@@ -76,6 +77,7 @@ const MemMapEntry virt_memmap[] = {
 [VIRT_PCIE_ECAM] =   { 0x1a00, 0x200 },
 [VIRT_BIOS_ROM] ={ 0x1fc0,  0x20 },
 [VIRT_UART] ={ 0x1fe001e0,   0x8 },
+[VIRT_IPI] = { 0x3ff01000, 0x400 },
 [VIRT_LIOINTC] = { 0x3ff01400,  0x64 },
 [VIRT_PCIE_MMIO] =   { 0x4000,0x4000 },
 [VIRT_HIGHMEM] = { 0x8000,   0x0 }, /* Variable */
@@ -529,6 +531,8 @@ static void mips_loongson3_virt_init(MachineState *machine)
 clock_set_hz(cpuclk, DEF_LOONGSON3_FREQ);
 
 for (i = 0; i < machine->smp.cpus; i++) {
+int node = i / LOONGSON3_CORE_PER_NODE;
+int core = i % LOONGSON3_CORE_PER_NODE;
 int ip;
 
 /* init CPUs */
@@ -539,12 +543,24 @@ static void mips_loongson3_virt_init(MachineState 
*machine)
 cpu_mips_clock_init(cpu);
 qemu_register_reset(main_cpu_reset, cpu);
 
-if (i >= 4) {
+/* IPI controller is in kernel for KVM */
+if (!kvm_enabled()) {
+DeviceState *ipi;
+
+hwaddr base = ((hwaddr)node << 44) + virt_memmap[VIRT_IPI].base;
+base += core * 0x100;
+ipi = qdev_new(TYPE_LOONGARCH_IPI);
+sysbus_realize_and_unref(SYS_BUS_DEVICE(ipi), _fatal);
+qdev_connect_gpio_out(ipi, 0, cpu->env.irq[6]);
+sysbus_mmio_map(SYS_BUS_DEVICE(ipi), 0, base);
+}
+
+if (node > 0) {
 continue; /* Only node-0 can be connected to LIOINTC */
 }
 
 for (ip = 0; ip < 4 ; ip++) {
-int pin = i * 4 + ip;
+int pin = core * LOONGSON3_CORE_PER_NODE + ip;
 sysbus_connect_irq(SYS_BUS_DEVICE(liointc),
pin, cpu->env.irq[ip + 2]);
 }
-- 
2.39.2 (Apple Git-143)




[PATCH 1/4] hw/intc/loongarch_ipi: Bring back all 4 IPI mailboxes

2023-05-21 Thread Jiaxun Yang
As per "Loongson 3A5000/3B5000 Processor Reference Manual",
Loongson 3A5000's IPI implementation have 4 mailboxes per
core.

However, in 78464f023b54 ("hw/loongarch/virt: Modify ipi as
percpu device"), the number of IPI mailboxes was reduced to
one, which mismatches actual hardware.

It won't affect LoongArch based system as LoongArch boot code
only uses the first mailbox, however MIPS based Loongson boot
code uses all 4 mailboxes.

Fixes: 78464f023b54 ("hw/loongarch/virt: Modify ipi as percpu device")
Signed-off-by: Jiaxun Yang 
---
 hw/intc/loongarch_ipi.c | 6 +++---
 include/hw/intc/loongarch_ipi.h | 4 +++-
 2 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/hw/intc/loongarch_ipi.c b/hw/intc/loongarch_ipi.c
index d6ab91721ea1..3e453816524e 100644
--- a/hw/intc/loongarch_ipi.c
+++ b/hw/intc/loongarch_ipi.c
@@ -238,14 +238,14 @@ static void loongarch_ipi_init(Object *obj)
 
 static const VMStateDescription vmstate_ipi_core = {
 .name = "ipi-single",
-.version_id = 1,
-.minimum_version_id = 1,
+.version_id = 2,
+.minimum_version_id = 2,
 .fields = (VMStateField[]) {
 VMSTATE_UINT32(status, IPICore),
 VMSTATE_UINT32(en, IPICore),
 VMSTATE_UINT32(set, IPICore),
 VMSTATE_UINT32(clear, IPICore),
-VMSTATE_UINT32_ARRAY(buf, IPICore, 2),
+VMSTATE_UINT32_ARRAY(buf, IPICore, IPI_MBX_NUM * 2),
 VMSTATE_END_OF_LIST()
 }
 };
diff --git a/include/hw/intc/loongarch_ipi.h b/include/hw/intc/loongarch_ipi.h
index 664e050b926e..6c6194786e80 100644
--- a/include/hw/intc/loongarch_ipi.h
+++ b/include/hw/intc/loongarch_ipi.h
@@ -28,6 +28,8 @@
 #define MAIL_SEND_OFFSET  0
 #define ANY_SEND_OFFSET   (IOCSR_ANY_SEND - IOCSR_MAIL_SEND)
 
+#define IPI_MBX_NUM   4
+
 #define TYPE_LOONGARCH_IPI "loongarch_ipi"
 OBJECT_DECLARE_SIMPLE_TYPE(LoongArchIPI, LOONGARCH_IPI)
 
@@ -37,7 +39,7 @@ typedef struct IPICore {
 uint32_t set;
 uint32_t clear;
 /* 64bit buf divide into 2 32bit buf */
-uint32_t buf[2];
+uint32_t buf[IPI_MBX_NUM * 2];
 qemu_irq irq;
 } IPICore;
 
-- 
2.39.2 (Apple Git-143)




Re: [PATCH v6 1/4] bswap: Add the ability to store to an unaligned 24 bit field

2023-05-21 Thread Michael S. Tsirkin
On Sat, May 20, 2023 at 07:08:22PM +0200, Philippe Mathieu-Daudé wrote:
> On 20/5/23 17:15, Richard Henderson wrote:
> > On 5/20/23 06:15, BALATON Zoltan wrote:
> > > On Sat, 20 May 2023, Peter Maydell wrote:
> > > > On Fri, 19 May 2023 at 15:19, Jonathan Cameron via
> > > >  wrote:
> > > > > 
> > > > > From: Ira Weiny 
> > > > > 
> > > > > CXL has 24 bit unaligned fields which need to be stored to.  CXL is
> > > > > specified as little endian.
> > > > > 
> > > > > Define st24_le_p() and the supporting functions to store such a field
> > > > > from a 32 bit host native value.
> > > > > 
> > > > > The use of b, w, l, q as the size specifier is limiting.  So "24" was
> > > > > used for the size part of the function name.
> > > 
> > > Maybe it's clearer to use 24 but if we want to keep these somewhat
> > > consistent how about using t for Triplet, Three-bytes or
> > > Twenty-four?
> > 
> > I think it's clearer to use '3'.
> > When I added 128-bit support I used cpu_ld16_mmu.
> 
> There is also ld8u / ld8s / st8.
> 
> > I think it would be clearer to not use letters anywhere, and to use
> > units of bytes instead of units of bits (no one can store just a bit),
> > but changing everything is a big job.
> 
> So:
> 
> ldub ->  ld1u,
> 
> lduw_le -> ld2u_le,
> 
> virtio_stl -> virtio_st4,
> 
> stq_be -> st8_be.
> 
> Right?


No, using bits is so ingrained by now, that people will think
st8 is a single byte.

And yes, you can store a bit - you have to read modify write but
hey.

> Also we have:
> 
> cpu_ld/st_*
> virtio_ld/st_*
> ld/st_*_phys
> ld/st_*_pci_dma
> address_space_ld/st
> 
> While mass-changing, we could use FOO_ld/st_BAR with FOO
> for API and BAR for API variant (endian, mmuidx, ra, ...):
> 
> So:
> 
> ld/st_*_pci_dma -> pci_dma_ld/st_*
> 
> for ld/st_*_phys I'm not sure.




Re: [PATCH] acpi/tests/bios-tables-test: add an environment variable for iasl location

2023-05-21 Thread Michael S. Tsirkin
On Wed, May 17, 2023 at 05:37:51PM +0530, Ani Sinha wrote:
> Currently the meson based QEMU build process locates the iasl binary from the
> current PATH and other locations [1] and uses that to set CONFIG_IASL which is
> then used by the test.
> 
> This has two disadvantages:
>  - If iasl was not previously installed in the PATH, one has to install iasl
>and rebuild QEMU in order to pick up the iasl location. One cannot simply
>use the existing bios-tables-test binary because CONFIG_IASL is only set
>during the QEMU build time by meson and then bios-tables-test has to be
>rebuilt with CONFIG_IASL set in order to use iasl.
>  - Sometimes, the stock iasl that comes with distributions is simply not good
>enough because it does not support the latest ACPI changes - newly
>introduced tables or new table attributes etc. In order to test ACPI code
>in QEMU, one has to clone the latest acpica upstream repository and
>rebuild iasl in order to get support for it. In those cases, one may want
>the test to use the iasl binary from a non-standard location.
> 
> In order to overcome the above two disadvantages, we introduce a new
> environment variable IASL_PATH that can be set by the tester pointing to an
> possibly non-standard iasl binary location. Bios-tables-test then uses this
> environment variable to set its iasl location, possibly also overriding the
> location that was pointed to by CONFIG_IASL that was set by meson. This way
> developers can not only use this new environment variable to set iasl
> location to quickly run bios-tables-test but also can point the test to a
> custom iasl if required.
> 
> [1] https://mesonbuild.com/Reference-manual_functions.html#find_program
> 
> Signed-off-by: Ani Sinha 

I don't much like it that the default is now a bit harder
to run. Case of playing with iasl is really esotetic.
I propose a simpler idea.
- add config-iasl.h with only CONFIG_IASL set to path
- include from bios test

Now if you change path only bios test is rebuilt.

Hmm?


> ---
>  tests/qtest/bios-tables-test.c | 14 ++
>  1 file changed, 14 insertions(+)
> 
> sample runs:
> 
> $ QTEST_QEMU_BINARY=./qemu-system-x86_64 V=2 ./tests/qtest/bios-tables-test
> ...
> acpi-test: Warning! APIC binary file mismatch. Actual [aml:/tmp/aml-DLHA51], 
> Expected [aml:tests/data/acpi/pc/APIC].
> See source file tests/qtest/bios-tables-test.c for instructions on how to 
> update expected files.
> Using iasl: /usr/bin/iasl
> acpi-test: Warning! APIC mismatch. Actual [asl:/tmp/asl-L9GA51.dsl, 
> aml:/tmp/aml-DLHA51], Expected [asl:/tmp/asl-10EA51.dsl, 
> aml:tests/data/acpi/pc/APIC].
> 
> $ QTEST_QEMU_BINARY=./qemu-system-x86_64 V=2 
> IASL_PATH=/home/anisinha/workspace/acpica/generate/unix/bin/iasl 
> ./tests/qtest/bios-tables-test
> ...
> acpi-test: Warning! APIC binary file mismatch. Actual [aml:/tmp/aml-5CQ341], 
> Expected [aml:tests/data/acpi/pc/APIC].
> See source file tests/qtest/bios-tables-test.c for instructions on how to 
> update expected files.
> User has provided an iasl path, using that: 
> /home/anisinha/workspace/acpica/generate/unix/bin/iasl
> acpi-test: Warning! APIC mismatch. Actual [asl:/tmp/asl-2GQ341.dsl, 
> aml:/tmp/aml-5CQ341], Expected [asl:/tmp/asl-IBR341.dsl, 
> aml:tests/data/acpi/pc/APIC].
> 
> diff --git a/tests/qtest/bios-tables-test.c b/tests/qtest/bios-tables-test.c
> index 7fd88b0e9c..37e8e484cb 100644
> --- a/tests/qtest/bios-tables-test.c
> +++ b/tests/qtest/bios-tables-test.c
> @@ -440,7 +440,12 @@ static void test_acpi_asl(test_data *data)
>  AcpiSdtTable *sdt, *exp_sdt;
>  test_data exp_data = {};
>  gboolean exp_err, err, all_tables_match = true;
> +const char *user_iasl_path = getenv("IASL_PATH");
>  
> +/* if user has provided a path to iasl, use that */
> +if (user_iasl_path) {
> +iasl = user_iasl_path;
> +}
>  exp_data.tables = load_expected_aml(data);
>  dump_aml_files(data, false);
>  for (i = 0; i < data->tables->len; ++i) {
> @@ -473,6 +478,15 @@ static void test_acpi_asl(test_data *data)
>  continue;
>  }
>  
> +if (verbosity_level >= 2) {
> +if (user_iasl_path) {
> +fprintf(stderr, "User has provided an iasl path," \
> +"using that: %s\n", user_iasl_path);
> +} else {
> +fprintf(stderr, "Using iasl: %s\n", iasl);
> +}
> +}
> +
>  err = load_asl(data->tables, sdt);
>  asl = normalize_asl(sdt->asl);
>  
> -- 
> 2.39.1