All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ashok Kumar <ashoks@broadcom.com>
To: Pavel Fedin <p.fedin@samsung.com>
Cc: Peter Maydell <peter.maydell@linaro.org>,
	Eric Auger <eric.auger@linaro.org>,
	Shlomo Pongratz <shlomo.pongratz@huawei.com>,
	Shlomo Pongratz <shlomopongratz@gmail.com>,
	qemu-devel@nongnu.org,
	Christoffer Dall <christoffer.dall@linaro.org>
Subject: Re: [Qemu-devel] [PATCH v11 5/5] hw/arm/virt: Add gic-version option to virt machine
Date: Tue, 25 Aug 2015 06:40:53 -0700	[thread overview]
Message-ID: <20150825134053.GB27329@ashoks@broadcom.com> (raw)
In-Reply-To: <0f869a8319f484f55b4845d1e8bc4764a8b767d9.1439968813.git.p.fedin@samsung.com>

On Wed, Aug 19, 2015 at 10:23:26AM +0300, Pavel Fedin wrote:
> Add gic_version to VirtMachineState, set it to value of the option
> and pass it around where necessary. Instantiate devices and fdt
> nodes according to the choice.
> 
> max_cpus for virt machine increased to 126 (calculated from redistributor
> space available in the memory map). GICv2 compatibility check happens
> inside arm_gic_common_realize().
> 
> ITS regions are added to the memory map too, however currently they
> are not used, just reserved.
> 
> Signed-off-by: Pavel Fedin <p.fedin@samsung.com>
> ---
>  hw/arm/virt.c         | 111 +++++++++++++++++++++++++++++++++++++++++---------
>  include/hw/arm/fdt.h  |   2 +-
>  include/hw/arm/virt.h |   5 ++-
>  3 files changed, 96 insertions(+), 22 deletions(-)
> 
> diff --git a/hw/arm/virt.c b/hw/arm/virt.c
> index d5a8417..e090640 100644
> --- a/hw/arm/virt.c
> +++ b/hw/arm/virt.c
> @@ -50,6 +50,7 @@
>  #include "hw/arm/fdt.h"
>  #include "hw/intc/arm_gic_common.h"
>  #include "kvm_arm.h"
> +#include "qapi/visitor.h"
>  
>  /* Number of external interrupt lines to configure the GIC with */
>  #define NUM_IRQS 256
> @@ -79,6 +80,7 @@ typedef struct {
>  typedef struct {
>      MachineState parent;
>      bool secure;
> +    int32_t gic_version;
>  } VirtMachineState;
>  
>  #define TYPE_VIRT_MACHINE   "virt"
> @@ -109,6 +111,9 @@ static const MemMapEntry a15memmap[] = {
>      [VIRT_GIC_DIST] =           { 0x08000000, 0x00010000 },
>      [VIRT_GIC_CPU] =            { 0x08010000, 0x00010000 },
>      [VIRT_GIC_V2M] =            { 0x08020000, 0x00001000 },
> +    [VIRT_ITS_CONTROL] =        { 0x08020000, 0x00010000 },
> +    [VIRT_ITS_TRANSLATION] =    { 0x08030000, 0x00010000 },
> +    [VIRT_GIC_REDIST] =         { 0x08040000, 0x00FC0000 },
>      [VIRT_UART] =               { 0x09000000, 0x00001000 },
>      [VIRT_RTC] =                { 0x09010000, 0x00001000 },
>      [VIRT_FW_CFG] =             { 0x09020000, 0x0000000a },
> @@ -258,10 +263,13 @@ static void fdt_add_timer_nodes(const VirtBoardInfo *vbi)
>       * they are edge-triggered.
>       */
>      ARMCPU *armcpu;
> +    uint32_t max;
>      uint32_t irqflags = GIC_FDT_IRQ_FLAGS_EDGE_LO_HI;
>  
> +    /* Argument is 32 bit but 8 bits are reserved for flags */
> +    max = (vbi->smp_cpus >= 24) ? 24 : vbi->smp_cpus;
>      irqflags = deposit32(irqflags, GIC_FDT_IRQ_PPI_CPU_START,
> -                         GIC_FDT_IRQ_PPI_CPU_WIDTH, (1 << vbi->smp_cpus) - 1);
> +                         GIC_FDT_IRQ_PPI_CPU_WIDTH, (1 << max) - 1);
>  
>      qemu_fdt_add_subnode(vbi->fdt, "/timer");
>  
> @@ -285,6 +293,18 @@ static void fdt_add_cpu_nodes(const VirtBoardInfo *vbi)
>  {
>      int cpu;
>  
> +    /*
> +     * From Documentation/devicetree/bindings/arm/cpus.txt
> +     *  On ARM v8 64-bit systems value should be set to 2,
> +     *  that corresponds to the MPIDR_EL1 register size.
> +     *  If MPIDR_EL1[63:32] value is equal to 0 on all CPUs
> +     *  in the system, #address-cells can be set to 1, since
> +     *  MPIDR_EL1[63:32] bits are not used for CPUs
> +     *  identification.
> +     *
> +     *  Now GIC500 doesn't support affinities 2 & 3 so currently
> +     *  #address-cells can stay 1 until future GIC
> +     */
>      qemu_fdt_add_subnode(vbi->fdt, "/cpus");
>      qemu_fdt_setprop_cell(vbi->fdt, "/cpus", "#address-cells", 0x1);
>      qemu_fdt_setprop_cell(vbi->fdt, "/cpus", "#size-cells", 0x0);
> @@ -321,25 +341,36 @@ static void fdt_add_v2m_gic_node(VirtBoardInfo *vbi)
>      qemu_fdt_setprop_cell(vbi->fdt, "/intc/v2m", "phandle", vbi->v2m_phandle);
>  }
>  
> -static void fdt_add_gic_node(VirtBoardInfo *vbi)
> +static void fdt_add_gic_node(VirtBoardInfo *vbi, int type)
>  {
>      vbi->gic_phandle = qemu_fdt_alloc_phandle(vbi->fdt);
>      qemu_fdt_setprop_cell(vbi->fdt, "/", "interrupt-parent", vbi->gic_phandle);
>  
>      qemu_fdt_add_subnode(vbi->fdt, "/intc");
> -    /* 'cortex-a15-gic' means 'GIC v2' */
> -    qemu_fdt_setprop_string(vbi->fdt, "/intc", "compatible",
> -                            "arm,cortex-a15-gic");
>      qemu_fdt_setprop_cell(vbi->fdt, "/intc", "#interrupt-cells", 3);
>      qemu_fdt_setprop(vbi->fdt, "/intc", "interrupt-controller", NULL, 0);
> -    qemu_fdt_setprop_sized_cells(vbi->fdt, "/intc", "reg",
> -                                     2, vbi->memmap[VIRT_GIC_DIST].base,
> -                                     2, vbi->memmap[VIRT_GIC_DIST].size,
> -                                     2, vbi->memmap[VIRT_GIC_CPU].base,
> -                                     2, vbi->memmap[VIRT_GIC_CPU].size);
>      qemu_fdt_setprop_cell(vbi->fdt, "/intc", "#address-cells", 0x2);
>      qemu_fdt_setprop_cell(vbi->fdt, "/intc", "#size-cells", 0x2);
>      qemu_fdt_setprop(vbi->fdt, "/intc", "ranges", NULL, 0);
> +    if (type == 3) {
> +        qemu_fdt_setprop_string(vbi->fdt, "/intc", "compatible",
> +                                "arm,gic-v3");
> +        qemu_fdt_setprop_sized_cells(vbi->fdt, "/intc", "reg",
> +                                     2, vbi->memmap[VIRT_GIC_DIST].base,
> +                                     2, vbi->memmap[VIRT_GIC_DIST].size,
> +                                     2, vbi->memmap[VIRT_GIC_REDIST].base,
> +                                     2, vbi->memmap[VIRT_GIC_REDIST].size);
> +    } else {
> +        /* 'cortex-a15-gic' means 'GIC v2' */
> +        qemu_fdt_setprop_string(vbi->fdt, "/intc", "compatible",
> +                                "arm,cortex-a15-gic");
> +        qemu_fdt_setprop_sized_cells(vbi->fdt, "/intc", "reg",
> +                                      2, vbi->memmap[VIRT_GIC_DIST].base,
> +                                      2, vbi->memmap[VIRT_GIC_DIST].size,
> +                                      2, vbi->memmap[VIRT_GIC_CPU].base,
> +                                      2, vbi->memmap[VIRT_GIC_CPU].size);
> +    }
> +
>      qemu_fdt_setprop_cell(vbi->fdt, "/intc", "phandle", vbi->gic_phandle);
>  }
>  
> @@ -362,18 +393,18 @@ static void create_v2m(VirtBoardInfo *vbi, qemu_irq *pic)
>      fdt_add_v2m_gic_node(vbi);
>  }
>  
> -static void create_gic(VirtBoardInfo *vbi, qemu_irq *pic)
> +static void create_gic(VirtBoardInfo *vbi, qemu_irq *pic, int type)
>  {
> -    /* We create a standalone GIC v2 */
> +    /* We create a standalone GIC */
>      DeviceState *gicdev;
>      SysBusDevice *gicbusdev;
>      const char *gictype;
>      int i;
>  
> -    gictype = gic_class_name();
> +    gictype = (type == 3) ? gicv3_class_name() : gic_class_name();
>  
>      gicdev = qdev_create(NULL, gictype);
> -    qdev_prop_set_uint32(gicdev, "revision", 2);
> +    qdev_prop_set_uint32(gicdev, "revision", type);
>      qdev_prop_set_uint32(gicdev, "num-cpu", smp_cpus);
>      /* Note that the num-irq property counts both internal and external
>       * interrupts; there are always 32 of the former (mandated by GIC spec).
> @@ -382,7 +413,11 @@ static void create_gic(VirtBoardInfo *vbi, qemu_irq *pic)
>      qdev_init_nofail(gicdev);
>      gicbusdev = SYS_BUS_DEVICE(gicdev);
>      sysbus_mmio_map(gicbusdev, 0, vbi->memmap[VIRT_GIC_DIST].base);
> -    sysbus_mmio_map(gicbusdev, 1, vbi->memmap[VIRT_GIC_CPU].base);
> +    if (type == 3) {
> +        sysbus_mmio_map(gicbusdev, 1, vbi->memmap[VIRT_GIC_REDIST].base);
> +    } else {
> +        sysbus_mmio_map(gicbusdev, 1, vbi->memmap[VIRT_GIC_CPU].base);
> +    }
>  
>      /* Wire the outputs from each CPU's generic timer to the
>       * appropriate GIC PPI inputs, and the GIC's IRQ output to
> @@ -417,9 +452,11 @@ static void create_gic(VirtBoardInfo *vbi, qemu_irq *pic)
>          pic[i] = qdev_get_gpio_in(gicdev, i);
>      }
>  
> -    fdt_add_gic_node(vbi);
> +    fdt_add_gic_node(vbi, type);
>  
> -    create_v2m(vbi, pic);
> +    if (type == 2) {
> +        create_v2m(vbi, pic);
> +    }
>  }
>  
>  static void create_uart(const VirtBoardInfo *vbi, qemu_irq *pic)
> @@ -723,7 +760,10 @@ static void create_pcie(const VirtBoardInfo *vbi, qemu_irq *pic)
>      qemu_fdt_setprop_cells(vbi->fdt, nodename, "bus-range", 0,
>                             nr_pcie_buses - 1);
>  
> -    qemu_fdt_setprop_cells(vbi->fdt, nodename, "msi-parent", vbi->v2m_phandle);
> +    if (vbi->v2m_phandle) {
> +        qemu_fdt_setprop_cells(vbi->fdt, nodename, "msi-parent",
> +                               vbi->v2m_phandle);
> +    }
>  
>      qemu_fdt_setprop_sized_cells(vbi->fdt, nodename, "reg",
>                                   2, base_ecam, 2, size_ecam);
> @@ -883,7 +923,7 @@ static void machvirt_init(MachineState *machine)
>  
>      create_flash(vbi);
>  
> -    create_gic(vbi, pic);
> +    create_gic(vbi, pic, vms->gic_version);
>  
>      create_uart(vbi, pic);
>  
> @@ -941,6 +981,26 @@ static void virt_set_secure(Object *obj, bool value, Error **errp)
>      vms->secure = value;
>  }
>  
> +static void virt_get_gic_version(Object *obj, Visitor *v, void *opaque,
> +                                 const char *name, Error **errp)
> +{
> +    VirtMachineState *vms = VIRT_MACHINE(obj);
> +
> +    visit_type_int32(v, &vms->gic_version, name, errp);
> +}
> +
> +static void virt_set_gic_version(Object *obj, Visitor *v, void *opaque,
> +                                 const char *name, Error **errp)
> +{
> +    VirtMachineState *vms = VIRT_MACHINE(obj);
> +
> +    visit_type_int32(v, &vms->gic_version, name, errp);
> +    if (vms->gic_version != 2 && vms->gic_version != 3) {
> +        error_report ("Only GICv2 and GICv3 supported currently\n");
> +        exit(1);
> +    }
> +}
> +
>  static void virt_instance_init(Object *obj)
>  {
>      VirtMachineState *vms = VIRT_MACHINE(obj);
> @@ -953,6 +1013,14 @@ static void virt_instance_init(Object *obj)
>                                      "Set on/off to enable/disable the ARM "
>                                      "Security Extensions (TrustZone)",
>                                      NULL);
> +
> +    /* Default GIC type is v2 */
> +    vms->gic_version = 2;
In KVM case instead of assigning GICv2 as default, can we probe the KVM
for GICv3 presence using KVM_CREATE_DEVICE_TEST and give priority to
GICv3? Any suggestions?

Thanks,
Ashok
> +    object_property_add(obj, "gic-version", "int", virt_get_gic_version,
> +                        virt_set_gic_version, NULL, NULL, NULL);
> +    object_property_set_description(obj, "gic-version",
> +                                    "Set GIC version. "
> +                                    "Valid values are 2 and 3", NULL);
>  }
>  
>  static void virt_class_init(ObjectClass *oc, void *data)
> @@ -962,7 +1030,10 @@ static void virt_class_init(ObjectClass *oc, void *data)
>      mc->name = TYPE_VIRT_MACHINE;
>      mc->desc = "ARM Virtual Machine",
>      mc->init = machvirt_init;
> -    mc->max_cpus = 8;
> +    /* Our maximum number of CPUs depends on how many redistributors
> +     * we can fit into memory map
> +     */
> +    mc->max_cpus = a15memmap[VIRT_GIC_REDIST].size / 0x20000;
>      mc->has_dynamic_sysbus = true;
>      mc->block_default_type = IF_VIRTIO;
>      mc->no_cdrom = 1;
> diff --git a/include/hw/arm/fdt.h b/include/hw/arm/fdt.h
> index c3d5015..dd794dd 100644
> --- a/include/hw/arm/fdt.h
> +++ b/include/hw/arm/fdt.h
> @@ -29,6 +29,6 @@
>  #define GIC_FDT_IRQ_FLAGS_LEVEL_LO 8
>  
>  #define GIC_FDT_IRQ_PPI_CPU_START 8
> -#define GIC_FDT_IRQ_PPI_CPU_WIDTH 8
> +#define GIC_FDT_IRQ_PPI_CPU_WIDTH 24
>  
>  #endif
> diff --git a/include/hw/arm/virt.h b/include/hw/arm/virt.h
> index d22fd8e..6c5a9c9 100644
> --- a/include/hw/arm/virt.h
> +++ b/include/hw/arm/virt.h
> @@ -46,6 +46,10 @@ enum {
>      VIRT_CPUPERIPHS,
>      VIRT_GIC_DIST,
>      VIRT_GIC_CPU,
> +    VIRT_GIC_V2M,
> +    VIRT_ITS_CONTROL,
> +    VIRT_ITS_TRANSLATION,
> +    VIRT_GIC_REDIST,
>      VIRT_UART,
>      VIRT_MMIO,
>      VIRT_RTC,
> @@ -54,7 +58,6 @@ enum {
>      VIRT_PCIE_MMIO,
>      VIRT_PCIE_PIO,
>      VIRT_PCIE_ECAM,
> -    VIRT_GIC_V2M,
>      VIRT_PLATFORM_BUS,
>  };
>  
> -- 
> 1.9.5.msysgit.0
> 
> 

  reply	other threads:[~2015-08-25 13:41 UTC|newest]

Thread overview: 9+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-08-19  7:23 [Qemu-devel] [PATCH v11 0/5] vGICv3 support Pavel Fedin
2015-08-19  7:23 ` [Qemu-devel] [PATCH v11 1/5] hw/intc: Implement GIC-500 base class Pavel Fedin
2015-08-19  7:23 ` [Qemu-devel] [PATCH v11 2/5] intc/gic: Extract some reusable vGIC code Pavel Fedin
2015-08-19  7:23 ` [Qemu-devel] [PATCH v11 3/5] arm_kvm: Do not assume particular GIC type in kvm_arch_irqchip_create() Pavel Fedin
2015-08-19  7:23 ` [Qemu-devel] [PATCH v11 4/5] hw/intc: Initial implementation of vGICv3 Pavel Fedin
2015-08-19  7:23 ` [Qemu-devel] [PATCH v11 5/5] hw/arm/virt: Add gic-version option to virt machine Pavel Fedin
2015-08-25 13:40   ` Ashok Kumar [this message]
     [not found]   ` <"20150825134053.GB27329@ashoks"@broadcom.com>
2015-08-25 13:53     ` Pavel Fedin
2015-08-25 13:31 ` [Qemu-devel] [PATCH v11 0/5] vGICv3 support Ashok Kumar

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20150825134053.GB27329@ashoks@broadcom.com \
    --to=ashoks@broadcom.com \
    --cc=christoffer.dall@linaro.org \
    --cc=eric.auger@linaro.org \
    --cc=p.fedin@samsung.com \
    --cc=peter.maydell@linaro.org \
    --cc=qemu-devel@nongnu.org \
    --cc=shlomo.pongratz@huawei.com \
    --cc=shlomopongratz@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.