xen-devel.lists.xenproject.org archive mirror
 help / color / mirror / Atom feed
From: Julien Grall <julien.grall@citrix.com>
To: Vijay Kilari <vijay.kilari@gmail.com>
Cc: Ian Campbell <Ian.Campbell@citrix.com>,
	Stefano Stabellini <stefano.stabellini@eu.citrix.com>,
	Prasun Kapoor <Prasun.Kapoor@caviumnetworks.com>,
	manish.jaggi@caviumnetworks.com, Tim Deegan <tim@xen.org>,
	"xen-devel@lists.xen.org" <xen-devel@lists.xen.org>,
	Stefano Stabellini <stefano.stabellini@citrix.com>,
	Vijaya Kumar K <Vijaya.Kumar@caviumnetworks.com>
Subject: Re: [PATCH v5 12/22] xen/arm: ITS: Add GICR register emulation
Date: Fri, 31 Jul 2015 12:05:28 +0100	[thread overview]
Message-ID: <55BB5678.2040108@citrix.com> (raw)
In-Reply-To: <CALicx6txSfsMe+imhWHDszTqZw-2MZ1mSqGGChEKMoH7uZbBUA@mail.gmail.com>

On 31/07/15 10:08, Vijay Kilari wrote:
> On Thu, Jul 30, 2015 at 10:34 PM, Julien Grall <julien.grall@citrix.com> wrote:
>> Hi Vijay,
>>
>> On 27/07/15 12:11, vijay.kilari@gmail.com wrote:
>>> diff --git a/xen/arch/arm/gic-v3.c b/xen/arch/arm/gic-v3.c
>>
>> [..]
>>
>>> +static int gicv3_dist_supports_lpis(void)
>>> +{
>>> +    return readl_relaxed(GICD + GICD_TYPER) & GICD_TYPER_LPIS_SUPPORTED;
>>> +}
>>> +
>>>  static int __cpuinit gicv3_cpu_init(void)
>>>  {
>>>      int i;
>>> @@ -1274,6 +1279,11 @@ static int __init gicv3_init(void)
>>>
>>>      spin_lock(&gicv3.lock);
>>>
>>> +    if ( gicv3_dist_supports_lpis() )
>>> +        gicv3_info.lpi_supported = 1;
>>> +    else
>>> +        gicv3_info.lpi_supported = 0;
>>> +
>>
>> You will avoid 3 lines if you do:
>>
>> gicv3_info.lpi_supported = !!gicv3_dist_supports_lpis();
>>
> 
>    This will change in patch #17 where we do check for its_probe() to
> be succesful
> to set gicv3_info.lpi_supported

Then move this addition of lpi_supported in patch #17. This is not
necessary at all here. And this is quite confusing to see GIC specific
changes in vGIC code.

Overall, I think your series would benefits to be split in two parts.
First part would contains all the code for the hardware GIC/ITS driver.
The second part would be for virtual GIC/ITS changes.

>>>      gicv3_dist_init();
>>>      res = gicv3_cpu_init();
>>>      gicv3_hyp_init();
>>> diff --git a/xen/arch/arm/gic.c b/xen/arch/arm/gic.c
>>> index 1757193..af8a34b 100644
>>> --- a/xen/arch/arm/gic.c
>>> +++ b/xen/arch/arm/gic.c
>>> @@ -67,6 +67,11 @@ unsigned int gic_number_lines(void)
>>>      return gic_hw_ops->info->nr_lines;
>>>  }
>>>
>>> +bool_t gic_lpi_supported(void)
>>> +{
>>> +    return gic_hw_ops->info->lpi_supported;
>>> +}
>>> +
>>>  void gic_save_state(struct vcpu *v)
>>>  {
>>>      ASSERT(!local_irq_is_enabled());
>>> diff --git a/xen/arch/arm/vgic-v3-its.c b/xen/arch/arm/vgic-v3-its.c
>>> index 1c7d9b6..4afb62b 100644
>>> --- a/xen/arch/arm/vgic-v3-its.c
>>> +++ b/xen/arch/arm/vgic-v3-its.c
>>
>> Can you explain why the emulation of the LPI property table has to be
>> done in the vITS code?
>>
>> Overall, there is nothing vITS specific in this code and all the
>> functions you've introduced within this file are called only by the
>> vgic-v3 code.
> 
> yes, it is called from vgic-v3 code because it is emulating GICR_PROP/PEND
> registers.
> 
> This is emulating LPI property table. Hence all the LPI handling code is kept
> in vits file.
> GICR_PROP/PEND is defined only for LPI case.

You don't explain why the LPI handling code is kept in the vits file....
The LPI property table can exist even without the presence of
the ITS.

There is nothing ITS specific in the emulation, and your design prove it
(you are calling all the emulation code from the vGICv3).

>>
>>> @@ -28,6 +28,7 @@
>>>  #include <asm/io.h>
>>>  #include <asm/gic_v3_defs.h>
>>>  #include <asm/gic.h>
>>> +#include <asm/gic-its.h>
>>>  #include <asm/vgic.h>
>>>  #include <asm/gic-its.h>
>>>  #include <asm/atomic.h>
>>> @@ -76,6 +77,34 @@ static inline uint32_t vits_get_max_collections(struct domain *d)
>>>      return (d->max_vcpus + 1);
>>>  }
>>>
>>> +static void vits_disable_lpi(struct vcpu *v, uint32_t vlpi)
>>> +{
>>> +    struct pending_irq *p;
>>> +
>>> +    p = irq_to_pending(v, vlpi);
>>> +    clear_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
>>> +    gic_remove_from_queues(v, vlpi);
>>> +}
>>> +
>>> +static void vits_enable_lpi(struct vcpu *v, uint32_t vlpi, uint8_t priority)
>>> +{
>>> +    struct pending_irq *p;
>>> +    unsigned long flags;
>>> +
>>> +    p = irq_to_pending(v, vlpi);
>>> +
>>> +    set_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
>>> +
>>> +    spin_lock_irqsave(&v->arch.vgic.lock, flags);
>>> +
>>> +    /*XXX: raise on right vcpu */
>>
>> As said on the previous versions, I think there will be locking issue
>> given that pending_irq structure is protected by the vCPU where the IRQ
>> is locked.
> 
>  Can you please explain in detail why there is a locking issue.
> I remember this locking mechanism is coming from enable_irqs()
> as we follow same infrastructure to inject/process LPIs

I guess you mean vgic_enable_irqs? And no what you've implemented is
definitely not the same as vgic_enable_irqs.

vgic_enable_irqs is locking the pending_irq structure using the vgic
lock of the targeting VCPU (see v_target = ... ->get_target_cpu(...)).

Here, you are locking with the current vCPU, i.e the vCPU which wrote
into the LPI property table.

All the vGIC code is doing the same, so using the wrong locking won't
protect this structure.

> 
>>
>> If you think it's not the case please explain why but don't leave the
>> question unanswered.
>>
> [...]
>>>
>>> +
>>> +int vits_map_lpi_prop(struct domain *d)
>>> +{
>>> +    struct vgic_its *vits = d->arch.vgic.vits;
>>> +    paddr_t gaddr, addr;
>>> +    unsigned long mfn;
>>> +    uint32_t lpi_size, id_bits;
>>> +    int i;
>>> +
>>> +    gaddr = vits->propbase & MASK_4K;
>>
>> The physical address is only bits [47:12]. The uppers are either RES0 or
>> used for the OuterCache.
> 
> Can you please be more explicit. What is the issue here?

Sorry, I was confused by the MASK_4K which actually is not implemented
as the name suggested but which clearing the bits [63:48].

A correct MASK_4K would haven't clear the top bits. So the name of this
define is not right.

> 
>>
>>> +    id_bits = ((vits->propbase & GICR_PROPBASER_IDBITS_MASK) + 1);
>>> +
>>> +    if ( id_bits > d->arch.vgic.id_bits )
>>> +        id_bits = d->arch.vgic.id_bits;
>>
>> As said on v4, you are allowing the possibility to have a smaller
>> property table than the effective number of LPIs.
>>
>> An ASSERT in vits_get_priority (patch #16) doesn't ensure the validity
>> of the size of the property table provided by the guest. This will
>> surely crash Xen in debug mode, and who knows what will happen in
>> production mode.
> 
>  lpi_size is calculated based on id_bits. If it is smaller, the lpi_size will be
> smaller where only size of lpi_size is considered.

Where id_bits is based on what the guest provides in GICR_PROPBASER.
Although the guest, malicious or not, can decide to setup this id_bits
smaller than the number of vLPIs effectively supported by the gic-v3.

In this case, if a vLPI higher than this number is injected you will hit
the ASSERT(vlpi < vits->prop_size) in vits_get_priority. A guest
*should* not be able to crash Xen because it decides to send valid input.

> 
>>> diff --git a/xen/arch/arm/vgic-v3.c b/xen/arch/arm/vgic-v3.c
>>> index 683e3cc..a466a8f 100644
>>> --- a/xen/arch/arm/vgic-v3.c
>>> +++ b/xen/arch/arm/vgic-v3.c
>>> @@ -29,6 +29,8 @@
>>>  #include <asm/current.h>
>>>  #include <asm/mmio.h>
>>>  #include <asm/gic_v3_defs.h>
>>> +#include <asm/gic.h>
>>> +#include <asm/gic-its.h>
>>>  #include <asm/vgic.h>
>>>
>>>  /* GICD_PIDRn register values for ARM implementations */
>>> @@ -109,29 +111,47 @@ static int __vgic_v3_rdistr_rd_mmio_read(struct vcpu *v, mmio_info_t *info,
>>>      struct hsr_dabt dabt = info->dabt;
>>>      struct cpu_user_regs *regs = guest_cpu_user_regs();
>>>      register_t *r = select_user_reg(regs, dabt.reg);
>>> -    uint64_t aff;
>>> +    uint64_t aff, val;
>>>
>>>      switch ( gicr_reg )
>>>      {
>>>      case GICR_CTLR:
>>> -        /* We have not implemented LPI's, read zero */
>>> -        goto read_as_zero_32;
>>> +        if ( dabt.size != DABT_WORD ) goto bad_width;
>>> +        vgic_lock(v);
>>> +        *r = v->domain->arch.vgic.gicr_ctlr;
>>> +        vgic_unlock(v);
>>> +        return 1;
>>>      case GICR_IIDR:
>>>          if ( dabt.size != DABT_WORD ) goto bad_width;
>>>          *r = GICV3_GICR_IIDR_VAL;
>>>          return 1;
>>>      case GICR_TYPER:
>>> -        if ( dabt.size != DABT_DOUBLE_WORD ) goto bad_width;
>>> -        /* TBD: Update processor id in [23:8] when ITS support is added */
>>> +    case GICR_TYPER + 4:
>>
>> Why did you introduce it only in v5? This change is not related to the
>> LPI but a correct implementation of access size on GICv3 register.
>>
>> Overall, I think this should be done in a separate patch for all the
>> registers and not only this one. It would make the code change less
>> complicate to read.
>>
>> Please fix the write version of TYPER which happen to be 64 bits only too.
> 
> I added it because, after updating my Linux kernel driver, I see that it
>  is making 32-bit access to TYPER register

This change should go in a separate patch then. It's not related to this
patch.

> 
> static bool gic_rdists_supports_plpis(void)
> {
> return !!(readl_relaxed(gic_data_rdist_rd_base() + GICR_TYPER) &
> GICR_TYPER_PLPIS);
> }
> 
> But spec doesn't say it supports 32-bit access.

8.1.3 ARM IHI 0069A

"For the GITS_*, GICD_* and GICR_* registers, the upper 32 bits and the
lower 32 bits can be accessed
independently, unless the register requires a 64 bit access."

Regards,

-- 
Julien Grall

  reply	other threads:[~2015-07-31 11:05 UTC|newest]

Thread overview: 81+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-07-27 11:11 [PATCH v5 00/22] Add ITS support vijay.kilari
2015-07-27 11:11 ` [PATCH v5 01/22] xen/arm: Return success if dt node does not have irq mapping vijay.kilari
2015-07-28 13:13   ` Julien Grall
2015-07-28 13:23     ` Ian Campbell
2015-07-28 13:27       ` Julien Grall
2015-09-02 15:25   ` Ian Campbell
2015-07-27 11:11 ` [PATCH v5 02/22] xen/arm: Add bitmap_find_next_zero_area helper function vijay.kilari
2015-08-11 13:53   ` Jan Beulich
2015-07-27 11:11 ` [PATCH v5 03/22] xen: Add log2 functionality vijay.kilari
2015-07-27 11:11 ` [PATCH v5 04/22] xen/arm: Set nr_cpu_ids to available number of cpus vijay.kilari
2015-07-28 13:21   ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 05/22] xen/arm: ITS: Port ITS driver to Xen vijay.kilari
2015-07-28 16:46   ` Julien Grall
2015-07-29 15:22     ` Vijay Kilari
2015-07-29 16:06       ` Ian Campbell
2015-07-29 16:18         ` Vijay Kilari
2015-07-31 10:28     ` Vijay Kilari
2015-07-31 11:10       ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 06/22] xen/arm: ITS: Add helper functions to manage its_devices vijay.kilari
2015-07-27 11:11 ` [PATCH v5 07/22] xen/arm: ITS: Add virtual ITS driver vijay.kilari
2015-07-28 17:13   ` Julien Grall
2015-07-31  6:49     ` Vijay Kilari
2015-07-31 10:14       ` Julien Grall
2015-07-31 10:32         ` Ian Campbell
2015-07-27 11:11 ` [PATCH v5 08/22] xen/arm: ITS: Add virtual ITS commands support vijay.kilari
2015-07-28 18:04   ` Julien Grall
2015-07-31  6:57     ` Vijay Kilari
2015-07-31 10:16       ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 09/22] xen/arm: ITS: Export ITS info to Virtual ITS vijay.kilari
2015-07-28 18:14   ` Julien Grall
2015-07-31  7:01     ` Vijay Kilari
2015-08-03 15:58       ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 10/22] xen/arm: ITS: Add GITS registers emulation vijay.kilari
2015-07-28 19:01   ` Julien Grall
2015-07-31  7:25     ` Vijay Kilari
2015-07-31 10:28       ` Julien Grall
2015-08-01  8:50     ` Vijay Kilari
2015-08-03 11:19       ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 11/22] xen/arm: ITS: Enable physical and virtual ITS driver compilation vijay.kilari
2015-07-27 11:11 ` [PATCH v5 12/22] xen/arm: ITS: Add GICR register emulation vijay.kilari
2015-07-30 17:04   ` Julien Grall
2015-07-31  9:08     ` Vijay Kilari
2015-07-31 11:05       ` Julien Grall [this message]
2015-08-01 10:25         ` Vijay Kilari
2015-08-01 15:51           ` Julien Grall
2015-08-03  9:36             ` Vijay Kilari
2015-08-03 13:01               ` Julien Grall
2015-08-03 13:51                 ` Vijay Kilari
2015-08-03 13:58                   ` Julien Grall
2015-08-04  6:55                     ` Vijay Kilari
2015-08-04  8:44                       ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 13/22] xen/arm: ITS: Implement gic_is_lpi helper function vijay.kilari
2015-07-30 17:14   ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 14/22] xen/arm: ITS: Allocate irq descriptors for LPIs vijay.kilari
2015-08-04 13:21   ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 15/22] xen/arm: ITS: implement hw_irq_controller " vijay.kilari
2015-08-04 13:45   ` Julien Grall
2015-08-06  8:15     ` Vijay Kilari
2015-08-06 10:05       ` Julien Grall
2015-08-06 10:11         ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 16/22] xen/arm: ITS: Route LPIs vijay.kilari
2015-08-04 14:54   ` Julien Grall
2015-07-27 11:11 ` [PATCH v5 17/22] xen/arm: ITS: Initialize physical ITS vijay.kilari
2015-08-17 19:00   ` Julien Grall
2015-07-27 11:12 ` [PATCH v5 18/22] xen/arm: ITS: Add domain specific ITS initialization vijay.kilari
2015-08-17 18:57   ` Julien Grall
2015-07-27 11:12 ` [PATCH v5 19/22] xen/arm: ITS: Add APIs to add and assign device vijay.kilari
2015-08-17 19:17   ` Julien Grall
2015-07-27 11:12 ` [PATCH v5 20/22] xen/arm: ITS: Map ITS translation space vijay.kilari
2015-08-17 19:20   ` Julien Grall
2015-08-18 19:14   ` Julien Grall
2015-08-18 22:37     ` Marc Zyngier
2015-09-02 15:45       ` Ian Campbell
2015-09-02 15:59         ` Marc Zyngier
2015-07-27 11:12 ` [PATCH v5 21/22] xen/arm: ITS: Generate ITS node for Dom0 vijay.kilari
2015-08-17 19:41   ` Julien Grall
2015-08-21 23:02     ` Vijay Kilari
2015-08-21 23:48       ` Julien Grall
2015-08-26 12:40     ` Vijay Kilari
2015-08-27  0:02       ` Julien Grall
2015-07-27 11:12 ` [PATCH v5 22/22] xen/arm: ITS: Add pci devices in ThunderX vijay.kilari

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=55BB5678.2040108@citrix.com \
    --to=julien.grall@citrix.com \
    --cc=Ian.Campbell@citrix.com \
    --cc=Prasun.Kapoor@caviumnetworks.com \
    --cc=Vijaya.Kumar@caviumnetworks.com \
    --cc=manish.jaggi@caviumnetworks.com \
    --cc=stefano.stabellini@citrix.com \
    --cc=stefano.stabellini@eu.citrix.com \
    --cc=tim@xen.org \
    --cc=vijay.kilari@gmail.com \
    --cc=xen-devel@lists.xen.org \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).