Re: [PATCH 2/3] scsi: make io_timeout configurable

2021-09-20 Thread Hannes Reinecke

On 9/20/21 8:56 PM, Paolo Bonzini wrote:

On Mon, Nov 16, 2020 at 7:31 PM Hannes Reinecke  wrote:

The current code sets an infinite timeout on SG_IO requests,
causing the guest to stall if the host experiences a frame
loss.
This patch adds an 'io_timeout' parameter for SCSIDevice to
make the SG_IO timeout configurable, and also shortens the
default timeout to 30 seconds to avoid infinite stalls.


Hannes, could 30 seconds be a bit too short for tape drives?

It would, but then anyone attempting to use tapes via qemu emulation 
deserves to suffer.
Tapes are bitchy even when used normally, so attempting to use them 
under qemu emulation will land you with lots of unhappy experiences, 
where the timeout is the least of your problems.

I sincerely doubt anyone will be using tapes here.
Not in real-world scenarios.

Cheers,

Hannes
--
Dr. Hannes ReineckeKernel Storage Architect
h...@suse.de  +49 911 74053 688
SUSE Software Solutions GmbH, Maxfeldstr. 5, 90409 Nürnberg
HRB 36809 (AG Nürnberg), Geschäftsführer: Felix Imendörffer



Re: [PATCH v2 38/53] qapi: introduce x-query-lapic QMP command

2021-09-20 Thread Dongli Zhang
Hi Daniel,

On 9/14/21 7:20 AM, Daniel P. Berrangé wrote:
> This is a counterpart to the HMP "info lapic" command. It is being
> added with an "x-" prefix because this QMP command is intended as an
> adhoc debugging tool and will thus not be modelled in QAPI as fully
> structured data, nor will it have long term guaranteed stability.
> The existing HMP command is rewritten to call the QMP command.
> 
> This command is unable to use the pre-existing HumanReadableText,
> because if 'common.json' is included into 'machine-target.json'
> the static marshalling method for HumanReadableText will be reported
> as unused by the compiler on all architectures except s390x.
> 
> Possible options were
> 
>  1 Support 'if' conditionals on 'include' statements in QAPI
>  2 Add further commands to 'machine-target.json' that use
>HumanReadableText, such that it has at least one usage
>on all architecture targets.
>  3 Duplicate HumanReadableText as TargetHumanReadableText
>adding conditions
> 
> This patch takes option (3) in the belief that we will eventually
> get to a point where option (2) happens, and TargetHumanReadableText
> can be removed again.
> 
> Signed-off-by: Daniel P. Berrangé 
> ---
>  hw/core/cpu-common.c |   7 ++
>  include/hw/core/cpu.h|  10 +++
>  qapi/machine-target.json |  19 -
>  target/i386/cpu-dump.c   | 161 ---
>  target/i386/cpu.h|   4 +-
>  target/i386/monitor.c|  46 +--
>  6 files changed, 160 insertions(+), 87 deletions(-)
> 
> diff --git a/hw/core/cpu-common.c b/hw/core/cpu-common.c
> index c2cd33a817..d1ebc77d1b 100644
> --- a/hw/core/cpu-common.c
> +++ b/hw/core/cpu-common.c
> @@ -49,6 +49,13 @@ CPUState *cpu_by_arch_id(int64_t id)
>  return NULL;
>  }
>  
> +int64_t cpu_get_arch_id(CPUState *cpu)
> +{
> +CPUClass *cc = CPU_GET_CLASS(cpu);
> +
> +return cc->get_arch_id(cpu);
> +}
> +
>  bool cpu_exists(int64_t id)
>  {
>  return !!cpu_by_arch_id(id);
> diff --git a/include/hw/core/cpu.h b/include/hw/core/cpu.h
> index 1599ef9df3..a0913eedaa 100644
> --- a/include/hw/core/cpu.h
> +++ b/include/hw/core/cpu.h
> @@ -780,6 +780,16 @@ bool cpu_exists(int64_t id);
>   */
>  CPUState *cpu_by_arch_id(int64_t id);
>  
> +/**
> + * cpu_get_arch_id:
> + * @cpu: the CPU to query
> + *
> + * Get the guest exposed CPU ID for @cpu
> + *
> + * Returns: The guest exposed CPU ID
> + */
> +int64_t cpu_get_arch_id(CPUState *cpu);
> +
>  /**
>   * cpu_interrupt:
>   * @cpu: The CPU to set an interrupt on.
> diff --git a/qapi/machine-target.json b/qapi/machine-target.json
> index 9040aff863..62220d1f08 100644
> --- a/qapi/machine-target.json
> +++ b/qapi/machine-target.json
> @@ -353,7 +353,8 @@
>  ##
>  { 'struct': 'TargetHumanReadableText',
>'data': { 'human-readable-text': 'str' },
> -  'if': 'TARGET_S390X' }
> +  'if': { 'any': ['TARGET_S390X',
> +  'TARGET_I386' ] } }
>  
>  ##
>  # @x-query-cmma:
> @@ -369,6 +370,22 @@
>'returns': 'TargetHumanReadableText',
>'if': 'TARGET_S390X' }
>  
> +##
> +# @x-query-lapic:
> +#
> +# @apic-id: the local APIC ID to report
> +#
> +# Query local APIC state.
> +#
> +# Returns: local APIC state
> +#
> +# Since: 6.2
> +##
> +{ 'command': 'x-query-lapic',
> +  'data': { 'apic-id': 'int' },
> +  'returns': 'TargetHumanReadableText',
> +  'if': 'TARGET_I386' }
> +
>  ##
>  # @x-query-skeys:
>  #
> diff --git a/target/i386/cpu-dump.c b/target/i386/cpu-dump.c
> index f30fbcb76e..41a1f64138 100644
> --- a/target/i386/cpu-dump.c
> +++ b/target/i386/cpu-dump.c
> @@ -20,6 +20,7 @@
>  #include "qemu/osdep.h"
>  #include "cpu.h"
>  #include "qemu/qemu-print.h"
> +#include "qapi/error.h"
>  #ifndef CONFIG_USER_ONLY
>  #include "hw/i386/apic_internal.h"
>  #endif
> @@ -179,24 +180,26 @@ static inline const char *dm2str(uint32_t dm)
>  return str[dm];
>  }
>  
> -static void dump_apic_lvt(const char *name, uint32_t lvt, bool is_timer)
> +static void format_apic_lvt(const char *name, uint32_t lvt, bool is_timer,
> +GString *buf)
>  {
>  uint32_t dm = (lvt & APIC_LVT_DELIV_MOD) >> APIC_LVT_DELIV_MOD_SHIFT;
> -qemu_printf("%s\t 0x%08x %s %-5s %-6s %-7s %-12s %-6s",
> -name, lvt,
> -lvt & APIC_LVT_INT_POLARITY ? "active-lo" : "active-hi",
> -lvt & APIC_LVT_LEVEL_TRIGGER ? "level" : "edge",
> -lvt & APIC_LVT_MASKED ? "masked" : "",
> -lvt & APIC_LVT_DELIV_STS ? "pending" : "",
> -!is_timer ?
> -"" : lvt & APIC_LVT_TIMER_PERIODIC ?
> -"periodic" : lvt & APIC_LVT_TIMER_TSCDEADLINE ?
> -"tsc-deadline" : "one-shot",
> +g_string_append_printf(buf, "%s\t 0x%08x %s %-5s %-6s %-7s %-12s %-6s",
> +   name, lvt,
> +   lvt & APIC_LVT_INT_POLARITY ?
> +   "active-lo" : "active-hi",
> 

Re: [PATCH 1/2] meson: introduce modules_arch

2021-09-20 Thread Gerd Hoffmann
  Hi,

> But, in anyway, I'll still need to store the target architecture that
> can use such core module, like I did here in this patch. Otherwise,
> if I compile different targets at the same time, I'll end up with the
> same problem of targets trying to load wrong modules.

That all works just fine today.  If you have target-specific modules
(i.e. source files added to specific_ss instead of softmmu_ss when
compiling into core qemu) you only need to add those to the
target_modules[] (instead of modules[]) and you are set.

In-tree example: qtest accelerator.

take care,
  Gerd




Re: [PATCH v2 23/23] test-clone-visitor: Correct an accidental rename

2021-09-20 Thread Philippe Mathieu-Daudé
On 9/17/21 16:31, Markus Armbruster wrote:
> Commit b359f4b203 "tests: Rename UserDefNativeListUnion to
> UserDefListUnion" renamed test_clone_native_list() to
> test_clone_list_union().  The function has nothing to do with unions.
> Rename it to test_clone_list().
> 
> Signed-off-by: Markus Armbruster 
> Reviewed-by: Eric Blake 
> ---
>  tests/unit/test-clone-visitor.c | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)

Maybe nitpicking, while this patch is related to the series,
although I understand you noticed the mistake while working
on this series, I'd move this cleanup as 1/23.

Reviewed-by: Philippe Mathieu-Daudé 




Re: [RESEND PATCH 1/3] hw/intc: openpic: Correct the reset value of IPIDR for FSL chipset

2021-09-20 Thread David Gibson
On Sat, Sep 18, 2021 at 11:26:51AM +0800, Bin Meng wrote:
> The reset value of IPIDR should be zero for Freescale chipset, per
> the following 2 manuals I checked:
> 
> - P2020RM (https://www.nxp.com/webapp/Download?colCode=P2020RM)
> - P4080RM (https://www.nxp.com/webapp/Download?colCode=P4080RM)
> 
> Currently it is set to 1, which leaves the IPI enabled on core 0
> after power-on reset. Such may cause unexpected interrupt to be
> delivered to core 0 if the IPI is triggered from core 0 to other
> cores later.
> 
> Fixes: ffd5e9fe0276 ("openpic: Reset IRQ source private members")
> Resolves: https://gitlab.com/qemu-project/qemu/-/issues/584
> Signed-off-by: Bin Meng 

Since these patches are very simple and look sensible, I've applied
them to ppc-for-6.2.

However, you should note that Greg and I are both moving into other
areas and don't have much capacity for ppc maintainership any more.
Therefore I'll shortly be sending some MAINTAINERS updates moving
openpic (amongst other things) to "Orphan" status.

> ---
> 
>  hw/intc/openpic.c | 9 +
>  1 file changed, 9 insertions(+)
> 
> diff --git a/hw/intc/openpic.c b/hw/intc/openpic.c
> index 9b4c17854d..2790c6710a 100644
> --- a/hw/intc/openpic.c
> +++ b/hw/intc/openpic.c
> @@ -1276,6 +1276,15 @@ static void openpic_reset(DeviceState *d)
>  break;
>  }
>  
> +/* Mask all IPI interrupts for Freescale OpenPIC */
> +if ((opp->model == OPENPIC_MODEL_FSL_MPIC_20) ||
> +(opp->model == OPENPIC_MODEL_FSL_MPIC_42)) {
> +if (i >= opp->irq_ipi0 && i < opp->irq_tim0) {
> +write_IRQreg_idr(opp, i, 0);
> +continue;
> +}
> +}
> +
>  write_IRQreg_idr(opp, i, opp->idr_reset);
>  }
>  /* Initialise IRQ destinations */

-- 
David Gibson| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au  | minimalist, thank you.  NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson


signature.asc
Description: PGP signature


Re: [PATCH v4 3/4] target/ppc: Convert debug to trace events (decrementer and IRQ)

2021-09-20 Thread David Gibson
On Mon, Sep 20, 2021 at 09:42:25AM +0200, Cédric Le Goater wrote:
> On 9/20/21 09:34, David Gibson wrote:
> > On Mon, Sep 20, 2021 at 08:12:02AM +0200, Cédric Le Goater wrote:
> > > Signed-off-by: Cédric Le Goater 
> > 
> > So.. all the functions here are called *set_irq*, but you've named the
> > tracepoints *irq_set*.
> 
> 
> Yes. I did that on purpose to identify easily the PPC IRQ subsystem,
> and to be able to use '-trace ppc_irq*' from the command line and in
> the monitor.
> 
> > It's not a big deal, but it seems like it
> > would be less confusing if you flipped that around to match the
> > function names.
> 
> but you would loose the ability to do what I described above.

Good point.  Applied to ppc-for-6.2.

> 
> Thanks,
> 
> C.
> > > ---
> > >   hw/ppc/ppc.c| 169 
> > >   hw/ppc/trace-events |  22 +-
> > >   2 files changed, 82 insertions(+), 109 deletions(-)
> > > 
> > > diff --git a/hw/ppc/ppc.c b/hw/ppc/ppc.c
> > > index a327206a0a1e..b813ef732ec1 100644
> > > --- a/hw/ppc/ppc.c
> > > +++ b/hw/ppc/ppc.c
> > > @@ -37,22 +37,6 @@
> > >   #include "migration/vmstate.h"
> > >   #include "trace.h"
> > > -//#define PPC_DEBUG_IRQ
> > > -//#define PPC_DEBUG_TB
> > > -
> > > -#ifdef PPC_DEBUG_IRQ
> > > -#  define LOG_IRQ(...) qemu_log_mask(CPU_LOG_INT, ## __VA_ARGS__)
> > > -#else
> > > -#  define LOG_IRQ(...) do { } while (0)
> > > -#endif
> > > -
> > > -
> > > -#ifdef PPC_DEBUG_TB
> > > -#  define LOG_TB(...) qemu_log(__VA_ARGS__)
> > > -#else
> > > -#  define LOG_TB(...) do { } while (0)
> > > -#endif
> > > -
> > >   static void cpu_ppc_tb_stop (CPUPPCState *env);
> > >   static void cpu_ppc_tb_start (CPUPPCState *env);
> > > @@ -86,9 +70,8 @@ void ppc_set_irq(PowerPCCPU *cpu, int n_IRQ, int level)
> > >   }
> > > -LOG_IRQ("%s: %p n_IRQ %d level %d => pending %08" PRIx32
> > > -"req %08x\n", __func__, env, n_IRQ, level,
> > > -env->pending_interrupts, CPU(cpu)->interrupt_request);
> > > +trace_ppc_irq_set_exit(env, n_IRQ, level, env->pending_interrupts,
> > > +   CPU(cpu)->interrupt_request);
> > >   if (locked) {
> > >   qemu_mutex_unlock_iothread();
> > > @@ -102,8 +85,8 @@ static void ppc6xx_set_irq(void *opaque, int pin, int 
> > > level)
> > >   CPUPPCState *env = >env;
> > >   int cur_level;
> > > -LOG_IRQ("%s: env %p pin %d level %d\n", __func__,
> > > -env, pin, level);
> > > +trace_ppc_irq_set(env, pin, level);
> > > +
> > >   cur_level = (env->irq_input_state >> pin) & 1;
> > >   /* Don't generate spurious events */
> > >   if ((cur_level == 1 && level == 0) || (cur_level == 0 && level != 
> > > 0)) {
> > > @@ -112,8 +95,7 @@ static void ppc6xx_set_irq(void *opaque, int pin, int 
> > > level)
> > >   switch (pin) {
> > >   case PPC6xx_INPUT_TBEN:
> > >   /* Level sensitive - active high */
> > > -LOG_IRQ("%s: %s the time base\n",
> > > -__func__, level ? "start" : "stop");
> > > +trace_ppc_irq_set_state("time base", level);
> > >   if (level) {
> > >   cpu_ppc_tb_start(env);
> > >   } else {
> > > @@ -122,14 +104,12 @@ static void ppc6xx_set_irq(void *opaque, int pin, 
> > > int level)
> > >   break;
> > >   case PPC6xx_INPUT_INT:
> > >   /* Level sensitive - active high */
> > > -LOG_IRQ("%s: set the external IRQ state to %d\n",
> > > -__func__, level);
> > > +trace_ppc_irq_set_state("external IRQ", level);
> > >   ppc_set_irq(cpu, PPC_INTERRUPT_EXT, level);
> > >   break;
> > >   case PPC6xx_INPUT_SMI:
> > >   /* Level sensitive - active high */
> > > -LOG_IRQ("%s: set the SMI IRQ state to %d\n",
> > > -__func__, level);
> > > +trace_ppc_irq_set_state("SMI IRQ", level);
> > >   ppc_set_irq(cpu, PPC_INTERRUPT_SMI, level);
> > >   break;
> > >   case PPC6xx_INPUT_MCP:
> > > @@ -138,8 +118,7 @@ static void ppc6xx_set_irq(void *opaque, int pin, int 
> > > level)
> > >*603/604/740/750: check HID0[EMCP]
> > >*/
> > >   if (cur_level == 1 && level == 0) {
> > > -LOG_IRQ("%s: raise machine check state\n",
> > > -__func__);
> > > +trace_ppc_irq_set_state("machine check", 1);
> > >   ppc_set_irq(cpu, PPC_INTERRUPT_MCK, 1);
> > >   }
> > >   break;
> > > @@ -148,20 +127,19 @@ static void ppc6xx_set_irq(void *opaque, int pin, 
> > > int level)
> > >   /* XXX: TODO: relay the signal to CKSTP_OUT pin */
> > >   /* XXX: Note that the only way to restart the CPU is to 
> > > reset it */
> > >   if (level) {
> > > - 

Re: [PATCH v9 0/7] pSeries FORM2 affinity support

2021-09-20 Thread David Gibson
On Mon, Sep 20, 2021 at 02:49:40PM -0300, Daniel Henrique Barboza wrote:
> Hi,
> 
> This version has a changed asked by Greg in patch 4, along with
> Greg's R-bs.
> 
> Changes from v8:
> - added Greg's reviewed-by in patches 3, 5, 6 and 7
> - patch 4:
>   * changed get_associativity() to return a const pointer
> - v8 link:
> https://lists.gnu.org/archive/html/qemu-devel/2021-09/msg04747.html

Applied to ppc-for-6.2, thanks.

> 
> Daniel Henrique Barboza (7):
>   spapr_numa.c: split FORM1 code into helpers
>   spapr_numa.c: scrap 'legacy_numa' concept
>   spapr_numa.c: parametrize FORM1 macros
>   spapr_numa.c: rename numa_assoc_array to FORM1_assoc_array
>   spapr: move FORM1 verifications to post CAS
>   spapr_numa.c: FORM2 NUMA affinity support
>   spapr_numa.c: handle auto NUMA node with no distance info
> 
>  hw/ppc/spapr.c  |  41 +---
>  hw/ppc/spapr_hcall.c|   7 +
>  hw/ppc/spapr_numa.c | 380 ++--
>  include/hw/ppc/spapr.h  |  35 ++--
>  include/hw/ppc/spapr_numa.h |   1 +
>  include/hw/ppc/spapr_ovec.h |   1 +
>  6 files changed, 354 insertions(+), 111 deletions(-)
> 

-- 
David Gibson| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au  | minimalist, thank you.  NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson


signature.asc
Description: PGP signature


Re: [PATCH v9 6/7] spapr_numa.c: FORM2 NUMA affinity support

2021-09-20 Thread David Gibson
On Mon, Sep 20, 2021 at 02:49:46PM -0300, Daniel Henrique Barboza wrote:
> The main feature of FORM2 affinity support is the separation of NUMA
> distances from ibm,associativity information. This allows for a more
> flexible and straightforward NUMA distance assignment without relying on
> complex associations between several levels of NUMA via
> ibm,associativity matches. Another feature is its extensibility. This base
> support contains the facilities for NUMA distance assignment, but in the
> future more facilities will be added for latency, performance, bandwidth
> and so on.
> 
> This patch implements the base FORM2 affinity support as follows:
> 
> - the use of FORM2 associativity is indicated by using bit 2 of byte 5
> of ibm,architecture-vec-5. A FORM2 aware guest can choose to use FORM1
> or FORM2 affinity. Setting both forms will default to FORM2. We're not
> advertising FORM2 for pseries-6.1 and older machine versions to prevent
> guest visible changes in those;
> 
> - ibm,associativity-reference-points has a new semantic. Instead of
> being used to calculate distances via NUMA levels, it's now used to
> indicate the primary domain index in the ibm,associativity domain of
> each resource. In our case it's set to {0x4}, matching the position
> where we already place logical_domain_id;
> 
> - two new RTAS DT artifacts are introduced: ibm,numa-lookup-index-table
> and ibm,numa-distance-table. The index table is used to list all the
> NUMA logical domains of the platform, in ascending order, and allows for
> spartial NUMA configurations (although QEMU ATM doesn't support that).
> ibm,numa-distance-table is an array that contains all the distances from
> the first NUMA node to all other nodes, then the second NUMA node
> distances to all other nodes and so on;
> 
> - get_max_dist_ref_points(), get_numa_assoc_size() and get_associativity()
> now checks for OV5_FORM2_AFFINITY and returns FORM2 values if the guest
> selected FORM2 affinity during CAS.
> 
> Reviewed-by: Greg Kurz 
> Signed-off-by: Daniel Henrique Barboza 
> ---
>  hw/ppc/spapr.c  |   8 ++
>  hw/ppc/spapr_numa.c | 146 
>  include/hw/ppc/spapr.h  |   9 +++
>  include/hw/ppc/spapr_ovec.h |   1 +
>  4 files changed, 164 insertions(+)
> 
> diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c
> index ada85ee083..babb662845 100644
> --- a/hw/ppc/spapr.c
> +++ b/hw/ppc/spapr.c
> @@ -2752,6 +2752,11 @@ static void spapr_machine_init(MachineState *machine)
>  
>  spapr_ovec_set(spapr->ov5, OV5_FORM1_AFFINITY);
>  
> +/* Do not advertise FORM2 NUMA support for pseries-6.1 and older */
> +if (!smc->pre_6_2_numa_affinity) {
> +spapr_ovec_set(spapr->ov5, OV5_FORM2_AFFINITY);
> +}
> +
>  /* advertise support for dedicated HP event source to guests */
>  if (spapr->use_hotplug_event_source) {
>  spapr_ovec_set(spapr->ov5, OV5_HP_EVT);
> @@ -4667,8 +4672,11 @@ DEFINE_SPAPR_MACHINE(6_2, "6.2", true);
>   */
>  static void spapr_machine_6_1_class_options(MachineClass *mc)
>  {
> +SpaprMachineClass *smc = SPAPR_MACHINE_CLASS(mc);
> +
>  spapr_machine_6_2_class_options(mc);
>  compat_props_add(mc->compat_props, hw_compat_6_1, hw_compat_6_1_len);
> +smc->pre_6_2_numa_affinity = true;
>  }
>  
>  DEFINE_SPAPR_MACHINE(6_1, "6.1", false);
> diff --git a/hw/ppc/spapr_numa.c b/hw/ppc/spapr_numa.c
> index 6718c0fdd1..13db321997 100644
> --- a/hw/ppc/spapr_numa.c
> +++ b/hw/ppc/spapr_numa.c
> @@ -24,6 +24,10 @@
>   */
>  static int get_max_dist_ref_points(SpaprMachineState *spapr)
>  {
> +if (spapr_ovec_test(spapr->ov5_cas, OV5_FORM2_AFFINITY)) {
> +return FORM2_DIST_REF_POINTS;
> +}
> +
>  return FORM1_DIST_REF_POINTS;
>  }
>  
> @@ -32,6 +36,10 @@ static int get_max_dist_ref_points(SpaprMachineState 
> *spapr)
>   */
>  static int get_numa_assoc_size(SpaprMachineState *spapr)
>  {
> +if (spapr_ovec_test(spapr->ov5_cas, OV5_FORM2_AFFINITY)) {
> +return FORM2_NUMA_ASSOC_SIZE;
> +}
> +
>  return FORM1_NUMA_ASSOC_SIZE;
>  }
>  
> @@ -52,6 +60,9 @@ static int get_vcpu_assoc_size(SpaprMachineState *spapr)
>   */
>  static const uint32_t *get_associativity(SpaprMachineState *spapr, int 
> node_id)
>  {
> +if (spapr_ovec_test(spapr->ov5_cas, OV5_FORM2_AFFINITY)) {
> +return spapr->FORM2_assoc_array[node_id];
> +}
>  return spapr->FORM1_assoc_array[node_id];
>  }
>  
> @@ -295,14 +306,50 @@ static void 
> spapr_numa_FORM1_affinity_init(SpaprMachineState *spapr,
>  spapr_numa_define_FORM1_domains(spapr);
>  }
>  
> +/*
> + * Init NUMA FORM2 machine state data
> + */
> +static void spapr_numa_FORM2_affinity_init(SpaprMachineState *spapr)
> +{
> +int i;
> +
> +/*
> + * For all resources but CPUs, FORM2 associativity arrays will
> + * be a size 2 array with the following format:
> + *
> + * ibm,associativity = {1, numa_id}
> + *
> + * CPUs will write an additional 'vcpu_id' 

Re: [PATCH v9 7/7] spapr_numa.c: handle auto NUMA node with no distance info

2021-09-20 Thread David Gibson
On Mon, Sep 20, 2021 at 02:49:47PM -0300, Daniel Henrique Barboza wrote:
> numa_complete_configuration() in hw/core/numa.c always adds a NUMA node
> for the pSeries machine if none was specified, but without node distance
> information for the single node created.
> 
> NUMA FORM1 affinity code didn't rely on numa_state information to do its
> job, but FORM2 does. As is now, this is the result of a pSeries guest
> with NUMA FORM2 affinity when no NUMA nodes is specified:
> 
> $ numactl -H
> available: 1 nodes (0)
> node 0 cpus: 0
> node 0 size: 16222 MB
> node 0 free: 15681 MB
> No distance information available.
> 
> This can be amended in spapr_numa_FORM2_write_rtas_tables(). We're
> enforcing that the local distance (the distance to the node to itself) is
> always 10. This allows for the proper creation of the NUMA distance tables,
> fixing the output of 'numactl -H' in the guest:
> 
> $ numactl -H
> available: 1 nodes (0)
> node 0 cpus: 0
> node 0 size: 16222 MB
> node 0 free: 15685 MB
> node distances:
> node   0
>   0:  10
> 
> CC: Igor Mammedov 
> Reviewed-by: Greg Kurz 
> Signed-off-by: Daniel Henrique Barboza 
> ---
>  hw/ppc/spapr_numa.c | 11 +++
>  1 file changed, 11 insertions(+)
> 
> diff --git a/hw/ppc/spapr_numa.c b/hw/ppc/spapr_numa.c
> index 13db321997..58d5dc7084 100644
> --- a/hw/ppc/spapr_numa.c
> +++ b/hw/ppc/spapr_numa.c
> @@ -539,6 +539,17 @@ static void 
> spapr_numa_FORM2_write_rtas_tables(SpaprMachineState *spapr,
>  
>  for (src = 0; src < nb_numa_nodes; src++) {
>  for (dst = 0; dst < nb_numa_nodes; dst++) {
> +/*
> + * We need to be explicit with the local distance
> + * value to cover the case where the user didn't added any
> + * NUMA nodes, but QEMU adds the default NUMA node without
> + * adding the numa_info to retrieve distance info from.
> + */
> +if (src == dst) {
> +node_distances[i++] = 10;

Would it make sense to use NUMA_DISTANCE_MIN here, rather than a fixed
value?

Again, simple enough that it can be fixed in followup.

> +continue;
> +}
> +
>  node_distances[i++] = numa_info[src].distance[dst];
>  }
>  }

-- 
David Gibson| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au  | minimalist, thank you.  NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson


signature.asc
Description: PGP signature


Re: [PATCH v4 4/4] target/ppc: Fix 64-bit decrementer

2021-09-20 Thread David Gibson
On Mon, Sep 20, 2021 at 08:12:03AM +0200, Cédric Le Goater wrote:
> The current way the mask is built can overflow with a 64-bit decrementer.
> Use sextract64() to extract the signed values and remove the logic to
> handle negative values which has become useless.
> 
> Cc: Luis Fernando Fujita Pires 
> Fixes: a8dafa525181 ("target/ppc: Implement large decrementer support for 
> TCG")
> Signed-off-by: Cédric Le Goater 

Applied to ppc-for-6.2, thanks.
> ---
>  hw/ppc/ppc.c | 20 +---
>  1 file changed, 9 insertions(+), 11 deletions(-)
> 
> diff --git a/hw/ppc/ppc.c b/hw/ppc/ppc.c
> index b813ef732ec1..f5d012f860af 100644
> --- a/hw/ppc/ppc.c
> +++ b/hw/ppc/ppc.c
> @@ -821,14 +821,12 @@ static void __cpu_ppc_store_decr(PowerPCCPU *cpu, 
> uint64_t *nextp,
>  CPUPPCState *env = >env;
>  ppc_tb_t *tb_env = env->tb_env;
>  uint64_t now, next;
> -bool negative;
> +int64_t signed_value;
> +int64_t signed_decr;
>  
>  /* Truncate value to decr_width and sign extend for simplicity */
> -value &= ((1ULL << nr_bits) - 1);
> -negative = !!(value & (1ULL << (nr_bits - 1)));
> -if (negative) {
> -value |= (0xULL << nr_bits);
> -}
> +signed_value = sextract64(value, 0, nr_bits);
> +signed_decr = sextract64(decr, 0, nr_bits);
>  
>  trace_ppc_decr_store(nr_bits, decr, value);
>  
> @@ -850,16 +848,16 @@ static void __cpu_ppc_store_decr(PowerPCCPU *cpu, 
> uint64_t *nextp,
>   * On MSB edge based DEC implementations the MSB going from 0 -> 1 
> triggers
>   * an edge interrupt, so raise it here too.
>   */
> -if ((value < 3) ||
> -((tb_env->flags & PPC_DECR_UNDERFLOW_LEVEL) && negative) ||
> -((tb_env->flags & PPC_DECR_UNDERFLOW_TRIGGERED) && negative
> -  && !(decr & (1ULL << (nr_bits - 1) {
> +if ((signed_value < 3) ||
> +((tb_env->flags & PPC_DECR_UNDERFLOW_LEVEL) && signed_value < 0) ||
> +((tb_env->flags & PPC_DECR_UNDERFLOW_TRIGGERED) && signed_value < 0
> +  && signed_decr >= 0)) {
>  (*raise_excp)(cpu);
>  return;
>  }
>  
>  /* On MSB level based systems a 0 for the MSB stops interrupt delivery */
> -if (!negative && (tb_env->flags & PPC_DECR_UNDERFLOW_LEVEL)) {
> +if (signed_value >= 0 && (tb_env->flags & PPC_DECR_UNDERFLOW_LEVEL)) {
>  (*lower_excp)(cpu);
>  }
>  

-- 
David Gibson| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au  | minimalist, thank you.  NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson


signature.asc
Description: PGP signature


[PULL 09/10] hw/core: Make do_unaligned_access noreturn

2021-09-20 Thread Richard Henderson
While we may have had some thought of allowing system-mode
to return from this hook, we have no guests that require this.

Reviewed-by: Alistair Francis 
Reviewed-by: Alex Bennée 
Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 include/hw/core/tcg-cpu-ops.h  | 3 ++-
 target/alpha/cpu.h | 4 ++--
 target/arm/internals.h | 2 +-
 target/microblaze/cpu.h| 2 +-
 target/mips/tcg/tcg-internal.h | 4 ++--
 target/nios2/cpu.h | 4 ++--
 target/ppc/internal.h  | 4 ++--
 target/riscv/cpu.h | 2 +-
 target/s390x/s390x-internal.h  | 4 ++--
 target/sh4/cpu.h   | 4 ++--
 target/xtensa/cpu.h| 4 ++--
 target/hppa/cpu.c  | 7 ---
 12 files changed, 23 insertions(+), 21 deletions(-)

diff --git a/include/hw/core/tcg-cpu-ops.h b/include/hw/core/tcg-cpu-ops.h
index 55123cb4d2..6cbe17f2e6 100644
--- a/include/hw/core/tcg-cpu-ops.h
+++ b/include/hw/core/tcg-cpu-ops.h
@@ -78,10 +78,11 @@ struct TCGCPUOps {
   MemTxResult response, uintptr_t retaddr);
 /**
  * @do_unaligned_access: Callback for unaligned access handling
+ * The callback must exit via raising an exception.
  */
 void (*do_unaligned_access)(CPUState *cpu, vaddr addr,
 MMUAccessType access_type,
-int mmu_idx, uintptr_t retaddr);
+int mmu_idx, uintptr_t retaddr) QEMU_NORETURN;
 
 /**
  * @adjust_watchpoint_address: hack for cpu_check_watchpoint used by ARM
diff --git a/target/alpha/cpu.h b/target/alpha/cpu.h
index ce9ec32199..772828cc26 100644
--- a/target/alpha/cpu.h
+++ b/target/alpha/cpu.h
@@ -283,8 +283,8 @@ hwaddr alpha_cpu_get_phys_page_debug(CPUState *cpu, vaddr 
addr);
 int alpha_cpu_gdb_read_register(CPUState *cpu, GByteArray *buf, int reg);
 int alpha_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg);
 void alpha_cpu_do_unaligned_access(CPUState *cpu, vaddr addr,
-   MMUAccessType access_type,
-   int mmu_idx, uintptr_t retaddr);
+   MMUAccessType access_type, int mmu_idx,
+   uintptr_t retaddr) QEMU_NORETURN;
 
 #define cpu_list alpha_cpu_list
 
diff --git a/target/arm/internals.h b/target/arm/internals.h
index cd2ea8a388..8a77929793 100644
--- a/target/arm/internals.h
+++ b/target/arm/internals.h
@@ -594,7 +594,7 @@ bool arm_s1_regime_using_lpae_format(CPUARMState *env, 
ARMMMUIdx mmu_idx);
 /* Raise a data fault alignment exception for the specified virtual address */
 void arm_cpu_do_unaligned_access(CPUState *cs, vaddr vaddr,
  MMUAccessType access_type,
- int mmu_idx, uintptr_t retaddr);
+ int mmu_idx, uintptr_t retaddr) QEMU_NORETURN;
 
 /* arm_cpu_do_transaction_failed: handle a memory system error response
  * (eg "no device/memory present at address") by raising an external abort
diff --git a/target/microblaze/cpu.h b/target/microblaze/cpu.h
index 13ed3cd4dd..b7a848bbae 100644
--- a/target/microblaze/cpu.h
+++ b/target/microblaze/cpu.h
@@ -361,7 +361,7 @@ bool mb_cpu_exec_interrupt(CPUState *cs, int int_req);
 #endif /* !CONFIG_USER_ONLY */
 void mb_cpu_do_unaligned_access(CPUState *cs, vaddr vaddr,
 MMUAccessType access_type,
-int mmu_idx, uintptr_t retaddr);
+int mmu_idx, uintptr_t retaddr) QEMU_NORETURN;
 void mb_cpu_dump_state(CPUState *cpu, FILE *f, int flags);
 hwaddr mb_cpu_get_phys_page_attrs_debug(CPUState *cpu, vaddr addr,
 MemTxAttrs *attrs);
diff --git a/target/mips/tcg/tcg-internal.h b/target/mips/tcg/tcg-internal.h
index c7a77ddccd..bad3deb611 100644
--- a/target/mips/tcg/tcg-internal.h
+++ b/target/mips/tcg/tcg-internal.h
@@ -22,8 +22,8 @@ bool mips_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
MMUAccessType access_type, int mmu_idx,
bool probe, uintptr_t retaddr);
 void mips_cpu_do_unaligned_access(CPUState *cpu, vaddr addr,
-  MMUAccessType access_type,
-  int mmu_idx, uintptr_t retaddr);
+  MMUAccessType access_type, int mmu_idx,
+  uintptr_t retaddr) QEMU_NORETURN;
 
 const char *mips_exception_name(int32_t exception);
 
diff --git a/target/nios2/cpu.h b/target/nios2/cpu.h
index 88a511209c..a80587338a 100644
--- a/target/nios2/cpu.h
+++ b/target/nios2/cpu.h
@@ -197,8 +197,8 @@ void dump_mmu(CPUNios2State *env);
 void nios2_cpu_dump_state(CPUState *cpu, FILE *f, int flags);
 hwaddr nios2_cpu_get_phys_page_debug(CPUState *cpu, vaddr addr);
 void nios2_cpu_do_unaligned_access(CPUState *cpu, vaddr addr,
- 

[PULL 07/10] tcg/sparc: Drop inline markers

2021-09-20 Thread Richard Henderson
Let the compiler decide about inlining.

Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/sparc/tcg-target.c.inc | 45 +++---
 1 file changed, 22 insertions(+), 23 deletions(-)

diff --git a/tcg/sparc/tcg-target.c.inc b/tcg/sparc/tcg-target.c.inc
index 688827968b..1763253edd 100644
--- a/tcg/sparc/tcg-target.c.inc
+++ b/tcg/sparc/tcg-target.c.inc
@@ -294,12 +294,12 @@ static const int tcg_target_call_oarg_regs[] = {
 bool use_vis3_instructions;
 #endif
 
-static inline int check_fit_i64(int64_t val, unsigned int bits)
+static bool check_fit_i64(int64_t val, unsigned int bits)
 {
 return val == sextract64(val, 0, bits);
 }
 
-static inline int check_fit_i32(int32_t val, unsigned int bits)
+static bool check_fit_i32(int32_t val, unsigned int bits)
 {
 return val == sextract32(val, 0, bits);
 }
@@ -362,14 +362,14 @@ static bool tcg_target_const_match(int64_t val, TCGType 
type, int ct)
 }
 }
 
-static inline void tcg_out_arith(TCGContext *s, TCGReg rd, TCGReg rs1,
- TCGReg rs2, int op)
+static void tcg_out_arith(TCGContext *s, TCGReg rd, TCGReg rs1,
+  TCGReg rs2, int op)
 {
 tcg_out32(s, op | INSN_RD(rd) | INSN_RS1(rs1) | INSN_RS2(rs2));
 }
 
-static inline void tcg_out_arithi(TCGContext *s, TCGReg rd, TCGReg rs1,
-  int32_t offset, int op)
+static void tcg_out_arithi(TCGContext *s, TCGReg rd, TCGReg rs1,
+   int32_t offset, int op)
 {
 tcg_out32(s, op | INSN_RD(rd) | INSN_RS1(rs1) | INSN_IMM13(offset));
 }
@@ -381,8 +381,7 @@ static void tcg_out_arithc(TCGContext *s, TCGReg rd, TCGReg 
rs1,
   | (val2const ? INSN_IMM13(val2) : INSN_RS2(val2)));
 }
 
-static inline bool tcg_out_mov(TCGContext *s, TCGType type,
-   TCGReg ret, TCGReg arg)
+static bool tcg_out_mov(TCGContext *s, TCGType type, TCGReg ret, TCGReg arg)
 {
 if (ret != arg) {
 tcg_out_arith(s, ret, arg, TCG_REG_G0, ARITH_OR);
@@ -390,12 +389,12 @@ static inline bool tcg_out_mov(TCGContext *s, TCGType 
type,
 return true;
 }
 
-static inline void tcg_out_sethi(TCGContext *s, TCGReg ret, uint32_t arg)
+static void tcg_out_sethi(TCGContext *s, TCGReg ret, uint32_t arg)
 {
 tcg_out32(s, SETHI | INSN_RD(ret) | ((arg & 0xfc00) >> 10));
 }
 
-static inline void tcg_out_movi_imm13(TCGContext *s, TCGReg ret, int32_t arg)
+static void tcg_out_movi_imm13(TCGContext *s, TCGReg ret, int32_t arg)
 {
 tcg_out_arithi(s, ret, TCG_REG_G0, arg, ARITH_OR);
 }
@@ -470,14 +469,14 @@ static void tcg_out_movi_int(TCGContext *s, TCGType type, 
TCGReg ret,
 }
 }
 
-static inline void tcg_out_movi(TCGContext *s, TCGType type,
-TCGReg ret, tcg_target_long arg)
+static void tcg_out_movi(TCGContext *s, TCGType type,
+ TCGReg ret, tcg_target_long arg)
 {
 tcg_out_movi_int(s, type, ret, arg, false);
 }
 
-static inline void tcg_out_ldst_rr(TCGContext *s, TCGReg data, TCGReg a1,
-   TCGReg a2, int op)
+static void tcg_out_ldst_rr(TCGContext *s, TCGReg data, TCGReg a1,
+TCGReg a2, int op)
 {
 tcg_out32(s, op | INSN_RD(data) | INSN_RS1(a1) | INSN_RS2(a2));
 }
@@ -494,20 +493,20 @@ static void tcg_out_ldst(TCGContext *s, TCGReg ret, 
TCGReg addr,
 }
 }
 
-static inline void tcg_out_ld(TCGContext *s, TCGType type, TCGReg ret,
-  TCGReg arg1, intptr_t arg2)
+static void tcg_out_ld(TCGContext *s, TCGType type, TCGReg ret,
+   TCGReg arg1, intptr_t arg2)
 {
 tcg_out_ldst(s, ret, arg1, arg2, (type == TCG_TYPE_I32 ? LDUW : LDX));
 }
 
-static inline void tcg_out_st(TCGContext *s, TCGType type, TCGReg arg,
-  TCGReg arg1, intptr_t arg2)
+static void tcg_out_st(TCGContext *s, TCGType type, TCGReg arg,
+   TCGReg arg1, intptr_t arg2)
 {
 tcg_out_ldst(s, arg, arg1, arg2, (type == TCG_TYPE_I32 ? STW : STX));
 }
 
-static inline bool tcg_out_sti(TCGContext *s, TCGType type, TCGArg val,
-   TCGReg base, intptr_t ofs)
+static bool tcg_out_sti(TCGContext *s, TCGType type, TCGArg val,
+TCGReg base, intptr_t ofs)
 {
 if (val == 0) {
 tcg_out_st(s, type, TCG_REG_G0, base, ofs);
@@ -527,12 +526,12 @@ static void tcg_out_ld_ptr(TCGContext *s, TCGReg ret, 
const void *arg)
 tcg_out_ld(s, TCG_TYPE_PTR, ret, ret, (uintptr_t)arg & 0x3ff);
 }
 
-static inline void tcg_out_sety(TCGContext *s, TCGReg rs)
+static void tcg_out_sety(TCGContext *s, TCGReg rs)
 {
 tcg_out32(s, WRY | INSN_RS1(TCG_REG_G0) | INSN_RS2(rs));
 }
 
-static inline void tcg_out_rdy(TCGContext *s, TCGReg rd)
+static void tcg_out_rdy(TCGContext *s, TCGReg rd)
 {
 tcg_out32(s, RDY | INSN_RD(rd));
 }
@@ -552,7 +551,7 @@ static void tcg_out_div32(TCGContext *s, TCGReg rd, TCGReg 

[PULL 05/10] tcg/mips: Unset TCG_TARGET_HAS_direct_jump

2021-09-20 Thread Richard Henderson
Only use indirect jumps.  Finish weaning away from the
unique alignment requirements for code_gen_buffer.

Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/mips/tcg-target.h | 12 +---
 tcg/mips/tcg-target.c.inc | 23 +--
 2 files changed, 10 insertions(+), 25 deletions(-)

diff --git a/tcg/mips/tcg-target.h b/tcg/mips/tcg-target.h
index 3a62055f04..c366fdf74b 100644
--- a/tcg/mips/tcg-target.h
+++ b/tcg/mips/tcg-target.h
@@ -39,11 +39,7 @@
 #define TCG_TARGET_TLB_DISPLACEMENT_BITS 16
 #define TCG_TARGET_NB_REGS 32
 
-/*
- * We have a 256MB branch region, but leave room to make sure the
- * main executable is also within that region.
- */
-#define MAX_CODE_GEN_BUFFER_SIZE  (128 * MiB)
+#define MAX_CODE_GEN_BUFFER_SIZE  ((size_t)-1)
 
 typedef enum {
 TCG_REG_ZERO = 0,
@@ -136,7 +132,7 @@ extern bool use_mips32r2_instructions;
 #define TCG_TARGET_HAS_muluh_i321
 #define TCG_TARGET_HAS_mulsh_i321
 #define TCG_TARGET_HAS_bswap32_i32  1
-#define TCG_TARGET_HAS_direct_jump  1
+#define TCG_TARGET_HAS_direct_jump  0
 
 #if TCG_TARGET_REG_BITS == 64
 #define TCG_TARGET_HAS_add2_i32 0
@@ -207,7 +203,9 @@ extern bool use_mips32r2_instructions;
 #define TCG_TARGET_DEFAULT_MO (0)
 #define TCG_TARGET_HAS_MEMORY_BSWAP 1
 
-void tb_target_set_jmp_target(uintptr_t, uintptr_t, uintptr_t, uintptr_t);
+/* not defined -- call should be eliminated at compile time */
+void tb_target_set_jmp_target(uintptr_t, uintptr_t, uintptr_t, uintptr_t)
+QEMU_ERROR("code path is reachable");
 
 #ifdef CONFIG_SOFTMMU
 #define TCG_TARGET_NEED_LDST_LABELS
diff --git a/tcg/mips/tcg-target.c.inc b/tcg/mips/tcg-target.c.inc
index 3a40af8799..41ffa28394 100644
--- a/tcg/mips/tcg-target.c.inc
+++ b/tcg/mips/tcg-target.c.inc
@@ -1654,17 +1654,11 @@ static void tcg_out_op(TCGContext *s, TCGOpcode opc,
 }
 break;
 case INDEX_op_goto_tb:
-if (s->tb_jmp_insn_offset) {
-/* direct jump method */
-s->tb_jmp_insn_offset[a0] = tcg_current_code_size(s);
-/* Avoid clobbering the address during retranslation.  */
-tcg_out32(s, OPC_J | (*(uint32_t *)s->code_ptr & 0x3ff));
-} else {
-/* indirect jump method */
-tcg_out_ld(s, TCG_TYPE_PTR, TCG_TMP0, TCG_REG_ZERO,
-   (uintptr_t)(s->tb_jmp_target_addr + a0));
-tcg_out_opc_reg(s, OPC_JR, 0, TCG_TMP0, 0);
-}
+/* indirect jump method */
+tcg_debug_assert(s->tb_jmp_insn_offset == 0);
+tcg_out_ld(s, TCG_TYPE_PTR, TCG_TMP0, TCG_REG_ZERO,
+   (uintptr_t)(s->tb_jmp_target_addr + a0));
+tcg_out_opc_reg(s, OPC_JR, 0, TCG_TMP0, 0);
 tcg_out_nop(s);
 set_jmp_reset_offset(s, a0);
 break;
@@ -2538,13 +2532,6 @@ static void tcg_target_init(TCGContext *s)
 tcg_regset_set_reg(s->reserved_regs, TCG_REG_GP);   /* global pointer */
 }
 
-void tb_target_set_jmp_target(uintptr_t tc_ptr, uintptr_t jmp_rx,
-  uintptr_t jmp_rw, uintptr_t addr)
-{
-qatomic_set((uint32_t *)jmp_rw, deposit32(OPC_J, 0, 26, addr >> 2));
-flush_idcache_range(jmp_rx, jmp_rw, 4);
-}
-
 typedef struct {
 DebugFrameHeader h;
 uint8_t fde_def_cfa[4];
-- 
2.25.1




[PULL 08/10] tcg/sparc: Introduce tcg_out_mov_delay

2021-09-20 Thread Richard Henderson
This version of tcg_out_mov is emits a nop to fill the
delay slot if the move is not required.

The only current use, for INDEX_op_goto_ptr, will always
require the move but properly documents the delay slot.

Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/sparc/tcg-target.c.inc | 21 +++--
 1 file changed, 15 insertions(+), 6 deletions(-)

diff --git a/tcg/sparc/tcg-target.c.inc b/tcg/sparc/tcg-target.c.inc
index 1763253edd..9720d76abd 100644
--- a/tcg/sparc/tcg-target.c.inc
+++ b/tcg/sparc/tcg-target.c.inc
@@ -362,6 +362,11 @@ static bool tcg_target_const_match(int64_t val, TCGType 
type, int ct)
 }
 }
 
+static void tcg_out_nop(TCGContext *s)
+{
+tcg_out32(s, NOP);
+}
+
 static void tcg_out_arith(TCGContext *s, TCGReg rd, TCGReg rs1,
   TCGReg rs2, int op)
 {
@@ -389,6 +394,15 @@ static bool tcg_out_mov(TCGContext *s, TCGType type, 
TCGReg ret, TCGReg arg)
 return true;
 }
 
+static void tcg_out_mov_delay(TCGContext *s, TCGReg ret, TCGReg arg)
+{
+if (ret != arg) {
+tcg_out_arith(s, ret, arg, TCG_REG_G0, ARITH_OR);
+} else {
+tcg_out_nop(s);
+}
+}
+
 static void tcg_out_sethi(TCGContext *s, TCGReg ret, uint32_t arg)
 {
 tcg_out32(s, SETHI | INSN_RD(ret) | ((arg & 0xfc00) >> 10));
@@ -551,11 +565,6 @@ static void tcg_out_div32(TCGContext *s, TCGReg rd, TCGReg 
rs1,
uns ? ARITH_UDIV : ARITH_SDIV);
 }
 
-static void tcg_out_nop(TCGContext *s)
-{
-tcg_out32(s, NOP);
-}
-
 static const uint8_t tcg_cond_to_bcond[] = {
 [TCG_COND_EQ] = COND_E,
 [TCG_COND_NE] = COND_NE,
@@ -1349,7 +1358,7 @@ static void tcg_out_op(TCGContext *s, TCGOpcode opc,
 case INDEX_op_goto_ptr:
 tcg_out_arithi(s, TCG_REG_G0, a0, 0, JMPL);
 if (USE_REG_TB) {
-tcg_out_arith(s, TCG_REG_TB, a0, TCG_REG_G0, ARITH_OR);
+tcg_out_mov_delay(s, TCG_REG_TB, a0);
 } else {
 tcg_out_nop(s);
 }
-- 
2.25.1




[PULL 04/10] tcg/mips: Allow JAL to be out of range in tcg_out_bswap_subr

2021-09-20 Thread Richard Henderson
Weaning off of unique alignment requirements, so allow JAL
to not reach the target.  TCG_TMP1 is always available for
use as a scratch because it is clobbered by the subroutine
being called.

Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/mips/tcg-target.c.inc | 6 --
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/tcg/mips/tcg-target.c.inc b/tcg/mips/tcg-target.c.inc
index 320795a637..3a40af8799 100644
--- a/tcg/mips/tcg-target.c.inc
+++ b/tcg/mips/tcg-target.c.inc
@@ -573,8 +573,10 @@ static void tcg_out_bswap16(TCGContext *s, TCGReg ret, 
TCGReg arg, int flags)
 
 static void tcg_out_bswap_subr(TCGContext *s, const tcg_insn_unit *sub)
 {
-bool ok = tcg_out_opc_jmp(s, OPC_JAL, sub);
-tcg_debug_assert(ok);
+if (!tcg_out_opc_jmp(s, OPC_JAL, sub)) {
+tcg_out_movi(s, TCG_TYPE_PTR, TCG_TMP1, (uintptr_t)sub);
+tcg_out_opc_reg(s, OPC_JALR, TCG_REG_RA, TCG_TMP1, 0);
+}
 }
 
 static void tcg_out_bswap32(TCGContext *s, TCGReg ret, TCGReg arg, int flags)
-- 
2.25.1




[PULL 10/10] tcg/riscv: Remove add with zero on user-only memory access

2021-09-20 Thread Richard Henderson
Reviewed-by: Philippe Mathieu-Daudé 
Reviewed-by: Alistair Francis 
Signed-off-by: Richard Henderson 
---
 tcg/riscv/tcg-target.c.inc | 10 ++
 1 file changed, 2 insertions(+), 8 deletions(-)

diff --git a/tcg/riscv/tcg-target.c.inc b/tcg/riscv/tcg-target.c.inc
index c16f96b401..dc8d8f1de2 100644
--- a/tcg/riscv/tcg-target.c.inc
+++ b/tcg/riscv/tcg-target.c.inc
@@ -1130,10 +1130,7 @@ static void tcg_out_qemu_ld(TCGContext *s, const TCGArg 
*args, bool is_64)
 tcg_out_ext32u(s, base, addr_regl);
 addr_regl = base;
 }
-
-if (guest_base == 0) {
-tcg_out_opc_reg(s, OPC_ADD, base, addr_regl, TCG_REG_ZERO);
-} else {
+if (guest_base != 0) {
 tcg_out_opc_reg(s, OPC_ADD, base, TCG_GUEST_BASE_REG, addr_regl);
 }
 tcg_out_qemu_ld_direct(s, data_regl, data_regh, base, opc, is_64);
@@ -1199,10 +1196,7 @@ static void tcg_out_qemu_st(TCGContext *s, const TCGArg 
*args, bool is_64)
 tcg_out_ext32u(s, base, addr_regl);
 addr_regl = base;
 }
-
-if (guest_base == 0) {
-tcg_out_opc_reg(s, OPC_ADD, base, addr_regl, TCG_REG_ZERO);
-} else {
+if (guest_base != 0) {
 tcg_out_opc_reg(s, OPC_ADD, base, TCG_GUEST_BASE_REG, addr_regl);
 }
 tcg_out_qemu_st_direct(s, data_regl, data_regh, base, opc);
-- 
2.25.1




[PULL 01/10] include/exec: Move cpu_signal_handler declaration

2021-09-20 Thread Richard Henderson
There is nothing target specific about this.  The implementation
is host specific, but the declaration is 100% common.

Reviewed-By: Warner Losh 
Reviewed-by: Philippe Mathieu-Daudé 
Reviewed-by: Alistair Francis 
Signed-off-by: Richard Henderson 
---
 include/exec/exec-all.h | 13 +
 target/alpha/cpu.h  |  6 --
 target/arm/cpu.h|  7 ---
 target/avr/cpu.h|  2 --
 target/cris/cpu.h   |  8 
 target/hexagon/cpu.h|  3 ---
 target/hppa/cpu.h   |  3 ---
 target/i386/cpu.h   |  7 ---
 target/m68k/cpu.h   |  8 
 target/microblaze/cpu.h |  7 ---
 target/mips/cpu.h   |  3 ---
 target/mips/internal.h  |  2 --
 target/nios2/cpu.h  |  2 --
 target/openrisc/cpu.h   |  2 --
 target/ppc/cpu.h|  7 ---
 target/riscv/cpu.h  |  2 --
 target/rx/cpu.h |  4 
 target/s390x/cpu.h  |  7 ---
 target/sh4/cpu.h|  3 ---
 target/sparc/cpu.h  |  2 --
 target/tricore/cpu.h|  2 --
 target/xtensa/cpu.h |  2 --
 22 files changed, 13 insertions(+), 89 deletions(-)

diff --git a/include/exec/exec-all.h b/include/exec/exec-all.h
index 5d1b6d80fb..9d5987ba04 100644
--- a/include/exec/exec-all.h
+++ b/include/exec/exec-all.h
@@ -662,6 +662,19 @@ static inline tb_page_addr_t 
get_page_addr_code_hostp(CPUArchState *env,
 }
 return addr;
 }
+
+/**
+ * cpu_signal_handler
+ * @signum: host signal number
+ * @pinfo: host siginfo_t
+ * @puc: host ucontext_t
+ *
+ * To be called from the SIGBUS and SIGSEGV signal handler to inform the
+ * virtual cpu of exceptions.  Returns true if the signal was handled by
+ * the virtual CPU.
+ */
+int cpu_signal_handler(int signum, void *pinfo, void *puc);
+
 #else
 static inline void mmap_lock(void) {}
 static inline void mmap_unlock(void) {}
diff --git a/target/alpha/cpu.h b/target/alpha/cpu.h
index 4e993bd15b..ce9ec32199 100644
--- a/target/alpha/cpu.h
+++ b/target/alpha/cpu.h
@@ -287,7 +287,6 @@ void alpha_cpu_do_unaligned_access(CPUState *cpu, vaddr 
addr,
int mmu_idx, uintptr_t retaddr);
 
 #define cpu_list alpha_cpu_list
-#define cpu_signal_handler cpu_alpha_signal_handler
 
 typedef CPUAlphaState CPUArchState;
 typedef AlphaCPU ArchCPU;
@@ -440,11 +439,6 @@ void alpha_translate_init(void);
 #define CPU_RESOLVING_TYPE TYPE_ALPHA_CPU
 
 void alpha_cpu_list(void);
-/* you can call this signal handler from your SIGBUS and SIGSEGV
-   signal handlers to inform the virtual CPU of exceptions. non zero
-   is returned if the signal was handled by the virtual CPU.  */
-int cpu_alpha_signal_handler(int host_signum, void *pinfo,
- void *puc);
 bool alpha_cpu_tlb_fill(CPUState *cs, vaddr address, int size,
 MMUAccessType access_type, int mmu_idx,
 bool probe, uintptr_t retaddr);
diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 09d9027734..751141915d 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -1121,12 +1121,6 @@ static inline bool is_a64(CPUARMState *env)
 return env->aarch64;
 }
 
-/* you can call this signal handler from your SIGBUS and SIGSEGV
-   signal handlers to inform the virtual CPU of exceptions. non zero
-   is returned if the signal was handled by the virtual CPU.  */
-int cpu_arm_signal_handler(int host_signum, void *pinfo,
-   void *puc);
-
 /**
  * pmu_op_start/finish
  * @env: CPUARMState
@@ -3015,7 +3009,6 @@ bool write_cpustate_to_list(ARMCPU *cpu, bool kvm_sync);
 #define ARM_CPU_TYPE_NAME(name) (name ARM_CPU_TYPE_SUFFIX)
 #define CPU_RESOLVING_TYPE TYPE_ARM_CPU
 
-#define cpu_signal_handler cpu_arm_signal_handler
 #define cpu_list arm_cpu_list
 
 /* ARM has the following "translation regimes" (as the ARM ARM calls them):
diff --git a/target/avr/cpu.h b/target/avr/cpu.h
index 93e3faa0a9..dceacf3cd7 100644
--- a/target/avr/cpu.h
+++ b/target/avr/cpu.h
@@ -175,7 +175,6 @@ static inline void set_avr_feature(CPUAVRState *env, int 
feature)
 }
 
 #define cpu_list avr_cpu_list
-#define cpu_signal_handler cpu_avr_signal_handler
 #define cpu_mmu_index avr_cpu_mmu_index
 
 static inline int avr_cpu_mmu_index(CPUAVRState *env, bool ifetch)
@@ -187,7 +186,6 @@ void avr_cpu_tcg_init(void);
 
 void avr_cpu_list(void);
 int cpu_avr_exec(CPUState *cpu);
-int cpu_avr_signal_handler(int host_signum, void *pinfo, void *puc);
 int avr_cpu_memory_rw_debug(CPUState *cs, vaddr address, uint8_t *buf,
 int len, bool is_write);
 
diff --git a/target/cris/cpu.h b/target/cris/cpu.h
index be021899ae..6603565f83 100644
--- a/target/cris/cpu.h
+++ b/target/cris/cpu.h
@@ -199,12 +199,6 @@ int crisv10_cpu_gdb_read_register(CPUState *cpu, 
GByteArray *buf, int reg);
 int cris_cpu_gdb_read_register(CPUState *cpu, GByteArray *buf, int reg);
 int cris_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg);
 
-/* you can call this signal handler from your SIGBUS and SIGSEGV
-   signal handlers to 

[PULL 00/10] tcg patch queue, v2

2021-09-20 Thread Richard Henderson
Drop has_work patches.
Add a few more misc cleanups.


The following changes since commit 326ff8dd09556fc2e257196c49f35009700794ac:

  Merge remote-tracking branch 'remotes/jasowang/tags/net-pull-request' into 
staging (2021-09-20 16:17:05 +0100)

are available in the Git repository at:

  https://gitlab.com/rth7680/qemu.git tags/pull-tcg-20210920

for you to fetch changes up to b21ba5dfe3f4a367910d490d10fa7c9fa76f1504:

  tcg/riscv: Remove add with zero on user-only memory access (2021-09-20 
14:17:54 -0700)


Move cpu_signal_handler declaration.
Restrict cpu_handle_halt to sysemu.
Make do_unaligned_access noreturn.
Misc tcg/mips cleanup
Misc tcg/sparc cleanup
Misc tcg/riscv cleanup


Philippe Mathieu-Daudé (1):
  accel/tcg: Restrict cpu_handle_halt() to sysemu

Richard Henderson (9):
  include/exec: Move cpu_signal_handler declaration
  tcg/mips: Drop inline markers
  tcg/mips: Allow JAL to be out of range in tcg_out_bswap_subr
  tcg/mips: Unset TCG_TARGET_HAS_direct_jump
  tcg/mips: Drop special alignment for code_gen_buffer
  tcg/sparc: Drop inline markers
  tcg/sparc: Introduce tcg_out_mov_delay
  hw/core: Make do_unaligned_access noreturn
  tcg/riscv: Remove add with zero on user-only memory access

 include/exec/exec-all.h|  13 +
 include/hw/core/tcg-cpu-ops.h  |   3 +-
 target/alpha/cpu.h |  10 +---
 target/arm/cpu.h   |   7 ---
 target/arm/internals.h |   2 +-
 target/avr/cpu.h   |   2 -
 target/cris/cpu.h  |   8 
 target/hexagon/cpu.h   |   3 --
 target/hppa/cpu.h  |   3 --
 target/i386/cpu.h  |   7 ---
 target/m68k/cpu.h  |   8 
 target/microblaze/cpu.h|   9 +---
 target/mips/cpu.h  |   3 --
 target/mips/internal.h |   2 -
 target/mips/tcg/tcg-internal.h |   4 +-
 target/nios2/cpu.h |   6 +--
 target/openrisc/cpu.h  |   2 -
 target/ppc/cpu.h   |   7 ---
 target/ppc/internal.h  |   4 +-
 target/riscv/cpu.h |   4 +-
 target/rx/cpu.h|   4 --
 target/s390x/cpu.h |   7 ---
 target/s390x/s390x-internal.h  |   4 +-
 target/sh4/cpu.h   |   7 +--
 target/sparc/cpu.h |   2 -
 target/tricore/cpu.h   |   2 -
 target/xtensa/cpu.h|   6 +--
 tcg/mips/tcg-target.h  |  12 ++---
 accel/tcg/cpu-exec.c   |   6 ++-
 target/hppa/cpu.c  |   7 +--
 tcg/region.c   |  91 ---
 tcg/mips/tcg-target.c.inc  | 105 ++---
 tcg/riscv/tcg-target.c.inc |  10 +---
 tcg/sparc/tcg-target.c.inc |  64 ++---
 34 files changed, 119 insertions(+), 315 deletions(-)



[PULL 02/10] accel/tcg: Restrict cpu_handle_halt() to sysemu

2021-09-20 Thread Richard Henderson
From: Philippe Mathieu-Daudé 

Commit 372579427a5 ("tcg: enable thread-per-vCPU") added the following
comment describing EXCP_HALTED in qemu_tcg_cpu_thread_fn():

case EXCP_HALTED:
 /* during start-up the vCPU is reset and the thread is
  * kicked several times. If we don't ensure we go back
  * to sleep in the halted state we won't cleanly
  * start-up when the vCPU is enabled.
  *
  * cpu->halted should ensure we sleep in wait_io_event
  */
 g_assert(cpu->halted);
 break;

qemu_wait_io_event() is sysemu-specific, so we can restrict the
cpu_handle_halt() call in cpu_exec() to system emulation.

Signed-off-by: Philippe Mathieu-Daudé 
Reviewed-by: Richard Henderson 
Message-Id: <20210912172731.789788-2-f4...@amsat.org>
Signed-off-by: Richard Henderson 
---
 accel/tcg/cpu-exec.c | 6 --
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/accel/tcg/cpu-exec.c b/accel/tcg/cpu-exec.c
index 75dbc1e4e3..5fd1ed3422 100644
--- a/accel/tcg/cpu-exec.c
+++ b/accel/tcg/cpu-exec.c
@@ -588,8 +588,9 @@ static inline void tb_add_jump(TranslationBlock *tb, int n,
 
 static inline bool cpu_handle_halt(CPUState *cpu)
 {
+#ifndef CONFIG_USER_ONLY
 if (cpu->halted) {
-#if defined(TARGET_I386) && !defined(CONFIG_USER_ONLY)
+#if defined(TARGET_I386)
 if (cpu->interrupt_request & CPU_INTERRUPT_POLL) {
 X86CPU *x86_cpu = X86_CPU(cpu);
 qemu_mutex_lock_iothread();
@@ -597,13 +598,14 @@ static inline bool cpu_handle_halt(CPUState *cpu)
 cpu_reset_interrupt(cpu, CPU_INTERRUPT_POLL);
 qemu_mutex_unlock_iothread();
 }
-#endif
+#endif /* TARGET_I386 */
 if (!cpu_has_work(cpu)) {
 return true;
 }
 
 cpu->halted = 0;
 }
+#endif /* !CONFIG_USER_ONLY */
 
 return false;
 }
-- 
2.25.1




[PULL 06/10] tcg/mips: Drop special alignment for code_gen_buffer

2021-09-20 Thread Richard Henderson
Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/region.c | 91 
 1 file changed, 91 deletions(-)

diff --git a/tcg/region.c b/tcg/region.c
index e64c3ea230..9cc30d4922 100644
--- a/tcg/region.c
+++ b/tcg/region.c
@@ -467,38 +467,6 @@ static size_t tcg_n_regions(size_t tb_size, unsigned 
max_cpus)
   (DEFAULT_CODE_GEN_BUFFER_SIZE_1 < MAX_CODE_GEN_BUFFER_SIZE \
? DEFAULT_CODE_GEN_BUFFER_SIZE_1 : MAX_CODE_GEN_BUFFER_SIZE)
 
-#ifdef __mips__
-/*
- * In order to use J and JAL within the code_gen_buffer, we require
- * that the buffer not cross a 256MB boundary.
- */
-static inline bool cross_256mb(void *addr, size_t size)
-{
-return ((uintptr_t)addr ^ ((uintptr_t)addr + size)) & ~0x0ffful;
-}
-
-/*
- * We weren't able to allocate a buffer without crossing that boundary,
- * so make do with the larger portion of the buffer that doesn't cross.
- * Returns the new base and size of the buffer in *obuf and *osize.
- */
-static inline void split_cross_256mb(void **obuf, size_t *osize,
- void *buf1, size_t size1)
-{
-void *buf2 = (void *)(((uintptr_t)buf1 + size1) & ~0x0ffful);
-size_t size2 = buf1 + size1 - buf2;
-
-size1 = buf2 - buf1;
-if (size1 < size2) {
-size1 = size2;
-buf1 = buf2;
-}
-
-*obuf = buf1;
-*osize = size1;
-}
-#endif
-
 #ifdef USE_STATIC_CODE_GEN_BUFFER
 static uint8_t static_code_gen_buffer[DEFAULT_CODE_GEN_BUFFER_SIZE]
 __attribute__((aligned(CODE_GEN_ALIGN)));
@@ -526,12 +494,6 @@ static int alloc_code_gen_buffer(size_t tb_size, int 
splitwx, Error **errp)
 size = QEMU_ALIGN_DOWN(tb_size, qemu_real_host_page_size);
 }
 
-#ifdef __mips__
-if (cross_256mb(buf, size)) {
-split_cross_256mb(, , buf, size);
-}
-#endif
-
 region.start_aligned = buf;
 region.total_size = size;
 
@@ -573,39 +535,6 @@ static int alloc_code_gen_buffer_anon(size_t size, int 
prot,
 return -1;
 }
 
-#ifdef __mips__
-if (cross_256mb(buf, size)) {
-/*
- * Try again, with the original still mapped, to avoid re-acquiring
- * the same 256mb crossing.
- */
-size_t size2;
-void *buf2 = mmap(NULL, size, prot, flags, -1, 0);
-switch ((int)(buf2 != MAP_FAILED)) {
-case 1:
-if (!cross_256mb(buf2, size)) {
-/* Success!  Use the new buffer.  */
-munmap(buf, size);
-break;
-}
-/* Failure.  Work with what we had.  */
-munmap(buf2, size);
-/* fallthru */
-default:
-/* Split the original buffer.  Free the smaller half.  */
-split_cross_256mb(, , buf, size);
-if (buf == buf2) {
-munmap(buf + size2, size - size2);
-} else {
-munmap(buf, size - size2);
-}
-size = size2;
-break;
-}
-buf = buf2;
-}
-#endif
-
 region.start_aligned = buf;
 region.total_size = size;
 return prot;
@@ -620,35 +549,15 @@ static bool alloc_code_gen_buffer_splitwx_memfd(size_t 
size, Error **errp)
 void *buf_rw = NULL, *buf_rx = MAP_FAILED;
 int fd = -1;
 
-#ifdef __mips__
-/* Find space for the RX mapping, vs the 256MiB regions. */
-if (alloc_code_gen_buffer_anon(size, PROT_NONE,
-   MAP_PRIVATE | MAP_ANONYMOUS |
-   MAP_NORESERVE, errp) < 0) {
-return false;
-}
-/* The size of the mapping may have been adjusted. */
-buf_rx = region.start_aligned;
-size = region.total_size;
-#endif
-
 buf_rw = qemu_memfd_alloc("tcg-jit", size, 0, , errp);
 if (buf_rw == NULL) {
 goto fail;
 }
 
-#ifdef __mips__
-void *tmp = mmap(buf_rx, size, PROT_READ | PROT_EXEC,
- MAP_SHARED | MAP_FIXED, fd, 0);
-if (tmp != buf_rx) {
-goto fail_rx;
-}
-#else
 buf_rx = mmap(NULL, size, PROT_READ | PROT_EXEC, MAP_SHARED, fd, 0);
 if (buf_rx == MAP_FAILED) {
 goto fail_rx;
 }
-#endif
 
 close(fd);
 region.start_aligned = buf_rw;
-- 
2.25.1




[PULL 03/10] tcg/mips: Drop inline markers

2021-09-20 Thread Richard Henderson
Let the compiler decide about inlining.
Remove tcg_out_ext8s and tcg_out_ext16s as unused.

Reviewed-by: Philippe Mathieu-Daudé 
Signed-off-by: Richard Henderson 
---
 tcg/mips/tcg-target.c.inc | 76 ++-
 1 file changed, 27 insertions(+), 49 deletions(-)

diff --git a/tcg/mips/tcg-target.c.inc b/tcg/mips/tcg-target.c.inc
index bf0eb84e2d..320795a637 100644
--- a/tcg/mips/tcg-target.c.inc
+++ b/tcg/mips/tcg-target.c.inc
@@ -187,7 +187,7 @@ static bool patch_reloc(tcg_insn_unit *code_ptr, int type,
 #endif
 
 
-static inline bool is_p2m1(tcg_target_long val)
+static bool is_p2m1(tcg_target_long val)
 {
 return val && ((val + 1) & val) == 0;
 }
@@ -361,8 +361,8 @@ typedef enum {
 /*
  * Type reg
  */
-static inline void tcg_out_opc_reg(TCGContext *s, MIPSInsn opc,
-   TCGReg rd, TCGReg rs, TCGReg rt)
+static void tcg_out_opc_reg(TCGContext *s, MIPSInsn opc,
+TCGReg rd, TCGReg rs, TCGReg rt)
 {
 int32_t inst;
 
@@ -376,8 +376,8 @@ static inline void tcg_out_opc_reg(TCGContext *s, MIPSInsn 
opc,
 /*
  * Type immediate
  */
-static inline void tcg_out_opc_imm(TCGContext *s, MIPSInsn opc,
-   TCGReg rt, TCGReg rs, TCGArg imm)
+static void tcg_out_opc_imm(TCGContext *s, MIPSInsn opc,
+TCGReg rt, TCGReg rs, TCGArg imm)
 {
 int32_t inst;
 
@@ -391,8 +391,8 @@ static inline void tcg_out_opc_imm(TCGContext *s, MIPSInsn 
opc,
 /*
  * Type bitfield
  */
-static inline void tcg_out_opc_bf(TCGContext *s, MIPSInsn opc, TCGReg rt,
-  TCGReg rs, int msb, int lsb)
+static void tcg_out_opc_bf(TCGContext *s, MIPSInsn opc, TCGReg rt,
+   TCGReg rs, int msb, int lsb)
 {
 int32_t inst;
 
@@ -404,8 +404,8 @@ static inline void tcg_out_opc_bf(TCGContext *s, MIPSInsn 
opc, TCGReg rt,
 tcg_out32(s, inst);
 }
 
-static inline void tcg_out_opc_bf64(TCGContext *s, MIPSInsn opc, MIPSInsn opm,
-MIPSInsn oph, TCGReg rt, TCGReg rs,
+static void tcg_out_opc_bf64(TCGContext *s, MIPSInsn opc, MIPSInsn opm,
+ MIPSInsn oph, TCGReg rt, TCGReg rs,
 int msb, int lsb)
 {
 if (lsb >= 32) {
@@ -422,8 +422,7 @@ static inline void tcg_out_opc_bf64(TCGContext *s, MIPSInsn 
opc, MIPSInsn opm,
 /*
  * Type branch
  */
-static inline void tcg_out_opc_br(TCGContext *s, MIPSInsn opc,
-  TCGReg rt, TCGReg rs)
+static void tcg_out_opc_br(TCGContext *s, MIPSInsn opc, TCGReg rt, TCGReg rs)
 {
 tcg_out_opc_imm(s, opc, rt, rs, 0);
 }
@@ -431,8 +430,8 @@ static inline void tcg_out_opc_br(TCGContext *s, MIPSInsn 
opc,
 /*
  * Type sa
  */
-static inline void tcg_out_opc_sa(TCGContext *s, MIPSInsn opc,
-  TCGReg rd, TCGReg rt, TCGArg sa)
+static void tcg_out_opc_sa(TCGContext *s, MIPSInsn opc,
+   TCGReg rd, TCGReg rt, TCGArg sa)
 {
 int32_t inst;
 
@@ -479,28 +478,27 @@ static bool tcg_out_opc_jmp(TCGContext *s, MIPSInsn opc, 
const void *target)
 return true;
 }
 
-static inline void tcg_out_nop(TCGContext *s)
+static void tcg_out_nop(TCGContext *s)
 {
 tcg_out32(s, 0);
 }
 
-static inline void tcg_out_dsll(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
+static void tcg_out_dsll(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
 {
 tcg_out_opc_sa64(s, OPC_DSLL, OPC_DSLL32, rd, rt, sa);
 }
 
-static inline void tcg_out_dsrl(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
+static void tcg_out_dsrl(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
 {
 tcg_out_opc_sa64(s, OPC_DSRL, OPC_DSRL32, rd, rt, sa);
 }
 
-static inline void tcg_out_dsra(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
+static void tcg_out_dsra(TCGContext *s, TCGReg rd, TCGReg rt, TCGArg sa)
 {
 tcg_out_opc_sa64(s, OPC_DSRA, OPC_DSRA32, rd, rt, sa);
 }
 
-static inline bool tcg_out_mov(TCGContext *s, TCGType type,
-   TCGReg ret, TCGReg arg)
+static bool tcg_out_mov(TCGContext *s, TCGType type, TCGReg ret, TCGReg arg)
 {
 /* Simple reg-reg move, optimising out the 'do nothing' case */
 if (ret != arg) {
@@ -612,27 +610,7 @@ static void tcg_out_bswap64(TCGContext *s, TCGReg ret, 
TCGReg arg)
 }
 }
 
-static inline void tcg_out_ext8s(TCGContext *s, TCGReg ret, TCGReg arg)
-{
-if (use_mips32r2_instructions) {
-tcg_out_opc_reg(s, OPC_SEB, ret, 0, arg);
-} else {
-tcg_out_opc_sa(s, OPC_SLL, ret, arg, 24);
-tcg_out_opc_sa(s, OPC_SRA, ret, ret, 24);
-}
-}
-
-static inline void tcg_out_ext16s(TCGContext *s, TCGReg ret, TCGReg arg)
-{
-if (use_mips32r2_instructions) {
-tcg_out_opc_reg(s, OPC_SEH, ret, 0, arg);
-} else {
-tcg_out_opc_sa(s, OPC_SLL, ret, arg, 16);
-tcg_out_opc_sa(s, OPC_SRA, ret, ret, 16);
-}
-}
-
-static inline void tcg_out_ext32u(TCGContext 

[PATCH v3] target/riscv: Set mstatus_hs.[SD|FS] bits if Clean and V=1 in mark_fs_dirty()

2021-09-20 Thread frank . chang
From: Frank Chang 

When V=1, both vsstauts.FS and HS-level sstatus.FS are in effect.
Modifying the floating-point state when V=1 causes both fields to
be set to 3 (Dirty).

However, it's possible that HS-level sstatus.FS is Clean and VS-level
vsstatus.FS is Dirty at the time mark_fs_dirty() is called when V=1.
We can't early return for this case because we still need to set
sstatus.FS to Dirty according to spec.

Signed-off-by: Frank Chang 
Reviewed-by: Vincent Chen 
Tested-by: Vincent Chen 
Reviewed-by: Richard Henderson 
---
 target/riscv/cpu.h   |  4 
 target/riscv/translate.c | 30 +-
 2 files changed, 21 insertions(+), 13 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index e735e53e26c..bef7c551646 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -394,6 +394,7 @@ FIELD(TB_FLAGS, SEW, 5, 3)
 FIELD(TB_FLAGS, VILL, 8, 1)
 /* Is a Hypervisor instruction load/store allowed? */
 FIELD(TB_FLAGS, HLSX, 9, 1)
+FIELD(TB_FLAGS, MSTATUS_HS_FS, 10, 2)
 
 bool riscv_cpu_is_32bit(CPURISCVState *env);
 
@@ -450,6 +451,9 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, 
target_ulong *pc,
 get_field(env->hstatus, HSTATUS_HU))) {
 flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
 }
+
+flags = FIELD_DP32(flags, TB_FLAGS, MSTATUS_HS_FS,
+   get_field(env->mstatus_hs, MSTATUS_FS));
 }
 #endif
 
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 74b33fa3c90..6be22347426 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -58,6 +58,7 @@ typedef struct DisasContext {
 target_ulong misa;
 uint32_t opcode;
 uint32_t mstatus_fs;
+uint32_t mstatus_hs_fs;
 uint32_t mem_idx;
 /* Remember the rounding mode encoded in the previous fp instruction,
which we have already installed into env->fp_status.  Or -1 for
@@ -280,27 +281,29 @@ static void gen_jal(DisasContext *ctx, int rd, 
target_ulong imm)
 static void mark_fs_dirty(DisasContext *ctx)
 {
 TCGv tmp;
-target_ulong sd;
+target_ulong sd = is_32bit(ctx) ? MSTATUS32_SD : MSTATUS64_SD;
 
-if (ctx->mstatus_fs == MSTATUS_FS) {
-return;
-}
-/* Remember the state change for the rest of the TB.  */
-ctx->mstatus_fs = MSTATUS_FS;
+if (ctx->mstatus_fs != MSTATUS_FS) {
+/* Remember the state change for the rest of the TB. */
+ctx->mstatus_fs = MSTATUS_FS;
 
-tmp = tcg_temp_new();
-sd = is_32bit(ctx) ? MSTATUS32_SD : MSTATUS64_SD;
+tmp = tcg_temp_new();
+tcg_gen_ld_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus));
+tcg_gen_ori_tl(tmp, tmp, MSTATUS_FS | sd);
+tcg_gen_st_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus));
+tcg_temp_free(tmp);
+}
 
-tcg_gen_ld_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus));
-tcg_gen_ori_tl(tmp, tmp, MSTATUS_FS | sd);
-tcg_gen_st_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus));
+if (ctx->virt_enabled && ctx->mstatus_hs_fs != MSTATUS_FS) {
+/* Remember the stage change for the rest of the TB. */
+ctx->mstatus_hs_fs = MSTATUS_FS;
 
-if (ctx->virt_enabled) {
+tmp = tcg_temp_new();
 tcg_gen_ld_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus_hs));
 tcg_gen_ori_tl(tmp, tmp, MSTATUS_FS | sd);
 tcg_gen_st_tl(tmp, cpu_env, offsetof(CPURISCVState, mstatus_hs));
+tcg_temp_free(tmp);
 }
-tcg_temp_free(tmp);
 }
 #else
 static inline void mark_fs_dirty(DisasContext *ctx) { }
@@ -533,6 +536,7 @@ static void riscv_tr_init_disas_context(DisasContextBase 
*dcbase, CPUState *cs)
 ctx->frm = -1;  /* unknown rounding mode */
 ctx->ext_ifencei = cpu->cfg.ext_ifencei;
 ctx->vlen = cpu->cfg.vlen;
+ctx->mstatus_hs_fs = FIELD_EX32(tb_flags, TB_FLAGS, MSTATUS_HS_FS);
 ctx->hlsx = FIELD_EX32(tb_flags, TB_FLAGS, HLSX);
 ctx->vill = FIELD_EX32(tb_flags, TB_FLAGS, VILL);
 ctx->sew = FIELD_EX32(tb_flags, TB_FLAGS, SEW);
-- 
2.25.1




Re: [PATCH v3 23/30] Hexagon HVX (target/hexagon) helper overrides - vector stores

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 218 +++
  target/hexagon/helper.h  |   1 +
  target/hexagon/op_helper.c   |   5 +
  3 files changed, 224 insertions(+)


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 25/30] Hexagon HVX (target/hexagon) instruction decoding

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Add new file to target/hexagon/meson.build

Signed-off-by: Taylor Simpson
---
  target/hexagon/mmvec/decode_ext_mmvec.h |  24 
  target/hexagon/decode.c |  24 +++-
  target/hexagon/mmvec/decode_ext_mmvec.c | 236 
  target/hexagon/meson.build  |   1 +
  4 files changed, 283 insertions(+), 2 deletions(-)
  create mode 100644 target/hexagon/mmvec/decode_ext_mmvec.h
  create mode 100644 target/hexagon/mmvec/decode_ext_mmvec.c


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 24/30] Hexagon HVX (target/hexagon) import semantics

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Imported from the Hexagon architecture library
 imported/allext.idef   Top level file for all extensions
 imported/mmvec/ext.idefHVX instruction definitions

Support functions added to target/hexagon/genptr.c


Acked-by: Richard Henderson 



Re: [PATCH v3 22/30] Hexagon HVX (target/hexagon) helper overrides - vector loads

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 150 +++
  1 file changed, 150 insertions(+)


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 21/30] Hexagon HVX (target/hexagon) helper overrides - vector splat and abs

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 26 ++
  1 file changed, 26 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v3 20/30] Hexagon HVX (target/hexagon) helper overrides - vector compares

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 103 +++
  1 file changed, 103 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v3 19/30] Hexagon HVX (target/hexagon) helper overrides - vector logical ops

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

+#define fGEN_TCG_V6_pred_xor(SHORTCODE) \
+tcg_gen_gvec_xor(MO_64, QdV_off, QsV_off, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg))
+
+#define fGEN_TCG_V6_pred_or_n(SHORTCODE) \
+do { \
+intptr_t tmpoff = offsetof(CPUHexagonState, qtmp); \
+tcg_gen_gvec_not(MO_64, tmpoff, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+tcg_gen_gvec_or(MO_64, QdV_off, QsV_off, tmpoff, \
+sizeof(MMQReg), sizeof(MMQReg)); \
+} while (0)


tcg_gen_gvec_orc.


+#define fGEN_TCG_V6_pred_and_n(SHORTCODE) \
+do { \
+intptr_t tmpoff = offsetof(CPUHexagonState, qtmp); \
+tcg_gen_gvec_not(MO_64, tmpoff, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+tcg_gen_gvec_and(MO_64, QdV_off, QsV_off, tmpoff, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+} while (0)


tcg_gen_gvec_andc.


r~



Re: [PATCH v3 18/30] Hexagon HVX (target/hexagon) helper overrides - vector max/min

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 34 ++
  1 file changed, 34 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v3 17/30] Hexagon HVX (target/hexagon) helper overrides - vector shifts

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 122 +++
  1 file changed, 122 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v3 15/30] Hexagon HVX (target/hexagon) helper overrides - vector assign & cmov

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 31 +++
  1 file changed, 31 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v3 16/30] Hexagon HVX (target/hexagon) helper overrides - vector add & sub

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_tcg_hvx.h | 50 
  1 file changed, 50 insertions(+)


Reviewed-by: Richard Henderson 

r~



Re: [PATCH v2 0/9] optimize the downtime for vfio migration

2021-09-20 Thread Longpeng (Mike, Cloud Infrastructure Service Product Dept.)
Hi guys,

Ping...

I just sent out V3, please review on V3, thanks!


在 2021/9/9 14:06, Longpeng(Mike) 写道:
> Hi guys,
> 
> In vfio migration resume phase, the cost would increase if the
> vfio device has more unmasked vectors. We try to optimize it in
> this series.
> 
> You can see the commit message in PATCH 9 for details.
> 
> Patch 1-5 are simple cleanups and fixup.
> Patch 6-8 are the preparations for the optimization.
> Patch 9 optimizes the vfio msix setup path.
> 
> Changes v1->v2:
>  - fix several typos and grammatical errors [Alex, Philippe]
>  - split fixups and cleanups into separate patches  [Alex, Philippe]
>  - introduce kvm_irqchip_add_deferred_msi_route to
>minimize code changes[Alex]
>  - enable the optimization in msi setup path[Alex]
> 
> Longpeng (Mike) (9):
>   vfio: simplify the conditional statements in vfio_msi_enable
>   vfio: move re-enabling INTX out of the common helper
>   vfio: simplify the failure path in vfio_msi_enable
>   msix: simplify the conditional in msix_set/unset_vector_notifiers
>   msix: reset poll_notifier to NULL if fail to set notifiers
>   kvm: irqchip: extract kvm_irqchip_add_deferred_msi_route
>   vfio: add infrastructure to commit the deferred kvm routing
>   Revert "vfio: Avoid disabling and enabling vectors repeatedly in VFIO
> migration"
>   vfio: defer to commit kvm irq routing when enable msi/msix
> 
>  accel/kvm/kvm-all.c  |  15 ++-
>  hw/pci/msix.c|   7 ++-
>  hw/vfio/pci.c| 125 
> +--
>  hw/vfio/pci.h|   1 +
>  include/sysemu/kvm.h |   6 +++
>  5 files changed, 105 insertions(+), 49 deletions(-)
> 



[PATCH v3 9/9] vfio: defer to commit kvm irq routing when enable msi/msix

2021-09-20 Thread Longpeng(Mike)
In migration resume phase, all unmasked msix vectors need to be
setup when load the VF state. However, the setup operation would
take longer if the VM has more VFs and each VF has more unmasked
vectors.

The hot spot is kvm_irqchip_commit_routes, it'll scan and update
all irqfds that already assigned each invocation, so more vectors
means need more time to process them.

vfio_pci_load_config
  vfio_msix_enable
msix_set_vector_notifiers
  for (vector = 0; vector < dev->msix_entries_nr; vector++) {
vfio_msix_vector_do_use
  vfio_add_kvm_msi_virq
kvm_irqchip_commit_routes <-- expensive
  }

We can reduce the cost by only commit once outside the loop. The
routes is cached in kvm_state, we commit them first and then bind
irqfd for each vector.

The test VM has 128 vcpus and 8 VF (each one has 65 vectors),
we measure the cost of the vfio_msix_enable for each VF, and
we can see 90+% costs can be reduce.

VF  Count of irqfds[*]  OriginalWith this patch

1st   658   2
2nd   130   15  2
3rd   195   22  2
4th   260   24  3
5th   325   36  2
6th   390   44  3
7th   455   51  3
8th   520   58  4
Total   258ms   21ms

[*] Count of irqfds
How many irqfds that already assigned and need to process in this
round.

The optimition can be applied to msi type too.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 36 
 1 file changed, 28 insertions(+), 8 deletions(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index 2de1cc5425..b26129bddf 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -513,11 +513,13 @@ static int vfio_msix_vector_do_use(PCIDevice *pdev, 
unsigned int nr,
  * increase them as needed.
  */
 if (vdev->nr_vectors < nr + 1) {
-vfio_disable_irqindex(>vbasedev, VFIO_PCI_MSIX_IRQ_INDEX);
 vdev->nr_vectors = nr + 1;
-ret = vfio_enable_vectors(vdev, true);
-if (ret) {
-error_report("vfio: failed to enable vectors, %d", ret);
+if (!vdev->defer_kvm_irq_routing) {
+vfio_disable_irqindex(>vbasedev, VFIO_PCI_MSIX_IRQ_INDEX);
+ret = vfio_enable_vectors(vdev, true);
+if (ret) {
+error_report("vfio: failed to enable vectors, %d", ret);
+}
 }
 } else {
 Error *err = NULL;
@@ -579,8 +581,7 @@ static void vfio_msix_vector_release(PCIDevice *pdev, 
unsigned int nr)
 }
 }
 
-/* TODO: invoked when enclabe msi/msix vectors */
-static __attribute__((unused)) void vfio_commit_kvm_msi_virq(VFIOPCIDevice 
*vdev)
+static void vfio_commit_kvm_msi_virq(VFIOPCIDevice *vdev)
 {
 int i;
 VFIOMSIVector *vector;
@@ -610,6 +611,9 @@ static __attribute__((unused)) void 
vfio_commit_kvm_msi_virq(VFIOPCIDevice *vdev
 
 static void vfio_msix_enable(VFIOPCIDevice *vdev)
 {
+PCIDevice *pdev = >pdev;
+int ret;
+
 vfio_disable_interrupts(vdev);
 
 vdev->msi_vectors = g_new0(VFIOMSIVector, vdev->msix->entries);
@@ -632,11 +636,22 @@ static void vfio_msix_enable(VFIOPCIDevice *vdev)
 vfio_msix_vector_do_use(>pdev, 0, NULL, NULL);
 vfio_msix_vector_release(>pdev, 0);
 
-if (msix_set_vector_notifiers(>pdev, vfio_msix_vector_use,
-  vfio_msix_vector_release, NULL)) {
+vdev->defer_kvm_irq_routing = true;
+
+ret = msix_set_vector_notifiers(>pdev, vfio_msix_vector_use,
+vfio_msix_vector_release, NULL);
+if (ret < 0) {
 error_report("vfio: msix_set_vector_notifiers failed");
+} else if (!pdev->msix_function_masked) {
+vfio_commit_kvm_msi_virq(vdev);
+vfio_disable_irqindex(>vbasedev, VFIO_PCI_MSIX_IRQ_INDEX);
+ret = vfio_enable_vectors(vdev, true);
+if (ret) {
+error_report("vfio: failed to enable vectors, %d", ret);
+}
 }
 
+vdev->defer_kvm_irq_routing = false;
 trace_vfio_msix_enable(vdev->vbasedev.name);
 }
 
@@ -645,6 +660,7 @@ static void vfio_msi_enable(VFIOPCIDevice *vdev)
 int ret, i;
 
 vfio_disable_interrupts(vdev);
+vdev->defer_kvm_irq_routing = true;
 
 vdev->nr_vectors = msi_nr_vectors_allocated(>pdev);
 retry:
@@ -671,6 +687,8 @@ retry:
 vfio_add_kvm_msi_virq(vdev, vector, i, false);
 }
 
+vfio_commit_kvm_msi_virq(vdev);
+
 /* Set interrupt type prior to possible interrupts */
 vdev->interrupt = VFIO_INT_MSI;
 
@@ -697,9 +715,11 @@ retry:
  */
 error_report("vfio: Error: Failed to enable MSI");
 
+vdev->defer_kvm_irq_routing = false;
 return;
 }
 
+vdev->defer_kvm_irq_routing = false;
 trace_vfio_msi_enable(vdev->vbasedev.name, vdev->nr_vectors);
 }
 
-- 
2.23.0




[PATCH v3 7/9] vfio: add infrastructure to commit the deferred kvm routing

2021-09-20 Thread Longpeng(Mike)
'defer_kvm_irq_routing' indicates whether we should defer to commit
the kvm routing.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 43 ++-
 hw/vfio/pci.h |  1 +
 2 files changed, 43 insertions(+), 1 deletion(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index 8e97ca93cf..8fe238b11d 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -423,12 +423,24 @@ static void vfio_add_kvm_msi_virq(VFIOPCIDevice *vdev, 
VFIOMSIVector *vector,
 return;
 }
 
-virq = kvm_irqchip_add_msi_route(kvm_state, vector_n, >pdev);
+virq = kvm_irqchip_add_deferred_msi_route(kvm_state, vector_n, 
>pdev);
 if (virq < 0) {
 event_notifier_cleanup(>kvm_interrupt);
 return;
 }
 
+if (vdev->defer_kvm_irq_routing) {
+/*
+ * Hold the allocated virq in vector->virq temporarily, will
+ * reset it to -1 when we fail to add the corresponding irqfd
+ * in vfio_commit_kvm_msi_virq().
+ */
+vector->virq = virq;
+return;
+}
+
+kvm_irqchip_commit_routes(kvm_state);
+
 if (kvm_irqchip_add_irqfd_notifier_gsi(kvm_state, >kvm_interrupt,
NULL, virq) < 0) {
 kvm_irqchip_release_virq(kvm_state, virq);
@@ -567,6 +579,35 @@ static void vfio_msix_vector_release(PCIDevice *pdev, 
unsigned int nr)
 }
 }
 
+/* TODO: invoked when enclabe msi/msix vectors */
+static __attribute__((unused)) void vfio_commit_kvm_msi_virq(VFIOPCIDevice 
*vdev)
+{
+int i;
+VFIOMSIVector *vector;
+
+if (!vdev->defer_kvm_irq_routing || !vdev->nr_vectors) {
+return;
+}
+
+kvm_irqchip_commit_routes(kvm_state);
+
+for (i = 0; i < vdev->nr_vectors; i++) {
+vector = >msi_vectors[i];
+
+if (!vector->use || vector->virq < 0) {
+continue;
+}
+
+if (kvm_irqchip_add_irqfd_notifier_gsi(kvm_state,
+   >kvm_interrupt,
+   NULL, vector->virq) < 0) {
+kvm_irqchip_release_virq(kvm_state, vector->virq);
+event_notifier_cleanup(>kvm_interrupt);
+vector->virq = -1;
+}
+}
+}
+
 static void vfio_msix_enable(VFIOPCIDevice *vdev)
 {
 PCIDevice *pdev = >pdev;
diff --git a/hw/vfio/pci.h b/hw/vfio/pci.h
index 64777516d1..d3c5177d37 100644
--- a/hw/vfio/pci.h
+++ b/hw/vfio/pci.h
@@ -171,6 +171,7 @@ struct VFIOPCIDevice {
 bool no_kvm_ioeventfd;
 bool no_vfio_ioeventfd;
 bool enable_ramfb;
+bool defer_kvm_irq_routing;
 VFIODisplay *dpy;
 Notifier irqchip_change_notifier;
 };
-- 
2.23.0




Re: [PATCH v3 08/30] Hexagon HVX (target/hexagon) semantics generator - part 2

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_helper_funcs.py  | 112 ++--
  target/hexagon/gen_helper_protos.py |  16 ++-
  target/hexagon/gen_tcg_funcs.py | 258 ++--
  3 files changed, 364 insertions(+), 22 deletions(-)


Acked-by: Richard Henderson 



[PATCH v3 4/9] msix: simplify the conditional in msix_set/unset_vector_notifiers

2021-09-20 Thread Longpeng(Mike)
'msix_function_masked' is synchronized with the device's config,
we can use it to replace the complex conditional statementis in
msix_set/unset_vector_notifiers.

Signed-off-by: Longpeng(Mike) 
---
 hw/pci/msix.c | 6 ++
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/hw/pci/msix.c b/hw/pci/msix.c
index ae9331cd0b..67682289af 100644
--- a/hw/pci/msix.c
+++ b/hw/pci/msix.c
@@ -592,8 +592,7 @@ int msix_set_vector_notifiers(PCIDevice *dev,
 dev->msix_vector_release_notifier = release_notifier;
 dev->msix_vector_poll_notifier = poll_notifier;
 
-if ((dev->config[dev->msix_cap + MSIX_CONTROL_OFFSET] &
-(MSIX_ENABLE_MASK | MSIX_MASKALL_MASK)) == MSIX_ENABLE_MASK) {
+if (!dev->msix_function_masked) {
 for (vector = 0; vector < dev->msix_entries_nr; vector++) {
 ret = msix_set_notifier_for_vector(dev, vector);
 if (ret < 0) {
@@ -622,8 +621,7 @@ void msix_unset_vector_notifiers(PCIDevice *dev)
 assert(dev->msix_vector_use_notifier &&
dev->msix_vector_release_notifier);
 
-if ((dev->config[dev->msix_cap + MSIX_CONTROL_OFFSET] &
-(MSIX_ENABLE_MASK | MSIX_MASKALL_MASK)) == MSIX_ENABLE_MASK) {
+if (!dev->msix_function_masked) {
 for (vector = 0; vector < dev->msix_entries_nr; vector++) {
 msix_unset_notifier_for_vector(dev, vector);
 }
-- 
2.23.0




[PATCH v3 2/9] vfio: move re-enabling INTX out of the common helper

2021-09-20 Thread Longpeng(Mike)
Move re-enabling INTX out, and the callers should decide to
re-enable it or not.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 17 +++--
 1 file changed, 11 insertions(+), 6 deletions(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index f7a3a13fb0..1e6797fd4b 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -690,7 +690,6 @@ retry:
 
 static void vfio_msi_disable_common(VFIOPCIDevice *vdev)
 {
-Error *err = NULL;
 int i;
 
 for (i = 0; i < vdev->nr_vectors; i++) {
@@ -709,15 +708,11 @@ static void vfio_msi_disable_common(VFIOPCIDevice *vdev)
 vdev->msi_vectors = NULL;
 vdev->nr_vectors = 0;
 vdev->interrupt = VFIO_INT_NONE;
-
-vfio_intx_enable(vdev, );
-if (err) {
-error_reportf_err(err, VFIO_MSG_PREFIX, vdev->vbasedev.name);
-}
 }
 
 static void vfio_msix_disable(VFIOPCIDevice *vdev)
 {
+Error *err = NULL;
 int i;
 
 msix_unset_vector_notifiers(>pdev);
@@ -738,6 +733,10 @@ static void vfio_msix_disable(VFIOPCIDevice *vdev)
 }
 
 vfio_msi_disable_common(vdev);
+vfio_intx_enable(vdev, );
+if (err) {
+error_reportf_err(err, VFIO_MSG_PREFIX, vdev->vbasedev.name);
+}
 
 memset(vdev->msix->pending, 0,
BITS_TO_LONGS(vdev->msix->entries) * sizeof(unsigned long));
@@ -747,8 +746,14 @@ static void vfio_msix_disable(VFIOPCIDevice *vdev)
 
 static void vfio_msi_disable(VFIOPCIDevice *vdev)
 {
+Error *err = NULL;
+
 vfio_disable_irqindex(>vbasedev, VFIO_PCI_MSI_IRQ_INDEX);
 vfio_msi_disable_common(vdev);
+vfio_intx_enable(vdev, );
+if (err) {
+error_reportf_err(err, VFIO_MSG_PREFIX, vdev->vbasedev.name);
+}
 
 trace_vfio_msi_disable(vdev->vbasedev.name);
 }
-- 
2.23.0




Re: [PATCH v3 09/30] Hexagon HVX (target/hexagon) C preprocessor for decode tree

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_dectree_import.c | 13 +
  1 file changed, 13 insertions(+)


Acked-by: Richard Henderson 

r~



[PATCH v3 1/9] vfio: simplify the conditional statements in vfio_msi_enable

2021-09-20 Thread Longpeng(Mike)
It's unnecessary to test against the specific return value of
VFIO_DEVICE_SET_IRQS, since any positive return is an error
indicating the number of vectors we should retry with.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index e1ea1d8a23..f7a3a13fb0 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -650,7 +650,7 @@ retry:
 if (ret) {
 if (ret < 0) {
 error_report("vfio: Error: Failed to setup MSI fds: %m");
-} else if (ret != vdev->nr_vectors) {
+} else {
 error_report("vfio: Error: Failed to enable %d "
  "MSI vectors, retry with %d", vdev->nr_vectors, ret);
 }
@@ -668,7 +668,7 @@ retry:
 g_free(vdev->msi_vectors);
 vdev->msi_vectors = NULL;
 
-if (ret > 0 && ret != vdev->nr_vectors) {
+if (ret > 0) {
 vdev->nr_vectors = ret;
 goto retry;
 }
-- 
2.23.0




[PATCH v3 0/9] optimize the downtime for vfio migration

2021-09-20 Thread Longpeng(Mike)
Hi guys,

In vfio migration resume phase, the cost would increase if the
vfio device has more unmasked vectors. We try to optimize it in
this series.

You can see the commit message in PATCH 9 for details.

Patch 1-5 are simple cleanups and fixup.
Patch 6-8 are the preparations for the optimization.
Patch 9 optimizes the vfio msix setup path.

Changes v2->v3:
 - fix two errors [Longpeng]

Changes v1->v2:
 - fix several typos and grammatical errors [Alex, Philippe]
 - split fixups and cleanups into separate patches  [Alex, Philippe]
 - introduce kvm_irqchip_add_deferred_msi_route to
   minimize code changes[Alex]
 - enable the optimization in msi setup path[Alex]

Longpeng (Mike) (9):
  vfio: simplify the conditional statements in vfio_msi_enable
  vfio: move re-enabling INTX out of the common helper
  vfio: simplify the failure path in vfio_msi_enable
  msix: simplify the conditional in msix_set/unset_vector_notifiers
  msix: reset poll_notifier to NULL if fail to set notifiers
  kvm: irqchip: extract kvm_irqchip_add_deferred_msi_route
  vfio: add infrastructure to commit the deferred kvm routing
  Revert "vfio: Avoid disabling and enabling vectors repeatedly in VFIO
migration"
  vfio: defer to commit kvm irq routing when enable msi/msix

 accel/kvm/kvm-all.c  |  15 +-
 hw/pci/msix.c|   7 ++-
 hw/vfio/pci.c| 126 ---
 hw/vfio/pci.h|   1 +
 include/sysemu/kvm.h |   6 +++
 5 files changed, 106 insertions(+), 49 deletions(-)

-- 
2.23.0




[PATCH v3 8/9] Revert "vfio: Avoid disabling and enabling vectors repeatedly in VFIO migration"

2021-09-20 Thread Longpeng(Mike)
Commit ecebe53fe993 ("vfio: Avoid disabling and enabling vectors
repeatedly in VFIO migration") avoid inefficiently disabling and
enabling vectors repeatedly and let the unmasked vectors to be
enabled one by one.

But we want to batch multiple routes and defer the commit, and only
commit once out side the loop of setting vector notifiers, so we
cannot to enable the vectors one by one in the loop now.

Revert that commit and we will take another way in the next patch,
it can not only avoid disabling/enabling vectors repeatedly, but
also satisfy our requirement of defer to commit.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 20 +++-
 1 file changed, 3 insertions(+), 17 deletions(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index 8fe238b11d..2de1cc5425 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -610,9 +610,6 @@ static __attribute__((unused)) void 
vfio_commit_kvm_msi_virq(VFIOPCIDevice *vdev
 
 static void vfio_msix_enable(VFIOPCIDevice *vdev)
 {
-PCIDevice *pdev = >pdev;
-unsigned int nr, max_vec = 0;
-
 vfio_disable_interrupts(vdev);
 
 vdev->msi_vectors = g_new0(VFIOMSIVector, vdev->msix->entries);
@@ -631,22 +628,11 @@ static void vfio_msix_enable(VFIOPCIDevice *vdev)
  * triggering to userspace, then immediately release the vector, leaving
  * the physical device with no vectors enabled, but MSI-X enabled, just
  * like the guest view.
- * If there are already unmasked vectors (in migration resume phase and
- * some guest startups) which will be enabled soon, we can allocate all
- * of them here to avoid inefficiently disabling and enabling vectors
- * repeatedly later.
  */
-if (!pdev->msix_function_masked) {
-for (nr = 0; nr < msix_nr_vectors_allocated(pdev); nr++) {
-if (!msix_is_masked(pdev, nr)) {
-max_vec = nr;
-}
-}
-}
-vfio_msix_vector_do_use(pdev, max_vec, NULL, NULL);
-vfio_msix_vector_release(pdev, max_vec);
+vfio_msix_vector_do_use(>pdev, 0, NULL, NULL);
+vfio_msix_vector_release(>pdev, 0);
 
-if (msix_set_vector_notifiers(pdev, vfio_msix_vector_use,
+if (msix_set_vector_notifiers(>pdev, vfio_msix_vector_use,
   vfio_msix_vector_release, NULL)) {
 error_report("vfio: msix_set_vector_notifiers failed");
 }
-- 
2.23.0




[PATCH v3 5/9] msix: reset poll_notifier to NULL if fail to set notifiers

2021-09-20 Thread Longpeng(Mike)
'msix_vector_poll_notifier' should be reset to NULL in the error
path in msix_set_vector_notifiers().

Signed-off-by: Longpeng(Mike) 
---
 hw/pci/msix.c | 1 +
 1 file changed, 1 insertion(+)

diff --git a/hw/pci/msix.c b/hw/pci/msix.c
index 67682289af..805770942b 100644
--- a/hw/pci/msix.c
+++ b/hw/pci/msix.c
@@ -611,6 +611,7 @@ undo:
 }
 dev->msix_vector_use_notifier = NULL;
 dev->msix_vector_release_notifier = NULL;
+dev->msix_vector_poll_notifier = NULL;
 return ret;
 }
 
-- 
2.23.0




[PATCH v3 6/9] kvm: irqchip: extract kvm_irqchip_add_deferred_msi_route

2021-09-20 Thread Longpeng(Mike)
Extract a common helper that add MSI route for specific vector
but does not commit immediately.

Signed-off-by: Longpeng(Mike) 
---
 accel/kvm/kvm-all.c  | 15 +--
 include/sysemu/kvm.h |  6 ++
 2 files changed, 19 insertions(+), 2 deletions(-)

diff --git a/accel/kvm/kvm-all.c b/accel/kvm/kvm-all.c
index e5b10dd129..d603afc44c 100644
--- a/accel/kvm/kvm-all.c
+++ b/accel/kvm/kvm-all.c
@@ -1950,7 +1950,7 @@ int kvm_irqchip_send_msi(KVMState *s, MSIMessage msg)
 return kvm_set_irq(s, route->kroute.gsi, 1);
 }
 
-int kvm_irqchip_add_msi_route(KVMState *s, int vector, PCIDevice *dev)
+int kvm_irqchip_add_deferred_msi_route(KVMState *s, int vector, PCIDevice *dev)
 {
 struct kvm_irq_routing_entry kroute = {};
 int virq;
@@ -1993,7 +1993,18 @@ int kvm_irqchip_add_msi_route(KVMState *s, int vector, 
PCIDevice *dev)
 
 kvm_add_routing_entry(s, );
 kvm_arch_add_msi_route_post(, vector, dev);
-kvm_irqchip_commit_routes(s);
+
+return virq;
+}
+
+int kvm_irqchip_add_msi_route(KVMState *s, int vector, PCIDevice *dev)
+{
+int virq;
+
+virq = kvm_irqchip_add_deferred_msi_route(s, vector, dev);
+if (virq >= 0) {
+kvm_irqchip_commit_routes(s);
+}
 
 return virq;
 }
diff --git a/include/sysemu/kvm.h b/include/sysemu/kvm.h
index a1ab1ee12d..8de0d9a715 100644
--- a/include/sysemu/kvm.h
+++ b/include/sysemu/kvm.h
@@ -476,6 +476,12 @@ void kvm_init_cpu_signals(CPUState *cpu);
  * @return: virq (>=0) when success, errno (<0) when failed.
  */
 int kvm_irqchip_add_msi_route(KVMState *s, int vector, PCIDevice *dev);
+/**
+ * Add MSI route for specific vector but does not commit to KVM
+ * immediately
+ */
+int kvm_irqchip_add_deferred_msi_route(KVMState *s, int vector,
+   PCIDevice *dev);
 int kvm_irqchip_update_msi_route(KVMState *s, int virq, MSIMessage msg,
  PCIDevice *dev);
 void kvm_irqchip_commit_routes(KVMState *s);
-- 
2.23.0




[PATCH v3 3/9] vfio: simplify the failure path in vfio_msi_enable

2021-09-20 Thread Longpeng(Mike)
Use vfio_msi_disable_common to simplify the error handling
in vfio_msi_enable.

Signed-off-by: Longpeng(Mike) 
---
 hw/vfio/pci.c | 16 ++--
 1 file changed, 2 insertions(+), 14 deletions(-)

diff --git a/hw/vfio/pci.c b/hw/vfio/pci.c
index 1e6797fd4b..8e97ca93cf 100644
--- a/hw/vfio/pci.c
+++ b/hw/vfio/pci.c
@@ -47,6 +47,7 @@
 
 static void vfio_disable_interrupts(VFIOPCIDevice *vdev);
 static void vfio_mmap_set_enabled(VFIOPCIDevice *vdev, bool enabled);
+static void vfio_msi_disable_common(VFIOPCIDevice *vdev);
 
 /*
  * Disabling BAR mmaping can be slow, but toggling it around INTx can
@@ -655,24 +656,12 @@ retry:
  "MSI vectors, retry with %d", vdev->nr_vectors, ret);
 }
 
-for (i = 0; i < vdev->nr_vectors; i++) {
-VFIOMSIVector *vector = >msi_vectors[i];
-if (vector->virq >= 0) {
-vfio_remove_kvm_msi_virq(vector);
-}
-qemu_set_fd_handler(event_notifier_get_fd(>interrupt),
-NULL, NULL, NULL);
-event_notifier_cleanup(>interrupt);
-}
-
-g_free(vdev->msi_vectors);
-vdev->msi_vectors = NULL;
+vfio_msi_disable_common(vdev);
 
 if (ret > 0) {
 vdev->nr_vectors = ret;
 goto retry;
 }
-vdev->nr_vectors = 0;
 
 /*
  * Failing to setup MSI doesn't really fall within any specification.
@@ -680,7 +669,6 @@ retry:
  * out to fall back to INTx for this device.
  */
 error_report("vfio: Error: Failed to enable MSI");
-vdev->interrupt = VFIO_INT_NONE;
 
 return;
 }
-- 
2.23.0




Re: [PATCH v3 07/30] Hexagon HVX (target/hexagon) semantics generator

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Add HVX support to the semantics generator

Signed-off-by: Taylor Simpson
---
  target/hexagon/gen_semantics.c | 33 +
  target/hexagon/hex_common.py   | 13 +
  2 files changed, 46 insertions(+)


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 06/30] Hexagon HVX (target/hexagon) import macro definitions

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

Imported from the Hexagon architecture library
 imported/allext_macros.def   Top level macro include for all extensions
 imported/macros.def  Scalar core macros (some HVX here)
 imported/mmvec/macros.defHVX macro definitions
The macro definition files specify instruction attributes that are applied
to each instruction that reverences the macro.

Signed-off-by: Taylor Simpson
---
  target/hexagon/imported/allext_macros.def |  25 +
  target/hexagon/imported/macros.def|  88 
  target/hexagon/imported/mmvec/macros.def  | 842 ++
  3 files changed, 955 insertions(+)
  create mode 100644 target/hexagon/imported/allext_macros.def
  create mode 100755 target/hexagon/imported/mmvec/macros.def


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 05/30] Hexagon HVX (target/hexagon) macros

2021-09-20 Thread Richard Henderson

On 9/20/21 2:24 PM, Taylor Simpson wrote:

macros to interface with the generator
macros referenced in instruction semantics

Signed-off-by: Taylor Simpson
---
  target/hexagon/macros.h   |  22 +++
  target/hexagon/mmvec/macros.h | 341 ++
  2 files changed, 363 insertions(+)
  create mode 100644 target/hexagon/mmvec/macros.h


Just about unreadable, but ok.
Acked-by: Richard Henderson 

r~



Re: [PATCH v3 04/30] Hexagon HVX (target/hexagon) instruction attributes

2021-09-20 Thread Richard Henderson

On 9/20/21 2:23 PM, Taylor Simpson wrote:

Signed-off-by: Taylor Simpson
---
  target/hexagon/attribs_def.h.inc | 22 ++
  1 file changed, 22 insertions(+)


Acked-by: Richard Henderson 

r~



Re: [PATCH v3 02/30] Hexagon HVX (target/hexagon) add Hexagon Vector eXtensions (HVX) to core

2021-09-20 Thread Richard Henderson

On 9/20/21 2:23 PM, Taylor Simpson wrote:

HVX is a set of wide vector instructions.  Machine state includes
 vector registers (VRegs)
 vector predicate registers (QRegs)
 temporary registers for intermediate values
 store buffer (masked stores and scatter/gather)

Signed-off-by: Taylor Simpson
---


Acked-by: Richard Henderson 


r~



Re: [PATCH v2 22/23] tests/qapi-schema: Rename flat-union-* test cases to union-*

2021-09-20 Thread Eric Blake
On Fri, Sep 17, 2021 at 04:31:33PM +0200, Markus Armbruster wrote:
> Signed-off-by: Markus Armbruster 
> ---

>  65 files changed, 48 insertions(+), 48 deletions(-)

The diff is harder to read in email (due to file rename comparison
sometimes going astray on short and similar file contents) when
compared to applying the patch and inspecting the directory proper,
but either way, it looks okay to me.

> +++ b/tests/qapi-schema/meson.build
> @@ -107,22 +107,6 @@ schemas = [
>'features-name-bad-type.json',
>'features-no-list.json',
>'features-unknown-key.json',
> -  'flat-union-array-branch.json',
> -  'flat-union-bad-base.json',
> -  'flat-union-bad-discriminator.json',
> -  'flat-union-base-any.json',
> -  'flat-union-base-union.json',
> -  'flat-union-clash-member.json',
> -  'flat-union-discriminator-bad-name.json',
> -  'flat-union-empty.json',
> -  'flat-union-inline-invalid-dict.json',
> -  'flat-union-int-branch.json',
> -  'flat-union-invalid-branch-key.json',
> -  'flat-union-invalid-discriminator.json',
> -  'flat-union-invalid-if-discriminator.json',
> -  'flat-union-no-base.json',
> -  'flat-union-optional-discriminator.json',
> -  'flat-union-string-discriminator.json',
>'funny-char.json',
>'funny-word.json',
>'ident-with-escape.json',
> @@ -190,12 +174,28 @@ schemas = [
>'unclosed-list.json',
>'unclosed-object.json',
>'unclosed-string.json',
> +  'union-array-branch.json',
> +  'union-bad-base.json',
> +  'union-bad-discriminator.json',
> +  'union-base-any.json',
>'union-base-empty.json',
>'union-base-no-discriminator.json',
> +  'union-base-union.json',
>'union-branch-if-invalid.json',
>'union-branch-invalid-dict.json',
> +  'union-clash-member.json',
> +  'union-discriminator-bad-name.json',
> +  'union-empty.json',
> +  'union-inline-invalid-dict.json',
> +  'union-int-branch.json',
>'union-invalid-base.json',
> +  'union-invalid-branch-key.json',
>'union-invalid-data.json',
> +  'union-invalid-discriminator.json',
> +  'union-invalid-if-discriminator.json',
> +  'union-no-base.json',
> +  'union-optional-discriminator.json',
> +  'union-string-discriminator.json',
>'union-unknown.json',

This is probably the best part of the patch to focus on.

Reviewed-by: Eric Blake 

[PATCH v5 31/31] accel: Add missing AccelOpsClass::has_work() and drop SysemuCPUOps one

2021-09-20 Thread Philippe Mathieu-Daudé
cpu_common_has_work() is the default has_work() implementation
and returns 'false'.

Explicit it for the QTest / HAX / HVF / NVMM / Xen accelerators
and remove cpu_common_has_work().

Since there are no more implementations of SysemuCPUOps::has_work,
remove it along with the assertion in cpu_has_work().

Reviewed-by: Richard Henderson 
Acked-by: Paul Durrant 
Signed-off-by: Philippe Mathieu-Daudé 
---
 include/hw/core/cpu.h |  2 --
 accel/hvf/hvf-accel-ops.c |  6 ++
 accel/qtest/qtest.c   |  6 ++
 accel/xen/xen-all.c   |  6 ++
 hw/core/cpu-common.c  |  6 --
 softmmu/cpus.c| 11 ++-
 target/i386/hax/hax-accel-ops.c   |  6 ++
 target/i386/nvmm/nvmm-accel-ops.c |  6 ++
 8 files changed, 32 insertions(+), 17 deletions(-)

diff --git a/include/hw/core/cpu.h b/include/hw/core/cpu.h
index e2dd171a13f..c64709b898c 100644
--- a/include/hw/core/cpu.h
+++ b/include/hw/core/cpu.h
@@ -89,7 +89,6 @@ struct SysemuCPUOps;
  * instantiatable CPU type.
  * @parse_features: Callback to parse command line arguments.
  * @reset_dump_flags: #CPUDumpFlags to use for reset logging.
- * @has_work: Callback for checking if there is work to do.
  * @memory_rw_debug: Callback for GDB memory access.
  * @dump_state: Callback for dumping state.
  * @get_arch_id: Callback for getting architecture-dependent CPU ID.
@@ -132,7 +131,6 @@ struct CPUClass {
 void (*parse_features)(const char *typename, char *str, Error **errp);
 
 int reset_dump_flags;
-bool (*has_work)(CPUState *cpu);
 int (*memory_rw_debug)(CPUState *cpu, vaddr addr,
uint8_t *buf, int len, bool is_write);
 void (*dump_state)(CPUState *cpu, FILE *, int flags);
diff --git a/accel/hvf/hvf-accel-ops.c b/accel/hvf/hvf-accel-ops.c
index d1691be9896..53c427ee42e 100644
--- a/accel/hvf/hvf-accel-ops.c
+++ b/accel/hvf/hvf-accel-ops.c
@@ -446,6 +446,11 @@ static void hvf_start_vcpu_thread(CPUState *cpu)
cpu, QEMU_THREAD_JOINABLE);
 }
 
+static bool hvf_cpu_has_work(CPUState *cpu)
+{
+return false;
+}
+
 static void hvf_accel_ops_class_init(ObjectClass *oc, void *data)
 {
 AccelOpsClass *ops = ACCEL_OPS_CLASS(oc);
@@ -456,6 +461,7 @@ static void hvf_accel_ops_class_init(ObjectClass *oc, void 
*data)
 ops->synchronize_post_init = hvf_cpu_synchronize_post_init;
 ops->synchronize_state = hvf_cpu_synchronize_state;
 ops->synchronize_pre_loadvm = hvf_cpu_synchronize_pre_loadvm;
+ops->has_work = hvf_cpu_has_work;
 };
 static const TypeInfo hvf_accel_ops_type = {
 .name = ACCEL_OPS_NAME("hvf"),
diff --git a/accel/qtest/qtest.c b/accel/qtest/qtest.c
index 7e6b8110d52..eb5a17cef18 100644
--- a/accel/qtest/qtest.c
+++ b/accel/qtest/qtest.c
@@ -47,12 +47,18 @@ static const TypeInfo qtest_accel_type = {
 };
 module_obj(TYPE_QTEST_ACCEL);
 
+static bool qtest_cpu_has_work(CPUState *cpu)
+{
+return false;
+}
+
 static void qtest_accel_ops_class_init(ObjectClass *oc, void *data)
 {
 AccelOpsClass *ops = ACCEL_OPS_CLASS(oc);
 
 ops->create_vcpu_thread = dummy_start_vcpu_thread;
 ops->get_virtual_clock = qtest_get_virtual_clock;
+ops->has_work = qtest_cpu_has_work;
 };
 
 static const TypeInfo qtest_accel_ops_type = {
diff --git a/accel/xen/xen-all.c b/accel/xen/xen-all.c
index 69aa7d018b2..fe5a37fa2e6 100644
--- a/accel/xen/xen-all.c
+++ b/accel/xen/xen-all.c
@@ -215,11 +215,17 @@ static const TypeInfo xen_accel_type = {
 .class_init = xen_accel_class_init,
 };
 
+static bool xen_cpu_has_work(CPUState *cpu)
+{
+return false;
+}
+
 static void xen_accel_ops_class_init(ObjectClass *oc, void *data)
 {
 AccelOpsClass *ops = ACCEL_OPS_CLASS(oc);
 
 ops->create_vcpu_thread = dummy_start_vcpu_thread;
+ops->has_work = xen_cpu_has_work;
 }
 
 static const TypeInfo xen_accel_ops_type = {
diff --git a/hw/core/cpu-common.c b/hw/core/cpu-common.c
index e2f5a646046..5ed1ccdfdd5 100644
--- a/hw/core/cpu-common.c
+++ b/hw/core/cpu-common.c
@@ -143,11 +143,6 @@ static void cpu_common_reset(DeviceState *dev)
 }
 }
 
-static bool cpu_common_has_work(CPUState *cs)
-{
-return false;
-}
-
 ObjectClass *cpu_class_by_name(const char *typename, const char *cpu_model)
 {
 CPUClass *cc = CPU_CLASS(object_class_by_name(typename));
@@ -279,7 +274,6 @@ static void cpu_class_init(ObjectClass *klass, void *data)
 
 k->parse_features = cpu_common_parse_features;
 k->get_arch_id = cpu_common_get_arch_id;
-k->has_work = cpu_common_has_work;
 k->gdb_read_register = cpu_common_gdb_read_register;
 k->gdb_write_register = cpu_common_gdb_write_register;
 set_bit(DEVICE_CATEGORY_CPU, dc->categories);
diff --git a/softmmu/cpus.c b/softmmu/cpus.c
index 98b4049aba7..e6dad2243c6 100644
--- a/softmmu/cpus.c
+++ b/softmmu/cpus.c
@@ -251,15 +251,8 @@ void cpu_interrupt(CPUState *cpu, int mask)
 
 bool cpu_has_work(CPUState *cpu)
 {
-CPUClass *cc = 

Re: [PATCH v4 11/20] nubus-device: add romfile property for loading declaration ROMs

2021-09-20 Thread Laurent Vivier
Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
> The declaration ROM is located at the top-most address of the standard slot
> space.
> 
> Signed-off-by: Mark Cave-Ayland 
> ---
>  hw/nubus/nubus-device.c  | 44 +++-
>  include/hw/nubus/nubus.h |  6 ++
>  2 files changed, 49 insertions(+), 1 deletion(-)
> 
> diff --git a/hw/nubus/nubus-device.c b/hw/nubus/nubus-device.c
> index 9c1992ceb0..3da0db4d54 100644
> --- a/hw/nubus/nubus-device.c
> +++ b/hw/nubus/nubus-device.c
> @@ -9,16 +9,21 @@
>   */
>  
>  #include "qemu/osdep.h"
> +#include "qemu/datadir.h"
> +#include "hw/loader.h"
>  #include "hw/nubus/nubus.h"
>  #include "qapi/error.h"
> +#include "qemu/error-report.h"
>  
>  
>  static void nubus_device_realize(DeviceState *dev, Error **errp)
>  {
>  NubusBus *nubus = NUBUS_BUS(qdev_get_parent_bus(dev));
>  NubusDevice *nd = NUBUS_DEVICE(dev);
> -char *name;
> +char *name, *path;
>  hwaddr slot_offset;
> +int64_t size;
> +int ret;
>  
>  /* Super */
>  slot_offset = (nd->slot - 6) * NUBUS_SUPER_SLOT_SIZE;
> @@ -38,10 +43,47 @@ static void nubus_device_realize(DeviceState *dev, Error 
> **errp)
>  memory_region_add_subregion(>slot_io, slot_offset,
>  >slot_mem);
>  g_free(name);
> +
> +/* Declaration ROM */
> +if (nd->romfile != NULL) {
> +path = qemu_find_file(QEMU_FILE_TYPE_BIOS, nd->romfile);
> +if (path == NULL) {
> +path = g_strdup(nd->romfile);
> +}
> +
> +size = get_image_size(path);
> +if (size < 0) {
> +error_setg(errp, "failed to find romfile \"%s\"", nd->romfile);
> +g_free(path);
> +return;
> +} else if (size == 0) {
> +error_setg(errp, "romfile \"%s\" is empty", nd->romfile);
> +g_free(path);
> +return;
> +} else if (size > NUBUS_DECL_ROM_MAX_SIZE) {
> +error_setg(errp, "romfile \"%s\" too large (maximum size 128K)",
> +   nd->romfile);
> +g_free(path);
> +return;
> +}
> +
> +name = g_strdup_printf("nubus-slot-%x-declaration-rom", nd->slot);
> +memory_region_init_rom(>decl_rom, OBJECT(dev), name, size,
> +   _abort);
> +ret = load_image_mr(path, >decl_rom);
> +g_free(path);
> +if (ret < 0) {
> +error_setg(errp, "could not load romfile \"%s\"", nd->romfile);
> +return;
> +}
> +memory_region_add_subregion(>slot_mem, NUBUS_SLOT_SIZE - size,
> +>decl_rom);
> +}
>  }
>  
>  static Property nubus_device_properties[] = {
>  DEFINE_PROP_INT32("slot", NubusDevice, slot, -1),
> +DEFINE_PROP_STRING("romfile", NubusDevice, romfile),
>  DEFINE_PROP_END_OF_LIST()
>  };
>  
> diff --git a/include/hw/nubus/nubus.h b/include/hw/nubus/nubus.h
> index 87a97516c7..0c9f50c32e 100644
> --- a/include/hw/nubus/nubus.h
> +++ b/include/hw/nubus/nubus.h
> @@ -12,6 +12,7 @@
>  #include "hw/qdev-properties.h"
>  #include "exec/address-spaces.h"
>  #include "qom/object.h"
> +#include "qemu/units.h"
>  
>  #define NUBUS_SUPER_SLOT_SIZE 0x1000U
>  #define NUBUS_SUPER_SLOT_NB   0x9
> @@ -39,12 +40,17 @@ struct NubusBus {
>  uint32_t slot_available_mask;
>  };
>  
> +#define NUBUS_DECL_ROM_MAX_SIZE(128 * KiB)
> +
>  struct NubusDevice {
>  DeviceState qdev;
>  
>  int32_t slot;
>  MemoryRegion super_slot_mem;
>  MemoryRegion slot_mem;
> +
> +char *romfile;
> +MemoryRegion decl_rom;
>  };
>  
>  #endif
> 

Reviewed-by: Laurent Vivier 



[PATCH v5 29/31] target/tricore: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/tricore/cpu.c | 6 +-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/target/tricore/cpu.c b/target/tricore/cpu.c
index b95682b7f04..419fa624bd5 100644
--- a/target/tricore/cpu.c
+++ b/target/tricore/cpu.c
@@ -62,10 +62,12 @@ static void tricore_cpu_reset(DeviceState *dev)
 cpu_state_reset(env);
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool tricore_cpu_has_work(CPUState *cs)
 {
 return true;
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void tricore_cpu_realizefn(DeviceState *dev, Error **errp)
 {
@@ -154,6 +156,9 @@ static const struct TCGCPUOps tricore_tcg_ops = {
 .initialize = tricore_tcg_init,
 .synchronize_from_tb = tricore_cpu_synchronize_from_tb,
 .tlb_fill = tricore_cpu_tlb_fill,
+#if !defined(CONFIG_USER_ONLY)
+.has_work = tricore_cpu_has_work,
+#endif
 };
 
 static void tricore_cpu_class_init(ObjectClass *c, void *data)
@@ -167,7 +172,6 @@ static void tricore_cpu_class_init(ObjectClass *c, void 
*data)
 
 device_class_set_parent_reset(dc, tricore_cpu_reset, >parent_reset);
 cc->class_by_name = tricore_cpu_class_by_name;
-cc->has_work = tricore_cpu_has_work;
 
 cc->gdb_read_register = tricore_cpu_gdb_read_register;
 cc->gdb_write_register = tricore_cpu_gdb_write_register;
-- 
2.31.1




RE: [PATCH v3 15/30] Hexagon HVX (target/hexagon) helper overrides - vector assign & cmov

2021-09-20 Thread Taylor Simpson


> -Original Message-
> From: Philippe Mathieu-Daudé  On
> Behalf Of Philippe Mathieu-Daudé
> Sent: Monday, September 20, 2021 4:59 PM
> To: Taylor Simpson ; qemu-devel@nongnu.org
> Cc: a...@rev.ng; Brian Cain ;
> richard.hender...@linaro.org
> Subject: Re: [PATCH v3 15/30] Hexagon HVX (target/hexagon) helper
> overrides - vector assign & cmov
> 
> On 9/20/21 23:24, Taylor Simpson wrote:
> > Signed-off-by: Taylor Simpson 
> > ---
> >  target/hexagon/gen_tcg_hvx.h | 31
> +++
> >  1 file changed, 31 insertions(+)
> >
> > diff --git a/target/hexagon/gen_tcg_hvx.h
> > b/target/hexagon/gen_tcg_hvx.h index eb29566..bcd53d4 100644
> > --- a/target/hexagon/gen_tcg_hvx.h
> > +++ b/target/hexagon/gen_tcg_hvx.h
> > @@ -126,4 +126,35 @@ static inline void assert_vhist_tmp(DisasContext
> *ctx)
> >  } while (0)
> >
> >
> > +#define fGEN_TCG_V6_vassign(SHORTCODE) \
> > +tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
> > + sizeof(MMVector), sizeof(MMVector))
> > +
> > +/* Vector conditional move */
> > +#define fGEN_TCG_VEC_CMOV(PRED) \
> > +do { \
> > +TCGv lsb = tcg_temp_new(); \
> > +TCGLabel *false_label = gen_new_label(); \
> > +TCGLabel *end_label = gen_new_label(); \
> > +tcg_gen_andi_tl(lsb, PsV, 1); \
> > +tcg_gen_brcondi_tl(TCG_COND_NE, lsb, PRED, false_label); \
> > +tcg_temp_free(lsb); \
> > +tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
> > + sizeof(MMVector), sizeof(MMVector)); \
> > +tcg_gen_br(end_label); \
> > +gen_set_label(false_label); \
> > +tcg_gen_ori_tl(hex_slot_cancelled, hex_slot_cancelled, \
> > +   1 << insn->slot); \
> > +gen_set_label(end_label); \
> > +} while (0)
> 
> Why a macro and not a (eventually inlined) function?

I make these macros to be consistent across the different overrides.  This one 
could easily be a function, but others cannot.  For example, 
fGEN_TCG_VEC_CMP_OP can't - see patch 20/30.

Having said that, I can change only the ones that don't need to be macros into 
functions if that is preferred.


Thanks,
Taylor




[PATCH v5 24/31] target/rx: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/rx/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/rx/cpu.c b/target/rx/cpu.c
index 25a4aa2976d..ac6b40b2716 100644
--- a/target/rx/cpu.c
+++ b/target/rx/cpu.c
@@ -41,11 +41,13 @@ static void rx_cpu_synchronize_from_tb(CPUState *cs,
 cpu->env.pc = tb->pc;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool rx_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request &
 (CPU_INTERRUPT_HARD | CPU_INTERRUPT_FIR);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void rx_cpu_reset(DeviceState *dev)
 {
@@ -189,6 +191,7 @@ static const struct TCGCPUOps rx_tcg_ops = {
 .tlb_fill = rx_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = rx_cpu_has_work,
 .cpu_exec_interrupt = rx_cpu_exec_interrupt,
 .do_interrupt = rx_cpu_do_interrupt,
 #endif /* !CONFIG_USER_ONLY */
@@ -206,7 +209,6 @@ static void rx_cpu_class_init(ObjectClass *klass, void 
*data)
   >parent_reset);
 
 cc->class_by_name = rx_cpu_class_by_name;
-cc->has_work = rx_cpu_has_work;
 cc->dump_state = rx_cpu_dump_state;
 cc->set_pc = rx_cpu_set_pc;
 
-- 
2.31.1




Re: [PATCH v3 15/30] Hexagon HVX (target/hexagon) helper overrides - vector assign & cmov

2021-09-20 Thread Philippe Mathieu-Daudé
On 9/20/21 23:24, Taylor Simpson wrote:
> Signed-off-by: Taylor Simpson 
> ---
>  target/hexagon/gen_tcg_hvx.h | 31 +++
>  1 file changed, 31 insertions(+)
> 
> diff --git a/target/hexagon/gen_tcg_hvx.h b/target/hexagon/gen_tcg_hvx.h
> index eb29566..bcd53d4 100644
> --- a/target/hexagon/gen_tcg_hvx.h
> +++ b/target/hexagon/gen_tcg_hvx.h
> @@ -126,4 +126,35 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
>  } while (0)
>  
>  
> +#define fGEN_TCG_V6_vassign(SHORTCODE) \
> +tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
> + sizeof(MMVector), sizeof(MMVector))
> +
> +/* Vector conditional move */
> +#define fGEN_TCG_VEC_CMOV(PRED) \
> +do { \
> +TCGv lsb = tcg_temp_new(); \
> +TCGLabel *false_label = gen_new_label(); \
> +TCGLabel *end_label = gen_new_label(); \
> +tcg_gen_andi_tl(lsb, PsV, 1); \
> +tcg_gen_brcondi_tl(TCG_COND_NE, lsb, PRED, false_label); \
> +tcg_temp_free(lsb); \
> +tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
> + sizeof(MMVector), sizeof(MMVector)); \
> +tcg_gen_br(end_label); \
> +gen_set_label(false_label); \
> +tcg_gen_ori_tl(hex_slot_cancelled, hex_slot_cancelled, \
> +   1 << insn->slot); \
> +gen_set_label(end_label); \
> +} while (0)

Why a macro and not a (eventually inlined) function?

> +/* Vector conditional move (true) */
> +#define fGEN_TCG_V6_vcmov(SHORTCODE) \
> +fGEN_TCG_VEC_CMOV(1)
> +
> +/* Vector conditional move (false) */
> +#define fGEN_TCG_V6_vncmov(SHORTCODE) \
> +fGEN_TCG_VEC_CMOV(0)
> +
>  #endif
> 



[PATCH v5 20/31] target/openrisc: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/openrisc/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/openrisc/cpu.c b/target/openrisc/cpu.c
index 27cb04152f9..3c368a1bde7 100644
--- a/target/openrisc/cpu.c
+++ b/target/openrisc/cpu.c
@@ -30,11 +30,13 @@ static void openrisc_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.dflag = 0;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool openrisc_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & (CPU_INTERRUPT_HARD |
 CPU_INTERRUPT_TIMER);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void openrisc_disas_set_info(CPUState *cpu, disassemble_info *info)
 {
@@ -189,6 +191,7 @@ static const struct TCGCPUOps openrisc_tcg_ops = {
 .tlb_fill = openrisc_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = openrisc_cpu_has_work,
 .cpu_exec_interrupt = openrisc_cpu_exec_interrupt,
 .do_interrupt = openrisc_cpu_do_interrupt,
 #endif /* !CONFIG_USER_ONLY */
@@ -205,7 +208,6 @@ static void openrisc_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_reset(dc, openrisc_cpu_reset, >parent_reset);
 
 cc->class_by_name = openrisc_cpu_class_by_name;
-cc->has_work = openrisc_cpu_has_work;
 cc->dump_state = openrisc_cpu_dump_state;
 cc->set_pc = openrisc_cpu_set_pc;
 cc->gdb_read_register = openrisc_cpu_gdb_read_register;
-- 
2.31.1




Re: [PATCH v5 05/31] sysemu: Introduce AccelOpsClass::has_work()

2021-09-20 Thread Richard Henderson

On 9/20/21 2:44 PM, Philippe Mathieu-Daudé wrote:

-g_assert(cc->has_work);
-return cc->has_work(cpu);
+if (cc->has_work) {
+return cc->has_work(cpu);
+}
+if (cpus_accel->has_work) {
+return cpus_accel->has_work(cpu);
+}
+g_assert_not_reached();


This might be close to the end result, but it isn't what we begin with in 
cpu_thread_is_idle.

You'd want

if (cc->has_work && cc->has_work(cpu)) {
return true;
}
if (cpus_accel->has_work && cpus_accel->has_work(cpu)) {
return true;
}
return false;

to start.  After the cpus_accel hook is filled in you can assert and return from 
cpus_accel->has_work.  And of course after cc->has_work is removed, that clause is gone.



r~



[PATCH v5 18/31] target/mips: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to TCG sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/mips/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/mips/cpu.c b/target/mips/cpu.c
index 00e0c55d0e4..3639c03f8ea 100644
--- a/target/mips/cpu.c
+++ b/target/mips/cpu.c
@@ -128,6 +128,7 @@ static void mips_cpu_set_pc(CPUState *cs, vaddr value)
 mips_env_set_pc(>env, value);
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool mips_cpu_has_work(CPUState *cs)
 {
 MIPSCPU *cpu = MIPS_CPU(cs);
@@ -172,6 +173,7 @@ static bool mips_cpu_has_work(CPUState *cs)
 }
 return has_work;
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 #include "cpu-defs.c.inc"
 
@@ -542,6 +544,7 @@ static const struct TCGCPUOps mips_tcg_ops = {
 .tlb_fill = mips_cpu_tlb_fill,
 
 #if !defined(CONFIG_USER_ONLY)
+.has_work = mips_cpu_has_work,
 .cpu_exec_interrupt = mips_cpu_exec_interrupt,
 .do_interrupt = mips_cpu_do_interrupt,
 .do_transaction_failed = mips_cpu_do_transaction_failed,
@@ -563,7 +566,6 @@ static void mips_cpu_class_init(ObjectClass *c, void *data)
 device_class_set_props(dc, mips_cpu_properties);
 
 cc->class_by_name = mips_cpu_class_by_name;
-cc->has_work = mips_cpu_has_work;
 cc->dump_state = mips_cpu_dump_state;
 cc->set_pc = mips_cpu_set_pc;
 cc->gdb_read_register = mips_cpu_gdb_read_register;
-- 
2.31.1




Re: [PATCH v5 12/31] target/cris: Restrict has_work() handler to sysemu

2021-09-20 Thread Richard Henderson

On 9/20/21 2:44 PM, Philippe Mathieu-Daudé wrote:

Restrict has_work() to sysemu.

Signed-off-by: Philippe Mathieu-Daudé
---
  target/cris/cpu.c | 5 -
  1 file changed, 4 insertions(+), 1 deletion(-)


Reviewed-by: Richard Henderson 

r~



[PATCH v5 16/31] target/m68k: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/m68k/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/m68k/cpu.c b/target/m68k/cpu.c
index 66d22d11895..ad5d26b5c9e 100644
--- a/target/m68k/cpu.c
+++ b/target/m68k/cpu.c
@@ -31,10 +31,12 @@ static void m68k_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.pc = value;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool m68k_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & CPU_INTERRUPT_HARD;
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void m68k_set_feature(CPUM68KState *env, int feature)
 {
@@ -518,6 +520,7 @@ static const struct TCGCPUOps m68k_tcg_ops = {
 .tlb_fill = m68k_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = m68k_cpu_has_work,
 .cpu_exec_interrupt = m68k_cpu_exec_interrupt,
 .do_interrupt = m68k_cpu_do_interrupt,
 .do_transaction_failed = m68k_cpu_transaction_failed,
@@ -535,7 +538,6 @@ static void m68k_cpu_class_init(ObjectClass *c, void *data)
 device_class_set_parent_reset(dc, m68k_cpu_reset, >parent_reset);
 
 cc->class_by_name = m68k_cpu_class_by_name;
-cc->has_work = m68k_cpu_has_work;
 cc->dump_state = m68k_cpu_dump_state;
 cc->set_pc = m68k_cpu_set_pc;
 cc->gdb_read_register = m68k_cpu_gdb_read_register;
-- 
2.31.1




Re: [PATCH v5 10/31] target/arm: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Richard Henderson

On 9/20/21 2:44 PM, Philippe Mathieu-Daudé wrote:

Restrict has_work() to TCG sysemu.

Signed-off-by: Philippe Mathieu-Daudé
---
  target/arm/cpu.c | 7 +--
  target/arm/cpu_tcg.c | 2 +-
  2 files changed, 6 insertions(+), 3 deletions(-)


Reviewed-by: Richard Henderson 

r~



[PATCH v5 28/31] target/sparc: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/sparc/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/sparc/cpu.c b/target/sparc/cpu.c
index e83e305aa9d..4a63ed12644 100644
--- a/target/sparc/cpu.c
+++ b/target/sparc/cpu.c
@@ -702,6 +702,7 @@ static void sparc_cpu_synchronize_from_tb(CPUState *cs,
 cpu->env.npc = tb->cs_base;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool sparc_cpu_has_work(CPUState *cs)
 {
 SPARCCPU *cpu = SPARC_CPU(cs);
@@ -710,6 +711,7 @@ static bool sparc_cpu_has_work(CPUState *cs)
 return (cs->interrupt_request & CPU_INTERRUPT_HARD) &&
cpu_interrupts_enabled(env);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static char *sparc_cpu_type_name(const char *cpu_model)
 {
@@ -867,6 +869,7 @@ static const struct TCGCPUOps sparc_tcg_ops = {
 .tlb_fill = sparc_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = sparc_cpu_has_work,
 .cpu_exec_interrupt = sparc_cpu_exec_interrupt,
 .do_interrupt = sparc_cpu_do_interrupt,
 .do_transaction_failed = sparc_cpu_do_transaction_failed,
@@ -888,7 +891,6 @@ static void sparc_cpu_class_init(ObjectClass *oc, void 
*data)
 
 cc->class_by_name = sparc_cpu_class_by_name;
 cc->parse_features = sparc_cpu_parse_features;
-cc->has_work = sparc_cpu_has_work;
 cc->dump_state = sparc_cpu_dump_state;
 #if !defined(TARGET_SPARC64) && !defined(CONFIG_USER_ONLY)
 cc->memory_rw_debug = sparc_cpu_memory_rw_debug;
-- 
2.31.1




[PATCH v5 30/31] target/xtensa: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/xtensa/cpu.c | 14 +++---
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/target/xtensa/cpu.c b/target/xtensa/cpu.c
index c1cbd03595e..5cb19a88819 100644
--- a/target/xtensa/cpu.c
+++ b/target/xtensa/cpu.c
@@ -43,18 +43,17 @@ static void xtensa_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.pc = value;
 }
 
+#ifndef CONFIG_USER_ONLY
+
 static bool xtensa_cpu_has_work(CPUState *cs)
 {
-#ifndef CONFIG_USER_ONLY
 XtensaCPU *cpu = XTENSA_CPU(cs);
 
 return !cpu->env.runstall && cpu->env.pending_irq_level;
-#else
-return true;
-#endif
 }
 
-#ifdef CONFIG_USER_ONLY
+#else /* CONFIG_USER_ONLY*/
+
 static bool abi_call0;
 
 void xtensa_set_abi_call0(void)
@@ -66,7 +65,8 @@ bool xtensa_abi_call0(void)
 {
 return abi_call0;
 }
-#endif
+
+#endif /* CONFIG_USER_ONLY */
 
 static void xtensa_cpu_reset(DeviceState *dev)
 {
@@ -196,6 +196,7 @@ static const struct TCGCPUOps xtensa_tcg_ops = {
 .debug_excp_handler = xtensa_breakpoint_handler,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = xtensa_cpu_has_work,
 .cpu_exec_interrupt = xtensa_cpu_exec_interrupt,
 .do_interrupt = xtensa_cpu_do_interrupt,
 .do_transaction_failed = xtensa_cpu_do_transaction_failed,
@@ -215,7 +216,6 @@ static void xtensa_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_reset(dc, xtensa_cpu_reset, >parent_reset);
 
 cc->class_by_name = xtensa_cpu_class_by_name;
-cc->has_work = xtensa_cpu_has_work;
 cc->dump_state = xtensa_cpu_dump_state;
 cc->set_pc = xtensa_cpu_set_pc;
 cc->gdb_read_register = xtensa_cpu_gdb_read_register;
-- 
2.31.1




Re: [PATCH v5 08/31] accel/tcg: Implement AccelOpsClass::has_work() as stub

2021-09-20 Thread Richard Henderson

On 9/20/21 2:44 PM, Philippe Mathieu-Daudé wrote:

+static bool tcg_cpu_has_work(CPUState *cpu)
+{
+CPUClass *cc = CPU_GET_CLASS(cpu);
+
+g_assert(cc->tcg_ops->has_work);
+return cc->tcg_ops->has_work(cpu);
+}


Now, you're expecting cc->has_work to disappear as cc->tcg_ops->has_work appears.  If 
we're expecting cc->has_work to not affect other accelerators, then I think you should 
first move cc->has_work to this function, *before* you add the tcg_ops hook.



r~



[PATCH v5 26/31] target/sh4: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/sh4/cpu.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/target/sh4/cpu.c b/target/sh4/cpu.c
index 2047742d03c..fb2116dc52e 100644
--- a/target/sh4/cpu.c
+++ b/target/sh4/cpu.c
@@ -58,13 +58,14 @@ static bool superh_io_recompile_replay_branch(CPUState *cs,
 }
 return false;
 }
-#endif
 
 static bool superh_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & CPU_INTERRUPT_HARD;
 }
 
+#endif /* !CONFIG_USER_ONLY */
+
 static void superh_cpu_reset(DeviceState *dev)
 {
 CPUState *s = CPU(dev);
@@ -239,6 +240,7 @@ static const struct TCGCPUOps superh_tcg_ops = {
 .tlb_fill = superh_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = superh_cpu_has_work,
 .cpu_exec_interrupt = superh_cpu_exec_interrupt,
 .do_interrupt = superh_cpu_do_interrupt,
 .do_unaligned_access = superh_cpu_do_unaligned_access,
@@ -258,7 +260,6 @@ static void superh_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_reset(dc, superh_cpu_reset, >parent_reset);
 
 cc->class_by_name = superh_cpu_class_by_name;
-cc->has_work = superh_cpu_has_work;
 cc->dump_state = superh_cpu_dump_state;
 cc->set_pc = superh_cpu_set_pc;
 cc->gdb_read_register = superh_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 22/31] target/ppc: Restrict has_work() handlers to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict PowerPCCPUClass::has_work() and ppc_cpu_has_work()
- SysemuCPUOps::has_work() implementation - to TCG sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/ppc/cpu-qom.h  |  4 +++-
 target/ppc/cpu_init.c | 24 ++--
 2 files changed, 21 insertions(+), 7 deletions(-)

diff --git a/target/ppc/cpu-qom.h b/target/ppc/cpu-qom.h
index 36110112506..ff2bafcde6f 100644
--- a/target/ppc/cpu-qom.h
+++ b/target/ppc/cpu-qom.h
@@ -188,8 +188,10 @@ struct PowerPCCPUClass {
 uint32_t flags;
 int bfd_mach;
 uint32_t l1_dcache_size, l1_icache_size;
-bool (*has_work)(CPUState *cpu);
 #ifndef CONFIG_USER_ONLY
+#ifdef CONFIG_TCG
+bool (*has_work)(CPUState *cpu);
+#endif /* CONFIG_TCG */
 unsigned int gdb_num_sprs;
 const char *gdb_spr_xml;
 #endif
diff --git a/target/ppc/cpu_init.c b/target/ppc/cpu_init.c
index 2f7d262b176..5c134adeea9 100644
--- a/target/ppc/cpu_init.c
+++ b/target/ppc/cpu_init.c
@@ -7583,6 +7583,7 @@ static bool ppc_pvr_match_power7(PowerPCCPUClass *pcc, 
uint32_t pvr)
 return false;
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool cpu_has_work_POWER7(CPUState *cs)
 {
 PowerPCCPU *cpu = POWERPC_CPU(cs);
@@ -7616,6 +7617,7 @@ static bool cpu_has_work_POWER7(CPUState *cs)
 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
 }
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
 {
@@ -7629,7 +7631,6 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
 pcc->pcr_supported = PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER7;
 pcc->check_pow = check_pow_nocheck;
-pcc->has_work = cpu_has_work_POWER7;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -7672,6 +7673,7 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
 pcc->lpcr_pm = LPCR_P7_PECE0 | LPCR_P7_PECE1 | LPCR_P7_PECE2;
 pcc->mmu_model = POWERPC_MMU_2_06;
 #if defined(CONFIG_SOFTMMU)
+pcc->has_work = cpu_has_work_POWER7;
 pcc->hash64_opts = _hash64_opts_POWER7;
 pcc->lrg_decr_bits = 32;
 #endif
@@ -7742,6 +7744,7 @@ static bool ppc_pvr_match_power8(PowerPCCPUClass *pcc, 
uint32_t pvr)
 return false;
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool cpu_has_work_POWER8(CPUState *cs)
 {
 PowerPCCPU *cpu = POWERPC_CPU(cs);
@@ -7783,6 +7786,7 @@ static bool cpu_has_work_POWER8(CPUState *cs)
 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
 }
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
 {
@@ -7796,7 +7800,6 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
 pcc->pcr_supported = PCR_COMPAT_2_07 | PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER8;
 pcc->check_pow = check_pow_nocheck;
-pcc->has_work = cpu_has_work_POWER8;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -7846,6 +7849,7 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
LPCR_P8_PECE3 | LPCR_P8_PECE4;
 pcc->mmu_model = POWERPC_MMU_2_07;
 #if defined(CONFIG_SOFTMMU)
+pcc->has_work = cpu_has_work_POWER8;
 pcc->hash64_opts = _hash64_opts_POWER7;
 pcc->lrg_decr_bits = 32;
 pcc->n_host_threads = 8;
@@ -7939,6 +7943,7 @@ static bool ppc_pvr_match_power9(PowerPCCPUClass *pcc, 
uint32_t pvr)
 return false;
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool cpu_has_work_POWER9(CPUState *cs)
 {
 PowerPCCPU *cpu = POWERPC_CPU(cs);
@@ -7996,6 +8001,7 @@ static bool cpu_has_work_POWER9(CPUState *cs)
 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
 }
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
 {
@@ -8010,7 +8016,6 @@ POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
  PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER9;
 pcc->check_pow = check_pow_nocheck;
-pcc->has_work = cpu_has_work_POWER9;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -8059,6 +8064,7 @@ POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
 pcc->lpcr_pm = LPCR_PDEE | LPCR_HDEE | LPCR_EEE | LPCR_DEE | LPCR_OEE;
 pcc->mmu_model = POWERPC_MMU_3_00;
 #if defined(CONFIG_SOFTMMU)
+pcc->has_work = cpu_has_work_POWER9;
 /* segment page size remain the same */
 pcc->hash64_opts = _hash64_opts_POWER7;
 pcc->radix_page_info = _radix_page_info;

[PATCH v5 09/31] target/alpha: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/alpha/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/alpha/cpu.c b/target/alpha/cpu.c
index 93e16a2ffb4..1ca601cac5b 100644
--- a/target/alpha/cpu.c
+++ b/target/alpha/cpu.c
@@ -33,6 +33,7 @@ static void alpha_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.pc = value;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool alpha_cpu_has_work(CPUState *cs)
 {
 /* Here we are checking to see if the CPU should wake up from HALT.
@@ -47,6 +48,7 @@ static bool alpha_cpu_has_work(CPUState *cs)
 | CPU_INTERRUPT_SMP
 | CPU_INTERRUPT_MCHK);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void alpha_cpu_disas_set_info(CPUState *cpu, disassemble_info *info)
 {
@@ -221,6 +223,7 @@ static const struct TCGCPUOps alpha_tcg_ops = {
 .tlb_fill = alpha_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = alpha_cpu_has_work,
 .cpu_exec_interrupt = alpha_cpu_exec_interrupt,
 .do_interrupt = alpha_cpu_do_interrupt,
 .do_transaction_failed = alpha_cpu_do_transaction_failed,
@@ -238,7 +241,6 @@ static void alpha_cpu_class_init(ObjectClass *oc, void 
*data)
 >parent_realize);
 
 cc->class_by_name = alpha_cpu_class_by_name;
-cc->has_work = alpha_cpu_has_work;
 cc->dump_state = alpha_cpu_dump_state;
 cc->set_pc = alpha_cpu_set_pc;
 cc->gdb_read_register = alpha_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 27/31] target/sparc: Remove pointless use of CONFIG_TCG definition

2021-09-20 Thread Philippe Mathieu-Daudé
The SPARC target only support TCG acceleration. Remove the CONFIG_TCG
definition introduced by mistake in commit 78271684719 ("cpu: tcg_ops:
move to tcg-cpu-ops.h, keep a pointer in CPUClass").

Reported-by: Richard Henderson 
Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/sparc/cpu.c | 2 --
 1 file changed, 2 deletions(-)

diff --git a/target/sparc/cpu.c b/target/sparc/cpu.c
index 5a8a4ce7506..e83e305aa9d 100644
--- a/target/sparc/cpu.c
+++ b/target/sparc/cpu.c
@@ -859,7 +859,6 @@ static const struct SysemuCPUOps sparc_sysemu_ops = {
 };
 #endif
 
-#ifdef CONFIG_TCG
 #include "hw/core/tcg-cpu-ops.h"
 
 static const struct TCGCPUOps sparc_tcg_ops = {
@@ -874,7 +873,6 @@ static const struct TCGCPUOps sparc_tcg_ops = {
 .do_unaligned_access = sparc_cpu_do_unaligned_access,
 #endif /* !CONFIG_USER_ONLY */
 };
-#endif /* CONFIG_TCG */
 
 static void sparc_cpu_class_init(ObjectClass *oc, void *data)
 {
-- 
2.31.1




[PATCH v5 21/31] target/ppc: Introduce PowerPCCPUClass::has_work()

2021-09-20 Thread Philippe Mathieu-Daudé
We're moving the hook from CPUState to TCGCPUOps. TCGCPUOps is
a const structure, so to avoid creating multiple versions of
the same structure, simply changing the has_work() handler,
introduce yet another indirection with a has_work() handler in
PowerPCCPUClass, and ppc_cpu_has_work() method which dispatch
to it.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/ppc/cpu-qom.h  |  1 +
 target/ppc/cpu_init.c | 23 ++-
 2 files changed, 15 insertions(+), 9 deletions(-)

diff --git a/target/ppc/cpu-qom.h b/target/ppc/cpu-qom.h
index 5800fa324e8..36110112506 100644
--- a/target/ppc/cpu-qom.h
+++ b/target/ppc/cpu-qom.h
@@ -188,6 +188,7 @@ struct PowerPCCPUClass {
 uint32_t flags;
 int bfd_mach;
 uint32_t l1_dcache_size, l1_icache_size;
+bool (*has_work)(CPUState *cpu);
 #ifndef CONFIG_USER_ONLY
 unsigned int gdb_num_sprs;
 const char *gdb_spr_xml;
diff --git a/target/ppc/cpu_init.c b/target/ppc/cpu_init.c
index 6aad01d1d3a..2f7d262b176 100644
--- a/target/ppc/cpu_init.c
+++ b/target/ppc/cpu_init.c
@@ -7621,7 +7621,6 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
 {
 DeviceClass *dc = DEVICE_CLASS(oc);
 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
-CPUClass *cc = CPU_CLASS(oc);
 
 dc->fw_name = "PowerPC,POWER7";
 dc->desc = "POWER7";
@@ -7630,7 +7629,7 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
 pcc->pcr_supported = PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER7;
 pcc->check_pow = check_pow_nocheck;
-cc->has_work = cpu_has_work_POWER7;
+pcc->has_work = cpu_has_work_POWER7;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -7789,7 +7788,6 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
 {
 DeviceClass *dc = DEVICE_CLASS(oc);
 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
-CPUClass *cc = CPU_CLASS(oc);
 
 dc->fw_name = "PowerPC,POWER8";
 dc->desc = "POWER8";
@@ -7798,7 +7796,7 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
 pcc->pcr_supported = PCR_COMPAT_2_07 | PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER8;
 pcc->check_pow = check_pow_nocheck;
-cc->has_work = cpu_has_work_POWER8;
+pcc->has_work = cpu_has_work_POWER8;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -8003,7 +8001,6 @@ POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
 {
 DeviceClass *dc = DEVICE_CLASS(oc);
 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
-CPUClass *cc = CPU_CLASS(oc);
 
 dc->fw_name = "PowerPC,POWER9";
 dc->desc = "POWER9";
@@ -8013,7 +8010,7 @@ POWERPC_FAMILY(POWER9)(ObjectClass *oc, void *data)
  PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER9;
 pcc->check_pow = check_pow_nocheck;
-cc->has_work = cpu_has_work_POWER9;
+pcc->has_work = cpu_has_work_POWER9;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -8212,7 +8209,6 @@ POWERPC_FAMILY(POWER10)(ObjectClass *oc, void *data)
 {
 DeviceClass *dc = DEVICE_CLASS(oc);
 PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
-CPUClass *cc = CPU_CLASS(oc);
 
 dc->fw_name = "PowerPC,POWER10";
 dc->desc = "POWER10";
@@ -8223,7 +8219,7 @@ POWERPC_FAMILY(POWER10)(ObjectClass *oc, void *data)
  PCR_COMPAT_2_06 | PCR_COMPAT_2_05;
 pcc->init_proc = init_proc_POWER10;
 pcc->check_pow = check_pow_nocheck;
-cc->has_work = cpu_has_work_POWER10;
+pcc->has_work = cpu_has_work_POWER10;
 pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
@@ -8790,7 +8786,7 @@ static void ppc_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.nip = value;
 }
 
-static bool ppc_cpu_has_work(CPUState *cs)
+static bool cpu_has_work_default(CPUState *cs)
 {
 PowerPCCPU *cpu = POWERPC_CPU(cs);
 CPUPPCState *env = >env;
@@ -8798,6 +8794,14 @@ static bool ppc_cpu_has_work(CPUState *cs)
 return msr_ee && (cs->interrupt_request & CPU_INTERRUPT_HARD);
 }
 
+static bool ppc_cpu_has_work(CPUState *cs)
+{
+PowerPCCPU *cpu = POWERPC_CPU(cs);
+PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
+
+return pcc->has_work(cs);
+}
+
 static void ppc_cpu_reset(DeviceState *dev)
 {
 CPUState *s = CPU(dev);
@@ -9037,6 +9041,7 @@ static void ppc_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_unrealize(dc, 

Re: [PATCH v4 10/20] nubus-device: remove nubus_register_rom() and nubus_register_format_block()

2021-09-20 Thread Laurent Vivier
Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
> Since there is no need to generate a dummy declaration ROM, remove both
> nubus_register_rom() and nubus_register_format_block(). These will shortly be
> replaced with a mechanism to optionally load a declaration ROM from disk to
> allow real images to be used within QEMU.
> 
> Signed-off-by: Mark Cave-Ayland 
> ---
>  hw/nubus/nubus-device.c  | 143 ---
>  include/hw/nubus/nubus.h |  19 --
>  2 files changed, 162 deletions(-)
> 
> diff --git a/hw/nubus/nubus-device.c b/hw/nubus/nubus-device.c
> index 7a32c8c95b..9c1992ceb0 100644
> --- a/hw/nubus/nubus-device.c
> +++ b/hw/nubus/nubus-device.c
> @@ -13,147 +13,6 @@
>  #include "qapi/error.h"
>  
>  
> -/* The Format Block Structure */
> -
> -#define FBLOCK_DIRECTORY_OFFSET 0
> -#define FBLOCK_LENGTH   4
> -#define FBLOCK_CRC  8
> -#define FBLOCK_REVISION_LEVEL   12
> -#define FBLOCK_FORMAT   13
> -#define FBLOCK_TEST_PATTERN 14
> -#define FBLOCK_RESERVED 18
> -#define FBLOCK_BYTE_LANES   19
> -
> -#define FBLOCK_SIZE 20
> -#define FBLOCK_PATTERN_VAL  0x5a932bc7
> -
> -static uint64_t nubus_fblock_read(void *opaque, hwaddr addr, unsigned int 
> size)
> -{
> -NubusDevice *dev = opaque;
> -uint64_t val;
> -
> -#define BYTE(v, b) (((v) >> (24 - 8 * (b))) & 0xff)
> -switch (addr) {
> -case FBLOCK_BYTE_LANES:
> -val = dev->byte_lanes;
> -val |= (val ^ 0xf) << 4;
> -break;
> -case FBLOCK_RESERVED:
> -val = 0x00;
> -break;
> -case FBLOCK_TEST_PATTERN...FBLOCK_TEST_PATTERN + 3:
> -val = BYTE(FBLOCK_PATTERN_VAL, addr - FBLOCK_TEST_PATTERN);
> -break;
> -case FBLOCK_FORMAT:
> -val = dev->rom_format;
> -break;
> -case FBLOCK_REVISION_LEVEL:
> -val = dev->rom_rev;
> -break;
> -case FBLOCK_CRC...FBLOCK_CRC + 3:
> -val = BYTE(dev->rom_crc, addr - FBLOCK_CRC);
> -break;
> -case FBLOCK_LENGTH...FBLOCK_LENGTH + 3:
> -val = BYTE(dev->rom_length, addr - FBLOCK_LENGTH);
> -break;
> -case FBLOCK_DIRECTORY_OFFSET...FBLOCK_DIRECTORY_OFFSET + 3:
> -val = BYTE(dev->directory_offset, addr - FBLOCK_DIRECTORY_OFFSET);
> -break;
> -default:
> -val = 0;
> -break;
> -}
> -return val;
> -}
> -
> -static void nubus_fblock_write(void *opaque, hwaddr addr, uint64_t val,
> -   unsigned int size)
> -{
> -/* read only */
> -}
> -
> -static const MemoryRegionOps nubus_format_block_ops = {
> -.read = nubus_fblock_read,
> -.write = nubus_fblock_write,
> -.endianness = DEVICE_BIG_ENDIAN,
> -.valid = {
> -.min_access_size = 1,
> -.max_access_size = 1,
> -}
> -};
> -
> -static void nubus_register_format_block(NubusDevice *dev)
> -{
> -char *fblock_name;
> -
> -fblock_name = g_strdup_printf("nubus-slot-%d-format-block",
> -  dev->slot);
> -
> -hwaddr fblock_offset = memory_region_size(>slot_mem) - FBLOCK_SIZE;
> -memory_region_init_io(>fblock_io, NULL, _format_block_ops,
> -  dev, fblock_name, FBLOCK_SIZE);
> -memory_region_add_subregion(>slot_mem, fblock_offset,
> ->fblock_io);
> -
> -g_free(fblock_name);
> -}
> -
> -static void mac_nubus_rom_write(void *opaque, hwaddr addr, uint64_t val,
> -   unsigned int size)
> -{
> -/* read only */
> -}
> -
> -static uint64_t mac_nubus_rom_read(void *opaque, hwaddr addr,
> -unsigned int size)
> -{
> -NubusDevice *dev = opaque;
> -
> -return dev->rom[addr];
> -}
> -
> -static const MemoryRegionOps mac_nubus_rom_ops = {
> -.read  = mac_nubus_rom_read,
> -.write = mac_nubus_rom_write,
> -.endianness = DEVICE_BIG_ENDIAN,
> -.valid = {
> -.min_access_size = 1,
> -.max_access_size = 1,
> -},
> -};
> -
> -
> -void nubus_register_rom(NubusDevice *dev, const uint8_t *rom, uint32_t size,
> -int revision, int format, uint8_t byte_lanes)
> -{
> -hwaddr rom_offset;
> -char *rom_name;
> -
> -/* FIXME : really compute CRC */
> -dev->rom_length = 0;
> -dev->rom_crc = 0;
> -
> -dev->rom_rev = revision;
> -dev->rom_format = format;
> -
> -dev->byte_lanes = byte_lanes;
> -dev->directory_offset = -size;
> -
> -/* ROM */
> -
> -dev->rom = rom;
> -rom_name = g_strdup_printf("nubus-slot-%d-rom", dev->slot);
> -memory_region_init_io(>rom_io, NULL, _nubus_rom_ops,
> -  dev, rom_name, size);
> -memory_region_set_readonly(>rom_io, true);
> -
> -rom_offset = memory_region_size(>slot_mem) - FBLOCK_SIZE +
> - dev->directory_offset;
> -memory_region_add_subregion(>slot_mem, rom_offset, >rom_io);
> -
> -

[PATCH v5 06/31] accel/kvm: Implement AccelOpsClass::has_work()

2021-09-20 Thread Philippe Mathieu-Daudé
Implement KVM has_work() handler in AccelOpsClass and
remove it from cpu_thread_is_idle() since cpu_has_work()
is already called.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 accel/kvm/kvm-accel-ops.c | 6 ++
 softmmu/cpus.c| 2 +-
 2 files changed, 7 insertions(+), 1 deletion(-)

diff --git a/accel/kvm/kvm-accel-ops.c b/accel/kvm/kvm-accel-ops.c
index 7516c67a3f5..6f4d5df3a0d 100644
--- a/accel/kvm/kvm-accel-ops.c
+++ b/accel/kvm/kvm-accel-ops.c
@@ -74,6 +74,11 @@ static void kvm_start_vcpu_thread(CPUState *cpu)
cpu, QEMU_THREAD_JOINABLE);
 }
 
+static bool kvm_cpu_has_work(CPUState *cpu)
+{
+return kvm_halt_in_kernel();
+}
+
 static void kvm_accel_ops_class_init(ObjectClass *oc, void *data)
 {
 AccelOpsClass *ops = ACCEL_OPS_CLASS(oc);
@@ -83,6 +88,7 @@ static void kvm_accel_ops_class_init(ObjectClass *oc, void 
*data)
 ops->synchronize_post_init = kvm_cpu_synchronize_post_init;
 ops->synchronize_state = kvm_cpu_synchronize_state;
 ops->synchronize_pre_loadvm = kvm_cpu_synchronize_pre_loadvm;
+ops->has_work = kvm_cpu_has_work;
 }
 
 static const TypeInfo kvm_accel_ops_type = {
diff --git a/softmmu/cpus.c b/softmmu/cpus.c
index e59046ce39c..b22804c4193 100644
--- a/softmmu/cpus.c
+++ b/softmmu/cpus.c
@@ -90,7 +90,7 @@ bool cpu_thread_is_idle(CPUState *cpu)
 return true;
 }
 if (!cpu->halted || cpu_has_work(cpu) ||
-kvm_halt_in_kernel() || whpx_apic_in_platform()) {
+whpx_apic_in_platform()) {
 return false;
 }
 return true;
-- 
2.31.1




[PATCH v5 25/31] target/s390x: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to TCG sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/s390x/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/s390x/cpu.c b/target/s390x/cpu.c
index 7b7b05f1d3a..df8ade9021d 100644
--- a/target/s390x/cpu.c
+++ b/target/s390x/cpu.c
@@ -88,6 +88,7 @@ static void s390_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.psw.addr = value;
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool s390_cpu_has_work(CPUState *cs)
 {
 S390CPU *cpu = S390_CPU(cs);
@@ -104,6 +105,7 @@ static bool s390_cpu_has_work(CPUState *cs)
 
 return s390_cpu_has_int(cpu);
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 /* S390CPUClass::reset() */
 static void s390_cpu_reset(CPUState *s, cpu_reset_type type)
@@ -269,6 +271,7 @@ static const struct TCGCPUOps s390_tcg_ops = {
 .tlb_fill = s390_cpu_tlb_fill,
 
 #if !defined(CONFIG_USER_ONLY)
+.has_work = s390_cpu_has_work,
 .cpu_exec_interrupt = s390_cpu_exec_interrupt,
 .do_interrupt = s390_cpu_do_interrupt,
 .debug_excp_handler = s390x_cpu_debug_excp_handler,
@@ -292,7 +295,6 @@ static void s390_cpu_class_init(ObjectClass *oc, void *data)
 
 scc->reset = s390_cpu_reset;
 cc->class_by_name = s390_cpu_class_by_name,
-cc->has_work = s390_cpu_has_work;
 cc->dump_state = s390_cpu_dump_state;
 cc->set_pc = s390_cpu_set_pc;
 cc->gdb_read_register = s390_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 04/31] hw/core: Un-inline cpu_has_work()

2021-09-20 Thread Philippe Mathieu-Daudé
We want to make cpu_has_work() per-accelerator. Only declare its
prototype and move its definition to softmmu/cpus.c.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 include/hw/core/cpu.h | 8 +---
 softmmu/cpus.c| 8 
 2 files changed, 9 insertions(+), 7 deletions(-)

diff --git a/include/hw/core/cpu.h b/include/hw/core/cpu.h
index 2bd563e221f..e2dd171a13f 100644
--- a/include/hw/core/cpu.h
+++ b/include/hw/core/cpu.h
@@ -546,13 +546,7 @@ void cpu_dump_state(CPUState *cpu, FILE *f, int flags);
  *
  * Returns: %true if the CPU has work, %false otherwise.
  */
-static inline bool cpu_has_work(CPUState *cpu)
-{
-CPUClass *cc = CPU_GET_CLASS(cpu);
-
-g_assert(cc->has_work);
-return cc->has_work(cpu);
-}
+bool cpu_has_work(CPUState *cpu);
 
 /**
  * cpu_get_phys_page_attrs_debug:
diff --git a/softmmu/cpus.c b/softmmu/cpus.c
index 071085f840b..7e2cb2c571b 100644
--- a/softmmu/cpus.c
+++ b/softmmu/cpus.c
@@ -251,6 +251,14 @@ void cpu_interrupt(CPUState *cpu, int mask)
 }
 }
 
+bool cpu_has_work(CPUState *cpu)
+{
+CPUClass *cc = CPU_GET_CLASS(cpu);
+
+g_assert(cc->has_work);
+return cc->has_work(cpu);
+}
+
 static int do_vm_stop(RunState state, bool send_stop)
 {
 int ret = 0;
-- 
2.31.1




[PATCH v5 14/31] target/hppa: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/hppa/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/hppa/cpu.c b/target/hppa/cpu.c
index e8edd189bfc..be940ae2246 100644
--- a/target/hppa/cpu.c
+++ b/target/hppa/cpu.c
@@ -60,10 +60,12 @@ static void hppa_cpu_synchronize_from_tb(CPUState *cs,
 cpu->env.psw_n = (tb->flags & PSW_N) != 0;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool hppa_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & CPU_INTERRUPT_HARD;
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void hppa_cpu_disas_set_info(CPUState *cs, disassemble_info *info)
 {
@@ -147,6 +149,7 @@ static const struct TCGCPUOps hppa_tcg_ops = {
 .tlb_fill = hppa_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = hppa_cpu_has_work,
 .cpu_exec_interrupt = hppa_cpu_exec_interrupt,
 .do_interrupt = hppa_cpu_do_interrupt,
 .do_unaligned_access = hppa_cpu_do_unaligned_access,
@@ -163,7 +166,6 @@ static void hppa_cpu_class_init(ObjectClass *oc, void *data)
 >parent_realize);
 
 cc->class_by_name = hppa_cpu_class_by_name;
-cc->has_work = hppa_cpu_has_work;
 cc->dump_state = hppa_cpu_dump_state;
 cc->set_pc = hppa_cpu_set_pc;
 cc->gdb_read_register = hppa_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 05/31] sysemu: Introduce AccelOpsClass::has_work()

2021-09-20 Thread Philippe Mathieu-Daudé
Introduce an accelerator-specific has_work() handler.
Eventually call it from cpu_has_work().

Signed-off-by: Philippe Mathieu-Daudé 
---
 include/sysemu/accel-ops.h | 5 +
 softmmu/cpus.c | 9 +++--
 2 files changed, 12 insertions(+), 2 deletions(-)

diff --git a/include/sysemu/accel-ops.h b/include/sysemu/accel-ops.h
index 032f6979d76..de83f095f20 100644
--- a/include/sysemu/accel-ops.h
+++ b/include/sysemu/accel-ops.h
@@ -31,6 +31,11 @@ struct AccelOpsClass {
 void (*create_vcpu_thread)(CPUState *cpu); /* MANDATORY NON-NULL */
 void (*kick_vcpu_thread)(CPUState *cpu);
 
+/**
+ * @has_work: Callback for checking if there is work to do.
+ */
+bool (*has_work)(CPUState *cpu);
+
 void (*synchronize_post_reset)(CPUState *cpu);
 void (*synchronize_post_init)(CPUState *cpu);
 void (*synchronize_state)(CPUState *cpu);
diff --git a/softmmu/cpus.c b/softmmu/cpus.c
index 7e2cb2c571b..e59046ce39c 100644
--- a/softmmu/cpus.c
+++ b/softmmu/cpus.c
@@ -255,8 +255,13 @@ bool cpu_has_work(CPUState *cpu)
 {
 CPUClass *cc = CPU_GET_CLASS(cpu);
 
-g_assert(cc->has_work);
-return cc->has_work(cpu);
+if (cc->has_work) {
+return cc->has_work(cpu);
+}
+if (cpus_accel->has_work) {
+return cpus_accel->has_work(cpu);
+}
+g_assert_not_reached();
 }
 
 static int do_vm_stop(RunState state, bool send_stop)
-- 
2.31.1




[PATCH v5 03/31] hw/core: Restrict cpu_has_work() to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
cpu_has_work() is only called from system emulation code.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 include/hw/core/cpu.h | 32 
 1 file changed, 16 insertions(+), 16 deletions(-)

diff --git a/include/hw/core/cpu.h b/include/hw/core/cpu.h
index bc864564cee..2bd563e221f 100644
--- a/include/hw/core/cpu.h
+++ b/include/hw/core/cpu.h
@@ -538,6 +538,22 @@ enum CPUDumpFlags {
 void cpu_dump_state(CPUState *cpu, FILE *f, int flags);
 
 #ifndef CONFIG_USER_ONLY
+/**
+ * cpu_has_work:
+ * @cpu: The vCPU to check.
+ *
+ * Checks whether the CPU has work to do.
+ *
+ * Returns: %true if the CPU has work, %false otherwise.
+ */
+static inline bool cpu_has_work(CPUState *cpu)
+{
+CPUClass *cc = CPU_GET_CLASS(cpu);
+
+g_assert(cc->has_work);
+return cc->has_work(cpu);
+}
+
 /**
  * cpu_get_phys_page_attrs_debug:
  * @cpu: The CPU to obtain the physical page address for.
@@ -636,22 +652,6 @@ CPUState *cpu_create(const char *typename);
  */
 const char *parse_cpu_option(const char *cpu_option);
 
-/**
- * cpu_has_work:
- * @cpu: The vCPU to check.
- *
- * Checks whether the CPU has work to do.
- *
- * Returns: %true if the CPU has work, %false otherwise.
- */
-static inline bool cpu_has_work(CPUState *cpu)
-{
-CPUClass *cc = CPU_GET_CLASS(cpu);
-
-g_assert(cc->has_work);
-return cc->has_work(cpu);
-}
-
 /**
  * qemu_cpu_is_self:
  * @cpu: The vCPU to check against.
-- 
2.31.1




[PATCH v5 11/31] target/avr: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/avr/cpu.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/target/avr/cpu.c b/target/avr/cpu.c
index 5d70e34dd54..6d51f91ca2c 100644
--- a/target/avr/cpu.c
+++ b/target/avr/cpu.c
@@ -195,6 +195,7 @@ static const struct SysemuCPUOps avr_sysemu_ops = {
 static const struct TCGCPUOps avr_tcg_ops = {
 .initialize = avr_cpu_tcg_init,
 .synchronize_from_tb = avr_cpu_synchronize_from_tb,
+.has_work = avr_cpu_has_work,
 .cpu_exec_interrupt = avr_cpu_exec_interrupt,
 .tlb_fill = avr_cpu_tlb_fill,
 .do_interrupt = avr_cpu_do_interrupt,
@@ -211,7 +212,6 @@ static void avr_cpu_class_init(ObjectClass *oc, void *data)
 
 cc->class_by_name = avr_cpu_class_by_name;
 
-cc->has_work = avr_cpu_has_work;
 cc->dump_state = avr_cpu_dump_state;
 cc->set_pc = avr_cpu_set_pc;
 cc->memory_rw_debug = avr_cpu_memory_rw_debug;
-- 
2.31.1




[PATCH v5 23/31] target/riscv: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to TCG sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/riscv/cpu.c | 8 +++-
 1 file changed, 3 insertions(+), 5 deletions(-)

diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
index 13575c14085..abb555a8bdb 100644
--- a/target/riscv/cpu.c
+++ b/target/riscv/cpu.c
@@ -335,9 +335,9 @@ static void riscv_cpu_synchronize_from_tb(CPUState *cs,
 env->pc = tb->pc;
 }
 
+#if defined(CONFIG_TCG) && !defined(CONFIG_USER_ONLY)
 static bool riscv_cpu_has_work(CPUState *cs)
 {
-#ifndef CONFIG_USER_ONLY
 RISCVCPU *cpu = RISCV_CPU(cs);
 CPURISCVState *env = >env;
 /*
@@ -345,10 +345,8 @@ static bool riscv_cpu_has_work(CPUState *cs)
  * mode and delegation registers, but respect individual enables
  */
 return (env->mip & env->mie) != 0;
-#else
-return true;
-#endif
 }
+#endif /* CONFIG_TCG && !CONFIG_USER_ONLY */
 
 void restore_state_to_opc(CPURISCVState *env, TranslationBlock *tb,
   target_ulong *data)
@@ -647,6 +645,7 @@ static const struct TCGCPUOps riscv_tcg_ops = {
 .tlb_fill = riscv_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = riscv_cpu_has_work,
 .cpu_exec_interrupt = riscv_cpu_exec_interrupt,
 .do_interrupt = riscv_cpu_do_interrupt,
 .do_transaction_failed = riscv_cpu_do_transaction_failed,
@@ -666,7 +665,6 @@ static void riscv_cpu_class_init(ObjectClass *c, void *data)
 device_class_set_parent_reset(dc, riscv_cpu_reset, >parent_reset);
 
 cc->class_by_name = riscv_cpu_class_by_name;
-cc->has_work = riscv_cpu_has_work;
 cc->dump_state = riscv_cpu_dump_state;
 cc->set_pc = riscv_cpu_set_pc;
 cc->gdb_read_register = riscv_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 01/31] target/arm: Implement arm_v7m_cpu_has_work()

2021-09-20 Thread Philippe Mathieu-Daudé
Implement SysemuCPUOps::has_work() handler for the ARM v7M CPU.

See the comments added in commit 7ecdaa4a963 ("armv7m: Fix
condition check for taking exceptions") which eventually
forgot to implement this has_work() handler:

  * ARMv7-M interrupt masking works differently than -A or -R.
  * There is no FIQ/IRQ distinction.

The NVIC signal any pending interrupt by raising ARM_CPU_IRQ
(see commit 56b7c66f498: "armv7m: QOMify the armv7m container")
which ends setting the CPU_INTERRUPT_HARD bit in interrupt_request.

Thus arm_v7m_cpu_has_work() implementation is thus quite trivial,
we simply need to check for this bit.

Cc: Peter Maydell 
Cc: Michael Davidsaver 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/arm/cpu_tcg.c | 6 ++
 1 file changed, 6 insertions(+)

diff --git a/target/arm/cpu_tcg.c b/target/arm/cpu_tcg.c
index 0d5adccf1a7..da348938407 100644
--- a/target/arm/cpu_tcg.c
+++ b/target/arm/cpu_tcg.c
@@ -23,6 +23,11 @@
 #if !defined(CONFIG_USER_ONLY) || !defined(TARGET_AARCH64)
 
 #if !defined(CONFIG_USER_ONLY) && defined(CONFIG_TCG)
+static bool arm_v7m_cpu_has_work(CPUState *cs)
+{
+return cs->interrupt_request & CPU_INTERRUPT_HARD;
+}
+
 static bool arm_v7m_cpu_exec_interrupt(CPUState *cs, int interrupt_request)
 {
 CPUClass *cc = CPU_GET_CLASS(cs);
@@ -920,6 +925,7 @@ static void arm_v7m_class_init(ObjectClass *oc, void *data)
 
 acc->info = data;
 #ifdef CONFIG_TCG
+cc->has_work = arm_v7m_cpu_has_work;
 cc->tcg_ops = _v7m_tcg_ops;
 #endif /* CONFIG_TCG */
 
-- 
2.31.1




[PATCH v5 19/31] target/nios2: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/nios2/cpu.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/target/nios2/cpu.c b/target/nios2/cpu.c
index 947bb09bc1e..9938d7c2919 100644
--- a/target/nios2/cpu.c
+++ b/target/nios2/cpu.c
@@ -34,10 +34,12 @@ static void nios2_cpu_set_pc(CPUState *cs, vaddr value)
 env->regs[R_PC] = value;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool nios2_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & (CPU_INTERRUPT_HARD | CPU_INTERRUPT_NMI);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void nios2_cpu_reset(DeviceState *dev)
 {
@@ -223,6 +225,7 @@ static const struct TCGCPUOps nios2_tcg_ops = {
 .tlb_fill = nios2_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = nios2_cpu_has_work,
 .cpu_exec_interrupt = nios2_cpu_exec_interrupt,
 .do_interrupt = nios2_cpu_do_interrupt,
 .do_unaligned_access = nios2_cpu_do_unaligned_access,
@@ -241,7 +244,6 @@ static void nios2_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_reset(dc, nios2_cpu_reset, >parent_reset);
 
 cc->class_by_name = nios2_cpu_class_by_name;
-cc->has_work = nios2_cpu_has_work;
 cc->dump_state = nios2_cpu_dump_state;
 cc->set_pc = nios2_cpu_set_pc;
 cc->disas_set_info = nios2_cpu_disas_set_info;
-- 
2.31.1




Re: [PATCH v4 09/20] macfb: don't register declaration ROM

2021-09-20 Thread Laurent Vivier
Le 20/09/2021 à 22:01, Laurent Vivier a écrit :
> Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
>> The macfb device is an on-board framebuffer and so is initialised by the
>> system declaration ROM included within the MacOS toolbox ROM.
>>
>> Signed-off-by: Mark Cave-Ayland 
>> ---
>>  hw/display/macfb.c | 6 --
>>  1 file changed, 6 deletions(-)
>>
>> diff --git a/hw/display/macfb.c b/hw/display/macfb.c
>> index d8183b9bbd..76808b69cc 100644
>> --- a/hw/display/macfb.c
>> +++ b/hw/display/macfb.c
>> @@ -383,10 +383,6 @@ static void macfb_sysbus_realize(DeviceState *dev, 
>> Error **errp)
>>  sysbus_init_mmio(SYS_BUS_DEVICE(s), >mem_vram);
>>  }
>>  
>> -const uint8_t macfb_rom[] = {
>> -255, 0, 0, 0,
>> -};
>> -
>>  static void macfb_nubus_realize(DeviceState *dev, Error **errp)
>>  {
>>  NubusDevice *nd = NUBUS_DEVICE(dev);
>> @@ -399,8 +395,6 @@ static void macfb_nubus_realize(DeviceState *dev, Error 
>> **errp)
>>  macfb_common_realize(dev, ms, errp);
>>  memory_region_add_subregion(>slot_mem, DAFB_BASE, >mem_ctrl);
>>  memory_region_add_subregion(>slot_mem, VIDEO_BASE, >mem_vram);
>> -
>> -nubus_register_rom(nd, macfb_rom, sizeof(macfb_rom), 1, 9, 0xf);
>>  }
>>  
>>  static void macfb_sysbus_reset(DeviceState *d)
>>
> 
> Will macfb continue to work with "-kernel" and without providing any MacOS 
> ROM?

My Quadra doesn't seem to report any ROM on boot, so it must be fine

Reviewed-by: Laurent Vivier 



[PATCH v5 10/31] target/arm: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to TCG sysemu.

Signed-off-by: Philippe Mathieu-Daudé 
---
 target/arm/cpu.c | 7 +--
 target/arm/cpu_tcg.c | 2 +-
 2 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/target/arm/cpu.c b/target/arm/cpu.c
index ba0741b20e4..e11aa625a5f 100644
--- a/target/arm/cpu.c
+++ b/target/arm/cpu.c
@@ -73,8 +73,8 @@ void arm_cpu_synchronize_from_tb(CPUState *cs,
 env->regs[15] = tb->pc;
 }
 }
-#endif /* CONFIG_TCG */
 
+#ifndef CONFIG_USER_ONLY
 static bool arm_cpu_has_work(CPUState *cs)
 {
 ARMCPU *cpu = ARM_CPU(cs);
@@ -85,6 +85,9 @@ static bool arm_cpu_has_work(CPUState *cs)
  | CPU_INTERRUPT_VFIQ | CPU_INTERRUPT_VIRQ
  | CPU_INTERRUPT_EXITTB);
 }
+#endif /* !CONFIG_USER_ONLY */
+
+#endif /* CONFIG_TCG */
 
 void arm_register_pre_el_change_hook(ARMCPU *cpu, ARMELChangeHookFn *hook,
  void *opaque)
@@ -2017,6 +2020,7 @@ static const struct TCGCPUOps arm_tcg_ops = {
 .debug_excp_handler = arm_debug_excp_handler,
 
 #if !defined(CONFIG_USER_ONLY)
+.has_work = arm_cpu_has_work,
 .cpu_exec_interrupt = arm_cpu_exec_interrupt,
 .do_interrupt = arm_cpu_do_interrupt,
 .do_transaction_failed = arm_cpu_do_transaction_failed,
@@ -2041,7 +2045,6 @@ static void arm_cpu_class_init(ObjectClass *oc, void 
*data)
 device_class_set_parent_reset(dc, arm_cpu_reset, >parent_reset);
 
 cc->class_by_name = arm_cpu_class_by_name;
-cc->has_work = arm_cpu_has_work;
 cc->dump_state = arm_cpu_dump_state;
 cc->set_pc = arm_cpu_set_pc;
 cc->gdb_read_register = arm_cpu_gdb_read_register;
diff --git a/target/arm/cpu_tcg.c b/target/arm/cpu_tcg.c
index da348938407..a3df208249a 100644
--- a/target/arm/cpu_tcg.c
+++ b/target/arm/cpu_tcg.c
@@ -907,6 +907,7 @@ static const struct TCGCPUOps arm_v7m_tcg_ops = {
 .debug_excp_handler = arm_debug_excp_handler,
 
 #if !defined(CONFIG_USER_ONLY)
+.has_work = arm_v7m_cpu_has_work,
 .cpu_exec_interrupt = arm_v7m_cpu_exec_interrupt,
 .do_interrupt = arm_v7m_cpu_do_interrupt,
 .do_transaction_failed = arm_cpu_do_transaction_failed,
@@ -925,7 +926,6 @@ static void arm_v7m_class_init(ObjectClass *oc, void *data)
 
 acc->info = data;
 #ifdef CONFIG_TCG
-cc->has_work = arm_v7m_cpu_has_work;
 cc->tcg_ops = _v7m_tcg_ops;
 #endif /* CONFIG_TCG */
 
-- 
2.31.1




Re: [PATCH v3 2/3] monitor/hmp: add support for flag argument with value

2021-09-20 Thread Eric Blake
On Mon, Sep 20, 2021 at 12:56:40PM +0200, Stefan Reiter wrote:
> Adds support for the "-xS" parameter type, where "-x" denotes a flag
> name and the "S" suffix indicates that this flag is supposed to take an
> arbitrary string parameter.
> 
> These parameters are always optional, the entry in the qdict will be
> omitted if the flag is not given.
> 
> Signed-off-by: Stefan Reiter 
> ---
>  monitor/hmp.c | 17 -
>  1 file changed, 16 insertions(+), 1 deletion(-)

Looks like yet another hack on top of our existing pile of hacks, but
it is cleaner in v3 than it was in v2, and I'm not coming up with
anything better.

> 
> diff --git a/monitor/hmp.c b/monitor/hmp.c
> index d50c3124e1..a32dce7a35 100644
> --- a/monitor/hmp.c
> +++ b/monitor/hmp.c
> @@ -980,6 +980,7 @@ static QDict *monitor_parse_arguments(Monitor *mon,
>  {
>  const char *tmp = p;
>  int skip_key = 0;
> +int ret;
>  /* option */
>  
>  c = *typestr++;
> @@ -1002,8 +1003,22 @@ static QDict *monitor_parse_arguments(Monitor *mon,
>  }
>  if (skip_key) {
>  p = tmp;
> +} else if (*typestr == 'S') {
> +/* has option with string value */
> +typestr++;
> +tmp = p++;
> +while (qemu_isspace(*p)) {
> +p++;
> +}
> +ret = get_str(buf, sizeof(buf), );
> +if (ret < 0) {
> +monitor_printf(mon, "%s: value expected for 
> -%c\n",
> +   cmd->name, *tmp);
> +goto fail;
> +}
> +qdict_put_str(qdict, key, buf);

Do we have any documentation that also needs a matching update?  Or is
our documentation for the pseudo-grammar of .hx parsing limited to the
code?

>  } else {
> -/* has option */
> +/* has boolean option */
>  p++;
>  qdict_put_bool(qdict, key, true);
>  }

Holding my nose a bit, but only because of the mess that this already
is, not because of what you added.

Reviewed-by: Eric Blake 

-- 
Eric Blake, Principal Software Engineer
Red Hat, Inc.   +1-919-301-3266
Virtualization:  qemu.org | libvirt.org




[PATCH v5 17/31] target/microblaze: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/microblaze/cpu.c | 8 
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/target/microblaze/cpu.c b/target/microblaze/cpu.c
index 15db277925f..36e6e540483 100644
--- a/target/microblaze/cpu.c
+++ b/target/microblaze/cpu.c
@@ -92,12 +92,13 @@ static void mb_cpu_synchronize_from_tb(CPUState *cs,
 cpu->env.iflags = tb->flags & IFLAGS_TB_MASK;
 }
 
+#ifndef CONFIG_USER_ONLY
+
 static bool mb_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & (CPU_INTERRUPT_HARD | CPU_INTERRUPT_NMI);
 }
 
-#ifndef CONFIG_USER_ONLY
 static void mb_cpu_ns_axi_dp(void *opaque, int irq, int level)
 {
 MicroBlazeCPU *cpu = opaque;
@@ -142,7 +143,7 @@ static void microblaze_cpu_set_irq(void *opaque, int irq, 
int level)
 cpu_reset_interrupt(cs, type);
 }
 }
-#endif
+#endif /* !CONFIG_USER_ONLY */
 
 static void mb_cpu_reset(DeviceState *dev)
 {
@@ -368,6 +369,7 @@ static const struct TCGCPUOps mb_tcg_ops = {
 .tlb_fill = mb_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = mb_cpu_has_work,
 .cpu_exec_interrupt = mb_cpu_exec_interrupt,
 .do_interrupt = mb_cpu_do_interrupt,
 .do_transaction_failed = mb_cpu_transaction_failed,
@@ -386,8 +388,6 @@ static void mb_cpu_class_init(ObjectClass *oc, void *data)
 device_class_set_parent_reset(dc, mb_cpu_reset, >parent_reset);
 
 cc->class_by_name = mb_cpu_class_by_name;
-cc->has_work = mb_cpu_has_work;
-
 cc->dump_state = mb_cpu_dump_state;
 cc->set_pc = mb_cpu_set_pc;
 cc->gdb_read_register = mb_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v5 00/31] accel: Move has_work() from SysemuCPUOps to AccelOpsClass

2021-09-20 Thread Philippe Mathieu-Daudé
Missing review:
- 0001-target-arm-Implement-arm_v7m_cpu_has_work.patch
- 0005-sysemu-Introduce-AccelOpsClass-has_work.patch
- 0008-accel-tcg-Implement-AccelOpsClass-has_work-as-stub.patch
- 0010-target-arm-Restrict-has_work-handler-to-sysemu-and-T.patch
- 0012-target-cris-Restrict-has_work-handler-to-sysemu.patch

Hi,

CPU has_work() is a per-accelerator handler. This series
- explicit the KVM / WHPX implementations
- moves TCG implementations in AccelOpsClass
- explicit missing implementations (returning 'false').

Since v4:
- Implement arm_v7m_cpu_has_work() (new patch)
- Assert has_work() handlers are set, don't use default value
- Fix ARM v7M and cris CPUs
- Reset R-b tags on modified patches

Since v3:
- Remove pointless CONFIG_TCG uses (rth)
- Rework PPC patches, still using indirection

Since v2:
- Full rewrite, no more RFC.

$ git backport-diff v3..v4
[] : patches are identical
[] : number of functional differences between upstream/downstream patch
[down] : patch is downstream-only
The flags [FC] indicate (F)unctional and (C)ontextual differences, respectively

001/31:[down] 'target/arm: Implement arm_v7m_cpu_has_work()'
002/31:[] [--] 'accel/tcg: Restrict cpu_handle_halt() to sysemu'
003/31:[] [--] 'hw/core: Restrict cpu_has_work() to sysemu'
004/31:[] [--] 'hw/core: Un-inline cpu_has_work()'
005/31:[0006] [FC] 'sysemu: Introduce AccelOpsClass::has_work()'
006/31:[] [--] 'accel/kvm: Implement AccelOpsClass::has_work()'
007/31:[] [--] 'accel/whpx: Implement AccelOpsClass::has_work()'
008/31:[0004] [FC] 'accel/tcg: Implement AccelOpsClass::has_work() as stub'
009/31:[] [--] 'target/alpha: Restrict has_work() handler to sysemu'
010/31:[0002] [FC] 'target/arm: Restrict has_work() handler to sysemu and TCG'
011/31:[] [--] 'target/avr: Restrict has_work() handler to sysemu'
012/31:[0001] [FC] 'target/cris: Restrict has_work() handler to sysemu'
013/31:[] [--] 'target/hexagon: Remove unused has_work() handler'
014/31:[] [--] 'target/hppa: Restrict has_work() handler to sysemu'
015/31:[] [--] 'target/i386: Restrict has_work() handler to sysemu and TCG'
016/31:[] [--] 'target/m68k: Restrict has_work() handler to sysemu'
017/31:[] [--] 'target/microblaze: Restrict has_work() handler to sysemu'
018/31:[] [--] 'target/mips: Restrict has_work() handler to sysemu and TCG'
019/31:[] [--] 'target/nios2: Restrict has_work() handler to sysemu'
020/31:[] [--] 'target/openrisc: Restrict has_work() handler to sysemu'
021/31:[] [--] 'target/ppc: Introduce PowerPCCPUClass::has_work()'
022/31:[] [--] 'target/ppc: Restrict has_work() handlers to sysemu and TCG'
023/31:[] [--] 'target/riscv: Restrict has_work() handler to sysemu and TCG'
024/31:[] [--] 'target/rx: Restrict has_work() handler to sysemu'
025/31:[] [--] 'target/s390x: Restrict has_work() handler to sysemu and TCG'
026/31:[] [--] 'target/sh4: Restrict has_work() handler to sysemu'
027/31:[] [--] 'target/sparc: Remove pointless use of CONFIG_TCG definition'
028/31:[] [--] 'target/sparc: Restrict has_work() handler to sysemu'
029/31:[] [--] 'target/tricore: Restrict has_work() handler to sysemu'
030/31:[] [--] 'target/xtensa: Restrict has_work() handler to sysemu'
031/31:[0006] [FC] 'accel: Add missing AccelOpsClass::has_work() and drop 
SysemuCPUOps one'

Philippe Mathieu-Daudé (31):
  target/arm: Implement arm_v7m_cpu_has_work()
  accel/tcg: Restrict cpu_handle_halt() to sysemu
  hw/core: Restrict cpu_has_work() to sysemu
  hw/core: Un-inline cpu_has_work()
  sysemu: Introduce AccelOpsClass::has_work()
  accel/kvm: Implement AccelOpsClass::has_work()
  accel/whpx: Implement AccelOpsClass::has_work()
  accel/tcg: Implement AccelOpsClass::has_work() as stub
  target/alpha: Restrict has_work() handler to sysemu
  target/arm: Restrict has_work() handler to sysemu and TCG
  target/avr: Restrict has_work() handler to sysemu
  target/cris: Restrict has_work() handler to sysemu
  target/hexagon: Remove unused has_work() handler
  target/hppa: Restrict has_work() handler to sysemu
  target/i386: Restrict has_work() handler to sysemu and TCG
  target/m68k: Restrict has_work() handler to sysemu
  target/microblaze: Restrict has_work() handler to sysemu
  target/mips: Restrict has_work() handler to sysemu and TCG
  target/nios2: Restrict has_work() handler to sysemu
  target/openrisc: Restrict has_work() handler to sysemu
  target/ppc: Introduce PowerPCCPUClass::has_work()
  target/ppc: Restrict has_work() handlers to sysemu and TCG
  target/riscv: Restrict has_work() handler to sysemu and TCG
  target/rx: Restrict has_work() handler to sysemu
  target/s390x: Restrict has_work() handler to sysemu and TCG
  target/sh4: Restrict has_work() handler to sysemu
  target/sparc: Remove pointless use of CONFIG_TCG definition
  target/sparc: Restrict has_work() handler to sysemu
  target/tricore: Restrict has_work() handler to sysemu
  target/xtensa: Restrict has_work() 

[PATCH v5 08/31] accel/tcg: Implement AccelOpsClass::has_work() as stub

2021-09-20 Thread Philippe Mathieu-Daudé
Add TCG target-specific has_work() handler in TCGCPUOps,
and add tcg_cpu_has_work() as AccelOpsClass has_work()
implementation.

Signed-off-by: Philippe Mathieu-Daudé 
---
 include/hw/core/tcg-cpu-ops.h |  4 
 accel/tcg/tcg-accel-ops.c | 10 ++
 2 files changed, 14 insertions(+)

diff --git a/include/hw/core/tcg-cpu-ops.h b/include/hw/core/tcg-cpu-ops.h
index 55123cb4d22..4a4c4053e3b 100644
--- a/include/hw/core/tcg-cpu-ops.h
+++ b/include/hw/core/tcg-cpu-ops.h
@@ -66,6 +66,10 @@ struct TCGCPUOps {
 void (*do_interrupt)(CPUState *cpu);
 #endif /* !CONFIG_USER_ONLY || !TARGET_I386 */
 #ifdef CONFIG_SOFTMMU
+/**
+ * @has_work: Callback for checking if there is work to do.
+ */
+bool (*has_work)(CPUState *cpu);
 /** @cpu_exec_interrupt: Callback for processing interrupts in cpu_exec */
 bool (*cpu_exec_interrupt)(CPUState *cpu, int interrupt_request);
 /**
diff --git a/accel/tcg/tcg-accel-ops.c b/accel/tcg/tcg-accel-ops.c
index 1a8e8390bd6..f539ba53806 100644
--- a/accel/tcg/tcg-accel-ops.c
+++ b/accel/tcg/tcg-accel-ops.c
@@ -32,6 +32,7 @@
 #include "qemu/main-loop.h"
 #include "qemu/guest-random.h"
 #include "exec/exec-all.h"
+#include "hw/core/tcg-cpu-ops.h"
 
 #include "tcg-accel-ops.h"
 #include "tcg-accel-ops-mttcg.h"
@@ -73,6 +74,14 @@ int tcg_cpus_exec(CPUState *cpu)
 return ret;
 }
 
+static bool tcg_cpu_has_work(CPUState *cpu)
+{
+CPUClass *cc = CPU_GET_CLASS(cpu);
+
+g_assert(cc->tcg_ops->has_work);
+return cc->tcg_ops->has_work(cpu);
+}
+
 /* mask must never be zero, except for A20 change call */
 void tcg_handle_interrupt(CPUState *cpu, int mask)
 {
@@ -108,6 +117,7 @@ static void tcg_accel_ops_init(AccelOpsClass *ops)
 ops->kick_vcpu_thread = rr_kick_vcpu_thread;
 ops->handle_interrupt = tcg_handle_interrupt;
 }
+ops->has_work = tcg_cpu_has_work;
 }
 
 static void tcg_accel_ops_class_init(ObjectClass *oc, void *data)
-- 
2.31.1




[PATCH v5 15/31] target/i386: Restrict has_work() handler to sysemu and TCG

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to TCG sysemu.

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/i386/cpu.c | 6 --
 target/i386/tcg/tcg-cpu.c | 8 +++-
 2 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/target/i386/cpu.c b/target/i386/cpu.c
index 6b029f1bdf1..36a1c5f3fd2 100644
--- a/target/i386/cpu.c
+++ b/target/i386/cpu.c
@@ -6554,11 +6554,6 @@ int x86_cpu_pending_interrupt(CPUState *cs, int 
interrupt_request)
 return 0;
 }
 
-static bool x86_cpu_has_work(CPUState *cs)
-{
-return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
-}
-
 static void x86_disas_set_info(CPUState *cs, disassemble_info *info)
 {
 X86CPU *cpu = X86_CPU(cs);
@@ -6763,7 +6758,6 @@ static void x86_cpu_common_class_init(ObjectClass *oc, 
void *data)
 
 cc->class_by_name = x86_cpu_class_by_name;
 cc->parse_features = x86_cpu_parse_featurestr;
-cc->has_work = x86_cpu_has_work;
 cc->dump_state = x86_cpu_dump_state;
 cc->set_pc = x86_cpu_set_pc;
 cc->gdb_read_register = x86_cpu_gdb_read_register;
diff --git a/target/i386/tcg/tcg-cpu.c b/target/i386/tcg/tcg-cpu.c
index 3ecfae34cb5..aef050d0898 100644
--- a/target/i386/tcg/tcg-cpu.c
+++ b/target/i386/tcg/tcg-cpu.c
@@ -55,6 +55,11 @@ static void x86_cpu_synchronize_from_tb(CPUState *cs,
 }
 
 #ifndef CONFIG_USER_ONLY
+static bool x86_cpu_has_work(CPUState *cs)
+{
+return x86_cpu_pending_interrupt(cs, cs->interrupt_request) != 0;
+}
+
 static bool x86_debug_check_breakpoint(CPUState *cs)
 {
 X86CPU *cpu = X86_CPU(cs);
@@ -63,7 +68,7 @@ static bool x86_debug_check_breakpoint(CPUState *cs)
 /* RF disables all architectural breakpoints. */
 return !(env->eflags & RF_MASK);
 }
-#endif
+#endif /* CONFIG_USER_ONLY */
 
 #include "hw/core/tcg-cpu-ops.h"
 
@@ -76,6 +81,7 @@ static const struct TCGCPUOps x86_tcg_ops = {
 #ifdef CONFIG_USER_ONLY
 .fake_user_interrupt = x86_cpu_do_interrupt,
 #else
+.has_work = x86_cpu_has_work,
 .do_interrupt = x86_cpu_do_interrupt,
 .cpu_exec_interrupt = x86_cpu_exec_interrupt,
 .debug_excp_handler = breakpoint_handler,
-- 
2.31.1




[PATCH v3 25/30] Hexagon HVX (target/hexagon) instruction decoding

2021-09-20 Thread Taylor Simpson
Add new file to target/hexagon/meson.build

Signed-off-by: Taylor Simpson 
---
 target/hexagon/mmvec/decode_ext_mmvec.h |  24 
 target/hexagon/decode.c |  24 +++-
 target/hexagon/mmvec/decode_ext_mmvec.c | 236 
 target/hexagon/meson.build  |   1 +
 4 files changed, 283 insertions(+), 2 deletions(-)
 create mode 100644 target/hexagon/mmvec/decode_ext_mmvec.h
 create mode 100644 target/hexagon/mmvec/decode_ext_mmvec.c

diff --git a/target/hexagon/mmvec/decode_ext_mmvec.h 
b/target/hexagon/mmvec/decode_ext_mmvec.h
new file mode 100644
index 000..3664b68
--- /dev/null
+++ b/target/hexagon/mmvec/decode_ext_mmvec.h
@@ -0,0 +1,24 @@
+/*
+ *  Copyright(c) 2019-2021 Qualcomm Innovation Center, Inc. All Rights 
Reserved.
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, see .
+ */
+
+#ifndef HEXAGON_DECODE_EXT_MMVEC_H
+#define HEXAGON_DECODE_EXT_MMVEC_H
+
+void mmvec_ext_decode_checks(Packet *pkt, bool disas_only);
+SlotMask mmvec_ext_decode_find_iclass_slots(int opcode);
+
+#endif
diff --git a/target/hexagon/decode.c b/target/hexagon/decode.c
index d424245..653bfd7 100644
--- a/target/hexagon/decode.c
+++ b/target/hexagon/decode.c
@@ -22,6 +22,7 @@
 #include "decode.h"
 #include "insn.h"
 #include "printinsn.h"
+#include "mmvec/decode_ext_mmvec.h"
 
 #define fZXTN(N, M, VAL) ((VAL) & ((1LL << (N)) - 1))
 
@@ -566,8 +567,12 @@ static void decode_remove_extenders(Packet *packet)
 
 static SlotMask get_valid_slots(const Packet *pkt, unsigned int slot)
 {
-return find_iclass_slots(pkt->insn[slot].opcode,
- pkt->insn[slot].iclass);
+if (GET_ATTRIB(pkt->insn[slot].opcode, A_EXTENSION)) {
+return mmvec_ext_decode_find_iclass_slots(pkt->insn[slot].opcode);
+} else {
+return find_iclass_slots(pkt->insn[slot].opcode,
+ pkt->insn[slot].iclass);
+}
 }
 
 #define DECODE_NEW_TABLE(TAG, SIZE, WHATNOT) /* NOTHING */
@@ -728,6 +733,11 @@ decode_insns_tablewalk(Insn *insn, const DectreeTable 
*table,
 }
 decode_op(insn, opc, encoding);
 return 1;
+} else if (table->table[i].type == DECTREE_EXTSPACE) {
+/*
+ * For now, HVX will be the only coproc
+ */
+return decode_insns_tablewalk(insn, ext_trees[EXT_IDX_mmvec], 
encoding);
 } else {
 return 0;
 }
@@ -874,6 +884,7 @@ int decode_packet(int max_words, const uint32_t *words, 
Packet *pkt,
 int words_read = 0;
 bool end_of_packet = false;
 int new_insns = 0;
+int i;
 uint32_t encoding32;
 
 /* Initialize */
@@ -901,6 +912,11 @@ int decode_packet(int max_words, const uint32_t *words, 
Packet *pkt,
 return 0;
 }
 pkt->encod_pkt_size_in_bytes = words_read * 4;
+pkt->pkt_has_hvx = false;
+for (i = 0; i < num_insns; i++) {
+pkt->pkt_has_hvx |=
+GET_ATTRIB(pkt->insn[i].opcode, A_CVI);
+}
 
 /*
  * Check for :endloop in the parse bits
@@ -931,6 +947,10 @@ int decode_packet(int max_words, const uint32_t *words, 
Packet *pkt,
 decode_set_slot_number(pkt);
 decode_fill_newvalue_regno(pkt);
 
+if (pkt->pkt_has_hvx) {
+mmvec_ext_decode_checks(pkt, disas_only);
+}
+
 if (!disas_only) {
 decode_shuffle_for_execution(pkt);
 decode_split_cmpjump(pkt);
diff --git a/target/hexagon/mmvec/decode_ext_mmvec.c 
b/target/hexagon/mmvec/decode_ext_mmvec.c
new file mode 100644
index 000..061a65a
--- /dev/null
+++ b/target/hexagon/mmvec/decode_ext_mmvec.c
@@ -0,0 +1,236 @@
+/*
+ *  Copyright(c) 2019-2021 Qualcomm Innovation Center, Inc. All Rights 
Reserved.
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, see .
+ */
+
+#include "qemu/osdep.h"

Re: [PATCH v4 18/20] nubus: add support for slot IRQs

2021-09-20 Thread Laurent Vivier
Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
> Each Nubus slot has an IRQ line that can be used to request service from the
> CPU. Connect the IRQs to the Nubus bridge so that they can be wired up using 
> qdev
> gpios accordingly, and introduce a new nubus_set_irq() function that can be 
> used
> by Nubus devices to control the slot IRQ.
> 
> Signed-off-by: Mark Cave-Ayland 
> ---
>  hw/nubus/nubus-bridge.c  | 2 ++
>  hw/nubus/nubus-device.c  | 8 
>  include/hw/nubus/nubus.h | 6 ++
>  3 files changed, 16 insertions(+)
> 
> diff --git a/hw/nubus/nubus-bridge.c b/hw/nubus/nubus-bridge.c
> index 2c7c4ee121..0366d925a9 100644
> --- a/hw/nubus/nubus-bridge.c
> +++ b/hw/nubus/nubus-bridge.c
> @@ -19,6 +19,8 @@ static void nubus_bridge_init(Object *obj)
>  NubusBus *bus = >bus;
>  
>  qbus_create_inplace(bus, sizeof(s->bus), TYPE_NUBUS_BUS, DEVICE(s), 
> NULL);
> +
> +qdev_init_gpio_out(DEVICE(s), bus->irqs, NUBUS_IRQS);
>  }
>  
>  static Property nubus_bridge_properties[] = {
> diff --git a/hw/nubus/nubus-device.c b/hw/nubus/nubus-device.c
> index 9cecb487a1..4856e81991 100644
> --- a/hw/nubus/nubus-device.c
> +++ b/hw/nubus/nubus-device.c
> @@ -10,12 +10,20 @@
>  
>  #include "qemu/osdep.h"
>  #include "qemu/datadir.h"
> +#include "hw/irq.h"
>  #include "hw/loader.h"
>  #include "hw/nubus/nubus.h"
>  #include "qapi/error.h"
>  #include "qemu/error-report.h"
>  
>  
> +void nubus_set_irq(NubusDevice *nd, int level)
> +{
> +NubusBus *nubus = NUBUS_BUS(qdev_get_parent_bus(DEVICE(nd)));
> +
> +qemu_set_irq(nubus->irqs[nd->slot], level);
> +}
> +
>  static void nubus_device_realize(DeviceState *dev, Error **errp)
>  {
>  NubusBus *nubus = NUBUS_BUS(qdev_get_parent_bus(dev));
> diff --git a/include/hw/nubus/nubus.h b/include/hw/nubus/nubus.h
> index cf9a585a91..1c487f74ac 100644
> --- a/include/hw/nubus/nubus.h
> +++ b/include/hw/nubus/nubus.h
> @@ -25,6 +25,8 @@
>  #define NUBUS_FIRST_SLOT  0x0
>  #define NUBUS_LAST_SLOT   0xf
>  
> +#define NUBUS_IRQS16
> +
>  #define TYPE_NUBUS_DEVICE "nubus-device"
>  OBJECT_DECLARE_SIMPLE_TYPE(NubusDevice, NUBUS_DEVICE)
>  
> @@ -44,6 +46,8 @@ struct NubusBus {
>  MemoryRegion slot_io;
>  
>  uint32_t slot_available_mask;
> +
> +qemu_irq irqs[NUBUS_IRQS];
>  };
>  
>  #define NUBUS_DECL_ROM_MAX_SIZE(128 * KiB)
> @@ -59,6 +63,8 @@ struct NubusDevice {
>  MemoryRegion decl_rom;
>  };
>  
> +void nubus_set_irq(NubusDevice *nd, int level);
> +
>  struct NubusBridge {
>  SysBusDevice parent_obj;
>  
> 

Reviewed-by: Laurent Vivier 



Re: [PATCH v4 19/20] q800: wire up nubus IRQs

2021-09-20 Thread Laurent Vivier
Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
> Nubus IRQs are routed to the CPU through the VIA2 device so wire up the IRQs
> using gpios accordingly.
> 
> Signed-off-by: Mark Cave-Ayland 
> ---
>  hw/m68k/q800.c | 5 +
>  1 file changed, 5 insertions(+)
> 
> diff --git a/hw/m68k/q800.c b/hw/m68k/q800.c
> index e34df1a829..fbc45a301f 100644
> --- a/hw/m68k/q800.c
> +++ b/hw/m68k/q800.c
> @@ -396,6 +396,11 @@ static void q800_init(MachineState *machine)
>  sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, 9 * NUBUS_SUPER_SLOT_SIZE);
>  sysbus_mmio_map(SYS_BUS_DEVICE(dev), 1, NUBUS_SLOT_BASE +
>  9 * NUBUS_SLOT_SIZE);
> +for (i = 0; i < VIA2_NUBUS_IRQ_NB; i++) {
> +qdev_connect_gpio_out(dev, 9 + i,
> +  qdev_get_gpio_in_named(via2_dev, "nubus-irq",
> + VIA2_NUBUS_IRQ_9 + i));
> +}
>  
>  nubus = _BRIDGE(dev)->bus;
>  
> 

Reviewed-by: Laurent Vivier 



[PATCH v5 13/31] target/hexagon: Remove unused has_work() handler

2021-09-20 Thread Philippe Mathieu-Daudé
has_work() is sysemu specific, and Hexagon target only provides
a linux-user implementation. Remove the unused hexagon_cpu_has_work().

Reviewed-by: Richard Henderson 
Signed-off-by: Philippe Mathieu-Daudé 
---
 target/hexagon/cpu.c | 6 --
 1 file changed, 6 deletions(-)

diff --git a/target/hexagon/cpu.c b/target/hexagon/cpu.c
index 3338365c16e..aa01974807c 100644
--- a/target/hexagon/cpu.c
+++ b/target/hexagon/cpu.c
@@ -189,11 +189,6 @@ static void hexagon_cpu_synchronize_from_tb(CPUState *cs,
 env->gpr[HEX_REG_PC] = tb->pc;
 }
 
-static bool hexagon_cpu_has_work(CPUState *cs)
-{
-return true;
-}
-
 void restore_state_to_opc(CPUHexagonState *env, TranslationBlock *tb,
   target_ulong *data)
 {
@@ -287,7 +282,6 @@ static void hexagon_cpu_class_init(ObjectClass *c, void 
*data)
 device_class_set_parent_reset(dc, hexagon_cpu_reset, >parent_reset);
 
 cc->class_by_name = hexagon_cpu_class_by_name;
-cc->has_work = hexagon_cpu_has_work;
 cc->dump_state = hexagon_dump_state;
 cc->set_pc = hexagon_cpu_set_pc;
 cc->gdb_read_register = hexagon_gdb_read_register;
-- 
2.31.1




[PATCH v3 19/30] Hexagon HVX (target/hexagon) helper overrides - vector logical ops

2021-09-20 Thread Taylor Simpson
Signed-off-by: Taylor Simpson 
---
 target/hexagon/gen_tcg_hvx.h | 52 
 1 file changed, 52 insertions(+)

diff --git a/target/hexagon/gen_tcg_hvx.h b/target/hexagon/gen_tcg_hvx.h
index 006ba74..bd0abc6 100644
--- a/target/hexagon/gen_tcg_hvx.h
+++ b/target/hexagon/gen_tcg_hvx.h
@@ -363,4 +363,56 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 tcg_gen_gvec_umin(MO_8, VdV_off, VuV_off, VvV_off, \
   sizeof(MMVector), sizeof(MMVector))
 
+/* Vector logical ops */
+#define fGEN_TCG_V6_vxor(SHORTCODE) \
+tcg_gen_gvec_xor(MO_64, VdV_off, VuV_off, VvV_off, \
+ sizeof(MMVector), sizeof(MMVector))
+
+#define fGEN_TCG_V6_vand(SHORTCODE) \
+tcg_gen_gvec_and(MO_64, VdV_off, VuV_off, VvV_off, \
+ sizeof(MMVector), sizeof(MMVector))
+
+#define fGEN_TCG_V6_vor(SHORTCODE) \
+tcg_gen_gvec_or(MO_64, VdV_off, VuV_off, VvV_off, \
+sizeof(MMVector), sizeof(MMVector))
+
+#define fGEN_TCG_V6_vnot(SHORTCODE) \
+tcg_gen_gvec_not(MO_64, VdV_off, VuV_off, \
+ sizeof(MMVector), sizeof(MMVector))
+
+/* Q register logical ops */
+#define fGEN_TCG_V6_pred_or(SHORTCODE) \
+tcg_gen_gvec_or(MO_64, QdV_off, QsV_off, QtV_off, \
+sizeof(MMQReg), sizeof(MMQReg))
+
+#define fGEN_TCG_V6_pred_and(SHORTCODE) \
+tcg_gen_gvec_and(MO_64, QdV_off, QsV_off, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg))
+
+#define fGEN_TCG_V6_pred_xor(SHORTCODE) \
+tcg_gen_gvec_xor(MO_64, QdV_off, QsV_off, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg))
+
+#define fGEN_TCG_V6_pred_or_n(SHORTCODE) \
+do { \
+intptr_t tmpoff = offsetof(CPUHexagonState, qtmp); \
+tcg_gen_gvec_not(MO_64, tmpoff, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+tcg_gen_gvec_or(MO_64, QdV_off, QsV_off, tmpoff, \
+sizeof(MMQReg), sizeof(MMQReg)); \
+} while (0)
+
+#define fGEN_TCG_V6_pred_and_n(SHORTCODE) \
+do { \
+intptr_t tmpoff = offsetof(CPUHexagonState, qtmp); \
+tcg_gen_gvec_not(MO_64, tmpoff, QtV_off, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+tcg_gen_gvec_and(MO_64, QdV_off, QsV_off, tmpoff, \
+ sizeof(MMQReg), sizeof(MMQReg)); \
+} while (0)
+
+#define fGEN_TCG_V6_pred_not(SHORTCODE) \
+tcg_gen_gvec_not(MO_64, QdV_off, QsV_off, \
+ sizeof(MMQReg), sizeof(MMQReg))
+
 #endif
-- 
2.7.4



Re: [PATCH v3 3/3] monitor: refactor set/expire_password and allow VNC display id

2021-09-20 Thread Eric Blake
On Mon, Sep 20, 2021 at 12:56:41PM +0200, Stefan Reiter wrote:
> It is possible to specify more than one VNC server on the command line,
> either with an explicit ID or the auto-generated ones à la "default",
> "vnc2", "vnc3", ...
> 
> It is not possible to change the password on one of these extra VNC
> displays though. Fix this by adding a "display" parameter to the
> "set_password" and "expire_password" QMP and HMP commands.
> 
> For HMP, the display is specified using the "-d" value flag.
> 
> For QMP, the schema is updated to explicitly express the supported
> variants of the commands with protocol-discriminated unions.
> 
> Suggested-by: Eric Blake 
> Suggested-by: Markus Armbruster 
> Signed-off-by: Stefan Reiter 
> ---
> 
> The union schema simplifies the QMP code, but makes the HMP part a bit more
> involved. Since the parameters are practically the same, is there a way to 
> just
> pass the HMP generated qdict off to the qapi parser to get the correct struct
> for calling the qmp_ methods?

Possibly, but I don't know it off-hand.

> 
>  hmp-commands.hx|  29 
>  monitor/hmp-cmds.c |  60 +++-
>  monitor/qmp-cmds.c |  62 ++---
>  qapi/ui.json   | 168 +
>  4 files changed, 235 insertions(+), 84 deletions(-)
> 
> diff --git a/hmp-commands.hx b/hmp-commands.hx
> index 8e45bce2cd..d78e4cfc47 100644
> --- a/hmp-commands.hx
> +++ b/hmp-commands.hx
> @@ -1514,34 +1514,35 @@ ERST
>  
>  {
>  .name   = "set_password",
> -.args_type  = "protocol:s,password:s,connected:s?",
> -.params = "protocol password action-if-connected",
> +.args_type  = "protocol:s,password:s,display:-dS,connected:s?",
> +.params = "protocol password [-d display] [action-if-connected]",

Puts your new -xS of patch 2/3 to use.

> +++ b/monitor/hmp-cmds.c
> @@ -1451,10 +1451,43 @@ void hmp_set_password(Monitor *mon, const QDict 
> *qdict)
>  {
>  const char *protocol  = qdict_get_str(qdict, "protocol");
>  const char *password  = qdict_get_str(qdict, "password");
> +const char *display = qdict_get_try_str(qdict, "display");
>  const char *connected = qdict_get_try_str(qdict, "connected");
>  Error *err = NULL;
> +DisplayProtocol proto;
>  
> -qmp_set_password(protocol, password, !!connected, connected, );
> +SetPasswordOptions opts = {
> +.password = g_strdup(password),
> +.u.vnc.display = NULL,
> +};
> +
> +proto = qapi_enum_parse(_lookup, protocol,
> +DISPLAY_PROTOCOL_VNC, );
> +if (err) {
> +hmp_handle_error(mon, err);
> +return;
> +}
> +opts.protocol = proto;
> +
> +if (proto == DISPLAY_PROTOCOL_VNC) {
> +if ((opts.u.vnc.has_display = !!display)) {

Assignment as a side-effect of the 'if' is a bit unusual in qemu
style.

> +opts.u.vnc.display = g_strdup(display);
> +}

In fact, g_strdup(NULL) does what you want; you can just write:

opts.u.vnc.has_display = !!display;
opts.u.vnc.display = g_strdup(display);

without an 'if'.

> +} else if (proto == DISPLAY_PROTOCOL_SPICE) {
> +if ((opts.u.spice.has_connected = !!connected)) {

And again.

> +opts.u.spice.connected =
> +qapi_enum_parse(_lookup, connected,
> +SET_PASSWORD_ACTION_KEEP, );
> +if (err) {
> +hmp_handle_error(mon, err);
> +return;
> +}
> +}
> +}
> +
> +qmp_set_password(, );
> +g_free(opts.password);
> +g_free(opts.u.vnc.display);
>  hmp_handle_error(mon, err);
>  }
>  
> @@ -1462,9 +1495,32 @@ void hmp_expire_password(Monitor *mon, const QDict 
> *qdict)
>  {
>  const char *protocol  = qdict_get_str(qdict, "protocol");
>  const char *whenstr = qdict_get_str(qdict, "time");
> +const char *display = qdict_get_try_str(qdict, "display");
>  Error *err = NULL;
> +DisplayProtocol proto;
>  
> -qmp_expire_password(protocol, whenstr, );
> +ExpirePasswordOptions opts = {
> +.time = g_strdup(whenstr),
> +.u.vnc.display = NULL,
> +};
> +
> +proto = qapi_enum_parse(_lookup, protocol,
> +DISPLAY_PROTOCOL_VNC, );
> +if (err) {
> +hmp_handle_error(mon, err);
> +return;
> +}
> +opts.protocol = proto;
> +
> +if (proto == DISPLAY_PROTOCOL_VNC) {
> +if ((opts.u.vnc.has_display = !!display)) {
> +opts.u.vnc.display = g_strdup(display);

and again

> +}
> +}
> +
> +qmp_expire_password(, );
> +g_free(opts.time);
> +g_free(opts.u.vnc.display);
>  hmp_handle_error(mon, err);
>  }
>  
> diff --git a/monitor/qmp-cmds.c b/monitor/qmp-cmds.c
> index 5c0d5e116b..cb229c01f8 100644
> --- a/monitor/qmp-cmds.c
> +++ b/monitor/qmp-cmds.c
...
> diff --git a/qapi/ui.json b/qapi/ui.json
> index b2cf7a6759..494c92a65e 

Re: [PATCH v4 20/20] q800: configure nubus available slots for Quadra 800

2021-09-20 Thread Laurent Vivier
Le 17/09/2021 à 09:50, Mark Cave-Ayland a écrit :
> Slot 0x9 is reserved for use by the in-built framebuffer whilst only slots
> 0xc, 0xd and 0xe physically exist on the Quadra 800.
> 
> Signed-off-by: Mark Cave-Ayland 
> ---
>  hw/m68k/q800.c | 9 +
>  1 file changed, 9 insertions(+)
> 
> diff --git a/hw/m68k/q800.c b/hw/m68k/q800.c
> index fbc45a301f..63f42764eb 100644
> --- a/hw/m68k/q800.c
> +++ b/hw/m68k/q800.c
> @@ -78,6 +78,13 @@
>  
>  #define MAC_CLOCK  3686418
>  
> +/*
> + * Slot 0x9 is reserved for use by the in-built framebuffer whilst only
> + * slots 0xc, 0xd and 0xe physically exist on the Quadra 800
> + */
> +#define Q800_NUBUS_SLOTS_AVAILABLE(BIT(0x9) | BIT(0xc) | BIT(0xd) | \
> +   BIT(0xe))
> +
>  /*
>   * The GLUE (General Logic Unit) is an Apple custom integrated circuit chip
>   * that performs a variety of functions (RAM management, clock generation, 
> ...).
> @@ -392,6 +399,8 @@ static void q800_init(MachineState *machine)
>  /* NuBus */
>  
>  dev = qdev_new(TYPE_MAC_NUBUS_BRIDGE);
> +qdev_prop_set_uint32(dev, "slot-available-mask",
> + Q800_NUBUS_SLOTS_AVAILABLE);
>  sysbus_realize_and_unref(SYS_BUS_DEVICE(dev), _fatal);
>  sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, 9 * NUBUS_SUPER_SLOT_SIZE);
>  sysbus_mmio_map(SYS_BUS_DEVICE(dev), 1, NUBUS_SLOT_BASE +
> 

Reviewed-by: Laurent Vivier 



[PATCH v5 12/31] target/cris: Restrict has_work() handler to sysemu

2021-09-20 Thread Philippe Mathieu-Daudé
Restrict has_work() to sysemu.

Signed-off-by: Philippe Mathieu-Daudé 
---
 target/cris/cpu.c | 5 -
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/target/cris/cpu.c b/target/cris/cpu.c
index c2e7483f5bd..b2761f8b110 100644
--- a/target/cris/cpu.c
+++ b/target/cris/cpu.c
@@ -35,10 +35,12 @@ static void cris_cpu_set_pc(CPUState *cs, vaddr value)
 cpu->env.pc = value;
 }
 
+#if !defined(CONFIG_USER_ONLY)
 static bool cris_cpu_has_work(CPUState *cs)
 {
 return cs->interrupt_request & (CPU_INTERRUPT_HARD | CPU_INTERRUPT_NMI);
 }
+#endif /* !CONFIG_USER_ONLY */
 
 static void cris_cpu_reset(DeviceState *dev)
 {
@@ -208,6 +210,7 @@ static const struct TCGCPUOps crisv10_tcg_ops = {
 .tlb_fill = cris_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = cris_cpu_has_work,
 .cpu_exec_interrupt = cris_cpu_exec_interrupt,
 .do_interrupt = crisv10_cpu_do_interrupt,
 #endif /* !CONFIG_USER_ONLY */
@@ -218,6 +221,7 @@ static const struct TCGCPUOps crisv32_tcg_ops = {
 .tlb_fill = cris_cpu_tlb_fill,
 
 #ifndef CONFIG_USER_ONLY
+.has_work = cris_cpu_has_work,
 .cpu_exec_interrupt = cris_cpu_exec_interrupt,
 .do_interrupt = cris_cpu_do_interrupt,
 #endif /* !CONFIG_USER_ONLY */
@@ -294,7 +298,6 @@ static void cris_cpu_class_init(ObjectClass *oc, void *data)
 device_class_set_parent_reset(dc, cris_cpu_reset, >parent_reset);
 
 cc->class_by_name = cris_cpu_class_by_name;
-cc->has_work = cris_cpu_has_work;
 cc->dump_state = cris_cpu_dump_state;
 cc->set_pc = cris_cpu_set_pc;
 cc->gdb_read_register = cris_cpu_gdb_read_register;
-- 
2.31.1




[PATCH v3 15/30] Hexagon HVX (target/hexagon) helper overrides - vector assign & cmov

2021-09-20 Thread Taylor Simpson
Signed-off-by: Taylor Simpson 
---
 target/hexagon/gen_tcg_hvx.h | 31 +++
 1 file changed, 31 insertions(+)

diff --git a/target/hexagon/gen_tcg_hvx.h b/target/hexagon/gen_tcg_hvx.h
index eb29566..bcd53d4 100644
--- a/target/hexagon/gen_tcg_hvx.h
+++ b/target/hexagon/gen_tcg_hvx.h
@@ -126,4 +126,35 @@ static inline void assert_vhist_tmp(DisasContext *ctx)
 } while (0)
 
 
+#define fGEN_TCG_V6_vassign(SHORTCODE) \
+tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
+ sizeof(MMVector), sizeof(MMVector))
+
+/* Vector conditional move */
+#define fGEN_TCG_VEC_CMOV(PRED) \
+do { \
+TCGv lsb = tcg_temp_new(); \
+TCGLabel *false_label = gen_new_label(); \
+TCGLabel *end_label = gen_new_label(); \
+tcg_gen_andi_tl(lsb, PsV, 1); \
+tcg_gen_brcondi_tl(TCG_COND_NE, lsb, PRED, false_label); \
+tcg_temp_free(lsb); \
+tcg_gen_gvec_mov(MO_64, VdV_off, VuV_off, \
+ sizeof(MMVector), sizeof(MMVector)); \
+tcg_gen_br(end_label); \
+gen_set_label(false_label); \
+tcg_gen_ori_tl(hex_slot_cancelled, hex_slot_cancelled, \
+   1 << insn->slot); \
+gen_set_label(end_label); \
+} while (0)
+
+
+/* Vector conditional move (true) */
+#define fGEN_TCG_V6_vcmov(SHORTCODE) \
+fGEN_TCG_VEC_CMOV(1)
+
+/* Vector conditional move (false) */
+#define fGEN_TCG_V6_vncmov(SHORTCODE) \
+fGEN_TCG_VEC_CMOV(0)
+
 #endif
-- 
2.7.4



[PATCH v3 30/30] Hexagon HVX (tests/tcg/hexagon) histogram test

2021-09-20 Thread Taylor Simpson
Signed-off-by: Taylor Simpson 
---
 tests/tcg/hexagon/hvx_histogram_input.h | 717 
 tests/tcg/hexagon/hvx_histogram_row.h   |  24 ++
 tests/tcg/hexagon/hvx_histogram.c   |  88 
 tests/tcg/hexagon/Makefile.target   |   5 +
 tests/tcg/hexagon/hvx_histogram_row.S   | 294 +
 5 files changed, 1128 insertions(+)
 create mode 100644 tests/tcg/hexagon/hvx_histogram_input.h
 create mode 100644 tests/tcg/hexagon/hvx_histogram_row.h
 create mode 100644 tests/tcg/hexagon/hvx_histogram.c
 create mode 100644 tests/tcg/hexagon/hvx_histogram_row.S

diff --git a/tests/tcg/hexagon/hvx_histogram_input.h 
b/tests/tcg/hexagon/hvx_histogram_input.h
new file mode 100644
index 000..2f91092
--- /dev/null
+++ b/tests/tcg/hexagon/hvx_histogram_input.h
@@ -0,0 +1,717 @@
+/*
+ *  Copyright(c) 2021 Qualcomm Innovation Center, Inc. All Rights Reserved.
+ *
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License as published by
+ *  the Free Software Foundation; either version 2 of the License, or
+ *  (at your option) any later version.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, see .
+ */
+
+{ 0x26, 0x32, 0x2e, 0x2e, 0x2d, 0x2c, 0x2d, 0x2d,
+  0x2c, 0x2e, 0x31, 0x33, 0x36, 0x39, 0x3b, 0x3f,
+  0x42, 0x46, 0x4a, 0x4c, 0x51, 0x53, 0x53, 0x54,
+  0x56, 0x57, 0x58, 0x57, 0x56, 0x52, 0x51, 0x4f,
+  0x4c, 0x49, 0x47, 0x42, 0x3e, 0x3b, 0x38, 0x35,
+  0x33, 0x30, 0x2e, 0x2c, 0x2b, 0x2a, 0x2a, 0x28,
+  0x28, 0x27, 0x27, 0x28, 0x29, 0x2a, 0x2c, 0x2e,
+  0x2f, 0x33, 0x36, 0x38, 0x3c, 0x3d, 0x40, 0x42,
+  0x43, 0x42, 0x43, 0x44, 0x43, 0x41, 0x40, 0x3b,
+  0x3b, 0x3a, 0x38, 0x35, 0x32, 0x2f, 0x2c, 0x29,
+  0x27, 0x26, 0x23, 0x21, 0x1e, 0x1c, 0x1a, 0x19,
+  0x17, 0x15, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10,
+  0x0f, 0x0e, 0x0f, 0x0f, 0x0e, 0x0d, 0x0d, 0x0d,
+  0x0c, 0x0d, 0x0e, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c,
+  0x0c, 0x0c, 0x0d, 0x0c, 0x0f, 0x0e, 0x0f, 0x0f,
+  0x0f, 0x10, 0x11, 0x12, 0x14, 0x16, 0x17, 0x19,
+  0x1c, 0x1d, 0x21, 0x25, 0x27, 0x29, 0x2b, 0x2f,
+  0x31, 0x33, 0x36, 0x38, 0x39, 0x3a, 0x3b, 0x3c,
+  0x3c, 0x3d, 0x3e, 0x3e, 0x3c, 0x3b, 0x3a, 0x39,
+  0x39, 0x3a, 0x3a, 0x3a, 0x3a, 0x3c, 0x3e, 0x43,
+  0x47, 0x4a, 0x4d, 0x51, 0x51, 0x54, 0x56, 0x56,
+  0x57, 0x56, 0x53, 0x4f, 0x4b, 0x47, 0x43, 0x41,
+  0x3e, 0x3c, 0x3a, 0x37, 0x36, 0x33, 0x32, 0x34,
+  0x34, 0x34, 0x34, 0x35, 0x36, 0x39, 0x3d, 0x3d,
+  0x3f, 0x40, 0x40, 0x40, 0x40, 0x3e, 0x40, 0x40,
+  0x42, 0x44, 0x47, 0x48, 0x4b, 0x4e, 0x56, 0x5c,
+  0x62, 0x68, 0x6f, 0x73, 0x76, 0x79, 0x7a, 0x7c,
+  0x7e, 0x7c, 0x78, 0x72, 0x6e, 0x69, 0x65, 0x60,
+  0x5b, 0x56, 0x52, 0x4d, 0x4a, 0x48, 0x47, 0x46,
+  0x44, 0x43, 0x42, 0x41, 0x41, 0x41, 0x40, 0x40,
+  0x3f, 0x3e, 0x3d, 0x3c, 0x3b, 0x3b, 0x38, 0x37,
+  0x36, 0x35, 0x36, 0x35, 0x36, 0x37, 0x38, 0x3c,
+  0x3d, 0x3f, 0x42, 0x44, 0x46, 0x48, 0x4b, 0x4c,
+  0x4e, 0x4e, 0x4d, 0x4c, 0x4a, 0x48, 0x49, 0x49,
+  0x4b, 0x4d, 0x4e, },
+{ 0x23, 0x2d, 0x29, 0x29, 0x28, 0x28, 0x29, 0x29,
+  0x28, 0x2b, 0x2d, 0x2f, 0x32, 0x34, 0x36, 0x3a,
+  0x3d, 0x41, 0x44, 0x47, 0x4a, 0x4c, 0x4e, 0x4e,
+  0x50, 0x51, 0x51, 0x51, 0x4f, 0x4c, 0x4b, 0x48,
+  0x46, 0x44, 0x40, 0x3d, 0x39, 0x36, 0x34, 0x30,
+  0x2f, 0x2d, 0x2a, 0x29, 0x28, 0x27, 0x26, 0x25,
+  0x25, 0x24, 0x24, 0x24, 0x26, 0x28, 0x28, 0x2a,
+  0x2b, 0x2e, 0x32, 0x34, 0x37, 0x39, 0x3b, 0x3c,
+  0x3d, 0x3d, 0x3e, 0x3e, 0x3e, 0x3c, 0x3b, 0x38,
+  0x37, 0x35, 0x33, 0x30, 0x2e, 0x2b, 0x27, 0x25,
+  0x24, 0x21, 0x20, 0x1d, 0x1b, 0x1a, 0x18, 0x16,
+  0x15, 0x14, 0x13, 0x12, 0x10, 0x11, 0x10, 0x0e,
+  0x0e, 0x0d, 0x0d, 0x0d, 0x0d, 0x0c, 0x0c, 0x0b,
+  0x0b, 0x0b, 0x0c, 0x0b, 0x0b, 0x09, 0x0a, 0x0b,
+  0x0b, 0x0a, 0x0a, 0x0c, 0x0c, 0x0c, 0x0d, 0x0e,
+  0x0e, 0x0f, 0x0f, 0x11, 0x12, 0x15, 0x15, 0x17,
+  0x1a, 0x1c, 0x1f, 0x22, 0x25, 0x26, 0x29, 0x2a,
+  0x2d, 0x30, 0x33, 0x34, 0x35, 0x35, 0x37, 0x37,
+  0x39, 0x3a, 0x39, 0x38, 0x37, 0x36, 0x36, 0x37,
+  0x35, 0x36, 0x35, 0x35, 0x36, 0x37, 0x3a, 0x3e,
+  0x40, 0x43, 0x48, 0x49, 0x4b, 0x4c, 0x4d, 0x4e,
+  0x4f, 0x4f, 0x4c, 0x48, 0x45, 0x41, 0x3e, 0x3b,
+  0x3a, 0x37, 0x36, 0x33, 0x32, 0x31, 0x30, 0x31,
+  0x32, 0x31, 0x31, 0x31, 0x31, 0x34, 0x37, 0x38,
+  0x3a, 0x3b, 0x3b, 0x3b, 0x3c, 0x3b, 0x3d, 0x3e,
+  0x3f, 0x40, 0x43, 0x44, 0x47, 0x4b, 0x4f, 0x56,
+  0x5a, 0x60, 0x66, 0x69, 0x6a, 0x6e, 0x71, 0x72,
+  0x73, 0x72, 0x6d, 0x69, 0x66, 0x60, 

  1   2   3   4   5   >