* [PATCH 0/2] vgic emulation and GICD_ITARGETSR
@ 2014-05-25 18:06 Stefano Stabellini
2014-05-25 18:06 ` [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0 Stefano Stabellini
` (2 more replies)
0 siblings, 3 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-05-25 18:06 UTC (permalink / raw)
To: xen-devel; +Cc: Julien Grall, Ian Campbell, Stefano Stabellini
Hi all,
this small patch series improves vgic emulation in relation to
GICD_ITARGETSR and irq delivery.
At the moment we don't support irq delivery to vcpu != 0, so prevent the
guest from setting itarget to something != 0.
vgic_enable_irqs and vgic_disable_irqs currently ignore the itarget
settings and just enable/disable irqs on the current vcpu. Fix their
behaviour to enable/disable irqs on the vcpu set by itarget, that is
always vcpu0 for irq >= 32.
Stefano Stabellini (2):
xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0.
xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
xen/arch/arm/vgic.c | 47 +++++++++++++++++++++++++++++++++++++++--------
1 file changed, 39 insertions(+), 8 deletions(-)
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0.
2014-05-25 18:06 [PATCH 0/2] vgic emulation and GICD_ITARGETSR Stefano Stabellini
@ 2014-05-25 18:06 ` Stefano Stabellini
2014-05-25 19:01 ` Julien Grall
2014-05-25 18:06 ` [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs Stefano Stabellini
2014-05-28 13:33 ` [PATCH 0/2] vgic emulation and GICD_ITARGETSR Ian Campbell
2 siblings, 1 reply; 13+ messages in thread
From: Stefano Stabellini @ 2014-05-25 18:06 UTC (permalink / raw)
To: xen-devel; +Cc: julien.grall, Ian.Campbell, Stefano Stabellini
Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
---
xen/arch/arm/vgic.c | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
index 4869b87..e4f38a0 100644
--- a/xen/arch/arm/vgic.c
+++ b/xen/arch/arm/vgic.c
@@ -581,6 +581,11 @@ static int vgic_distr_mmio_write(struct vcpu *v, mmio_info_t *info)
if ( dabt.size != 0 && dabt.size != 2 ) goto bad_width;
rank = vgic_irq_rank(v, 8, gicd_reg - GICD_ITARGETSR);
if ( rank == NULL) goto write_ignore;
+ if ( *r )
+ {
+ gdprintk(XENLOG_DEBUG, "SPI delivery to seconday cpus is unimplemented\n");
+ return 1;
+ }
vgic_lock_rank(v, rank);
if ( dabt.size == 2 )
rank->itargets[REG_RANK_INDEX(8, gicd_reg - GICD_ITARGETSR)] = *r;
--
1.7.10.4
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-25 18:06 [PATCH 0/2] vgic emulation and GICD_ITARGETSR Stefano Stabellini
2014-05-25 18:06 ` [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0 Stefano Stabellini
@ 2014-05-25 18:06 ` Stefano Stabellini
2014-05-27 16:54 ` Julien Grall
2014-05-28 13:38 ` Ian Campbell
2014-05-28 13:33 ` [PATCH 0/2] vgic emulation and GICD_ITARGETSR Ian Campbell
2 siblings, 2 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-05-25 18:06 UTC (permalink / raw)
To: xen-devel; +Cc: julien.grall, Ian.Campbell, Stefano Stabellini
vgic_enable_irqs should enable irq delivery to the vcpu specified by
GICD_ITARGETSR, rather than the vcpu that wrote to GICD_ISENABLER.
Similarly vgic_disable_irqs should use the target vcpu specified by
itarget to disable irqs.
Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
---
xen/arch/arm/vgic.c | 42 ++++++++++++++++++++++++++++++++++--------
1 file changed, 34 insertions(+), 8 deletions(-)
diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
index e4f38a0..0f0ba1d 100644
--- a/xen/arch/arm/vgic.c
+++ b/xen/arch/arm/vgic.c
@@ -376,12 +376,25 @@ static void vgic_disable_irqs(struct vcpu *v, uint32_t r, int n)
unsigned int irq;
unsigned long flags;
int i = 0;
+ int target;
+ struct vcpu *v_target;
+ struct vgic_irq_rank *rank;
while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
irq = i + (32 * n);
- p = irq_to_pending(v, irq);
+ rank = vgic_irq_rank(v, 1, irq/32);
+ vgic_lock_rank(v, rank);
+ if ( irq >= 32 )
+ {
+ target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
+ target &= 0xff;
+ v_target = v->domain->vcpu[target];
+ } else
+ v_target = v;
+ vgic_unlock_rank(v, rank);
+ p = irq_to_pending(v_target, irq);
clear_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
- gic_remove_from_queues(v, irq);
+ gic_remove_from_queues(v_target, irq);
if ( p->desc != NULL )
{
spin_lock_irqsave(&p->desc->lock, flags);
@@ -399,21 +412,34 @@ static void vgic_enable_irqs(struct vcpu *v, uint32_t r, int n)
unsigned int irq;
unsigned long flags;
int i = 0;
+ int target;
+ struct vcpu *v_target;
+ struct vgic_irq_rank *rank;
while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
irq = i + (32 * n);
- p = irq_to_pending(v, irq);
+ rank = vgic_irq_rank(v, 1, irq/32);
+ vgic_lock_rank(v, rank);
+ if ( irq >= 32 )
+ {
+ target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
+ target &= 0xff;
+ v_target = v->domain->vcpu[target];
+ } else
+ v_target = v;
+ vgic_unlock_rank(v, rank);
+ p = irq_to_pending(v_target, irq);
set_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
- if ( irq == v->domain->arch.evtchn_irq &&
+ if ( irq == v_target->domain->arch.evtchn_irq &&
vcpu_info(current, evtchn_upcall_pending) &&
list_empty(&p->inflight) )
- vgic_vcpu_inject_irq(v, irq);
+ vgic_vcpu_inject_irq(v_target, irq);
else {
unsigned long flags;
- spin_lock_irqsave(&v->arch.vgic.lock, flags);
+ spin_lock_irqsave(&v_target->arch.vgic.lock, flags);
if ( !list_empty(&p->inflight) && !test_bit(GIC_IRQ_GUEST_VISIBLE, &p->status) )
- gic_raise_guest_irq(v, irq, p->priority);
- spin_unlock_irqrestore(&v->arch.vgic.lock, flags);
+ gic_raise_guest_irq(v_target, irq, p->priority);
+ spin_unlock_irqrestore(&v_target->arch.vgic.lock, flags);
}
if ( p->desc != NULL )
{
--
1.7.10.4
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0.
2014-05-25 18:06 ` [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0 Stefano Stabellini
@ 2014-05-25 19:01 ` Julien Grall
2014-05-27 16:24 ` Stefano Stabellini
0 siblings, 1 reply; 13+ messages in thread
From: Julien Grall @ 2014-05-25 19:01 UTC (permalink / raw)
To: Stefano Stabellini, xen-devel; +Cc: julien.grall, Ian.Campbell
Hi Stefano,
On 25/05/14 19:06, Stefano Stabellini wrote:
> Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
> ---
> xen/arch/arm/vgic.c | 5 +++++
> 1 file changed, 5 insertions(+)
>
> diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
> index 4869b87..e4f38a0 100644
> --- a/xen/arch/arm/vgic.c
> +++ b/xen/arch/arm/vgic.c
> @@ -581,6 +581,11 @@ static int vgic_distr_mmio_write(struct vcpu *v, mmio_info_t *info)
> if ( dabt.size != 0 && dabt.size != 2 ) goto bad_width;
> rank = vgic_irq_rank(v, 8, gicd_reg - GICD_ITARGETSR);
> if ( rank == NULL) goto write_ignore;
> + if ( *r )
This is wrong, ITARGETSR store a 4 bitmask of CPUs, one per interrupt.
Each bit of the mask correspond to a CPU (see Table 4-17 in the GICv2
manual).
Furthermore, I think it's safe to just ignore write. The manual says:
"It is IMPLEMENTATION DEFINED which, if any, SPIs are statically
configured in hardware. The CPU targets field for such an SPI is
read-only, and returns a value that indicates the CPU targets for the
interrupt."
With the former comment, your patch #2 is also wrong.
> + {
> + gdprintk(XENLOG_DEBUG, "SPI delivery to seconday cpus is unimplemented\n");
s/seconday/secondary/
Regards,
--
Julien Grall
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0.
2014-05-25 19:01 ` Julien Grall
@ 2014-05-27 16:24 ` Stefano Stabellini
0 siblings, 0 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-05-27 16:24 UTC (permalink / raw)
To: Julien Grall; +Cc: julien.grall, xen-devel, Ian.Campbell, Stefano Stabellini
On Sun, 25 May 2014, Julien Grall wrote:
> Hi Stefano,
>
> On 25/05/14 19:06, Stefano Stabellini wrote:
> > Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
> > ---
> > xen/arch/arm/vgic.c | 5 +++++
> > 1 file changed, 5 insertions(+)
> >
> > diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
> > index 4869b87..e4f38a0 100644
> > --- a/xen/arch/arm/vgic.c
> > +++ b/xen/arch/arm/vgic.c
> > @@ -581,6 +581,11 @@ static int vgic_distr_mmio_write(struct vcpu *v,
> > mmio_info_t *info)
> > if ( dabt.size != 0 && dabt.size != 2 ) goto bad_width;
> > rank = vgic_irq_rank(v, 8, gicd_reg - GICD_ITARGETSR);
> > if ( rank == NULL) goto write_ignore;
> > + if ( *r )
>
> This is wrong, ITARGETSR store a 4 bitmask of CPUs, one per interrupt. Each
> bit of the mask correspond to a CPU (see Table 4-17 in the GICv2 manual).
you are right
> Furthermore, I think it's safe to just ignore write. The manual says:
> "It is IMPLEMENTATION DEFINED which, if any, SPIs are statically configured in
> hardware. The CPU targets field for such an SPI is read-only, and returns a
> value that indicates the CPU targets for the interrupt."
Good point
> With the former comment, your patch #2 is also wrong.
Patch #2 is valid regardless of the specific itarget setting
> > + {
> > + gdprintk(XENLOG_DEBUG, "SPI delivery to seconday cpus is
> > unimplemented\n");
>
> s/seconday/secondary/
>
> Regards,
>
> --
> Julien Grall
>
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-25 18:06 ` [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs Stefano Stabellini
@ 2014-05-27 16:54 ` Julien Grall
2014-05-27 17:02 ` Stefano Stabellini
2014-05-28 13:38 ` Ian Campbell
1 sibling, 1 reply; 13+ messages in thread
From: Julien Grall @ 2014-05-27 16:54 UTC (permalink / raw)
To: Stefano Stabellini, xen-devel; +Cc: julien.grall, Ian.Campbell
Hi Stefano,
On 05/25/2014 07:06 PM, Stefano Stabellini wrote:
> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> irq = i + (32 * n);
> - p = irq_to_pending(v, irq);
> + rank = vgic_irq_rank(v, 1, irq/32);
> + vgic_lock_rank(v, rank);
> + if ( irq >= 32 )
> + {
> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> + target &= 0xff;
> + v_target = v->domain->vcpu[target];
Without looking to the target stuff (see comment on patch #1), I don't
need to do a specific case for SPIs.
It will avoid diverging following the IRQ type.
Regards,
--
Julien Grall
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-27 16:54 ` Julien Grall
@ 2014-05-27 17:02 ` Stefano Stabellini
2014-05-27 17:09 ` Julien Grall
2014-05-27 17:10 ` Julien Grall
0 siblings, 2 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-05-27 17:02 UTC (permalink / raw)
To: Julien Grall; +Cc: julien.grall, xen-devel, Ian.Campbell, Stefano Stabellini
On Tue, 27 May 2014, Julien Grall wrote:
> Hi Stefano,
>
> On 05/25/2014 07:06 PM, Stefano Stabellini wrote:
> > while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> > irq = i + (32 * n);
> > - p = irq_to_pending(v, irq);
> > + rank = vgic_irq_rank(v, 1, irq/32);
> > + vgic_lock_rank(v, rank);
> > + if ( irq >= 32 )
> > + {
> > + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> > + target &= 0xff;
> > + v_target = v->domain->vcpu[target];
>
> Without looking to the target stuff (see comment on patch #1), I don't
> need to do a specific case for SPIs.
>
> It will avoid diverging following the IRQ type.
Sooner or later we'll implement SPI delivery to vcpu != 0. When we do
we'll actually need this patch, that is correct even without SPI
delivery to vcpu != 0.
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-27 17:02 ` Stefano Stabellini
@ 2014-05-27 17:09 ` Julien Grall
2014-05-27 17:10 ` Julien Grall
1 sibling, 0 replies; 13+ messages in thread
From: Julien Grall @ 2014-05-27 17:09 UTC (permalink / raw)
To: Stefano Stabellini; +Cc: julien.grall, xen-devel, Ian.Campbell
On 05/27/2014 06:02 PM, Stefano Stabellini wrote:
> On Tue, 27 May 2014, Julien Grall wrote:
>> On 05/25/2014 07:06 PM, Stefano Stabellini wrote:
>>> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
>>> irq = i + (32 * n);
>>> - p = irq_to_pending(v, irq);
>>> + rank = vgic_irq_rank(v, 1, irq/32);
>>> + vgic_lock_rank(v, rank);
>>> + if ( irq >= 32 )
>>> + {
>>> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
>>> + target &= 0xff;
>>> + v_target = v->domain->vcpu[target];
>>
>> Without looking to the target stuff (see comment on patch #1), I don't
>> need to do a specific case for SPIs.
>>
>> It will avoid diverging following the IRQ type.
>
> Sooner or later we'll implement SPI delivery to vcpu != 0. When we do
> we'll actually need this patch, that is correct even without SPI
> delivery to vcpu != 0.
>
Hrrrm .... right I forgot this case. If so, the vgic_irq_rank_lock
doesn't need to be taken for non-SPIs.
Regards,
--
Julien Grall
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-27 17:02 ` Stefano Stabellini
2014-05-27 17:09 ` Julien Grall
@ 2014-05-27 17:10 ` Julien Grall
2014-06-03 14:24 ` Stefano Stabellini
1 sibling, 1 reply; 13+ messages in thread
From: Julien Grall @ 2014-05-27 17:10 UTC (permalink / raw)
To: Stefano Stabellini; +Cc: julien.grall, xen-devel, Ian.Campbell
On 05/27/2014 06:02 PM, Stefano Stabellini wrote:
> On Tue, 27 May 2014, Julien Grall wrote:
>> Hi Stefano,
>>
>> On 05/25/2014 07:06 PM, Stefano Stabellini wrote:
>>> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
>>> irq = i + (32 * n);
>>> - p = irq_to_pending(v, irq);
>>> + rank = vgic_irq_rank(v, 1, irq/32);
>>> + vgic_lock_rank(v, rank);
>>> + if ( irq >= 32 )
>>> + {
>>> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
>>> + target &= 0xff;
>>> + v_target = v->domain->vcpu[target];
>>
>> Without looking to the target stuff (see comment on patch #1), I don't
>> need to do a specific case for SPIs.
>>
>> It will avoid diverging following the IRQ type.
>
> Sooner or later we'll implement SPI delivery to vcpu != 0. When we do
> we'll actually need this patch, that is correct even without SPI
> delivery to vcpu != 0.
>
To be clear, I didn't say this patch was not useful. I just say we can
merge the code and do use the same path for non-SPIs.
Regards,
--
Julien Grall
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 0/2] vgic emulation and GICD_ITARGETSR
2014-05-25 18:06 [PATCH 0/2] vgic emulation and GICD_ITARGETSR Stefano Stabellini
2014-05-25 18:06 ` [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0 Stefano Stabellini
2014-05-25 18:06 ` [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs Stefano Stabellini
@ 2014-05-28 13:33 ` Ian Campbell
2 siblings, 0 replies; 13+ messages in thread
From: Ian Campbell @ 2014-05-28 13:33 UTC (permalink / raw)
To: Stefano Stabellini; +Cc: Julien Grall, xen-devel
On Sun, 2014-05-25 at 19:06 +0100, Stefano Stabellini wrote:
> Hi all,
> this small patch series improves vgic emulation in relation to
> GICD_ITARGETSR and irq delivery.
>
> At the moment we don't support irq delivery to vcpu != 0, so prevent the
> guest from setting itarget to something != 0.
How hard would this be to support? I think all interrupts already all
arrive at pCPU==0, so we must be capable of forwarding them to whichever
pCPU might be running vCPU==0? Is extending that to select wihch vcpu to
send to hard?
> vgic_enable_irqs and vgic_disable_irqs currently ignore the itarget
> settings and just enable/disable irqs on the current vcpu. Fix their
> behaviour to enable/disable irqs on the vcpu set by itarget, that is
> always vcpu0 for irq >= 32.
>
>
> Stefano Stabellini (2):
> xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0.
> xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
>
> xen/arch/arm/vgic.c | 47 +++++++++++++++++++++++++++++++++++++++--------
> 1 file changed, 39 insertions(+), 8 deletions(-)
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-25 18:06 ` [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs Stefano Stabellini
2014-05-27 16:54 ` Julien Grall
@ 2014-05-28 13:38 ` Ian Campbell
2014-06-03 14:03 ` Stefano Stabellini
1 sibling, 1 reply; 13+ messages in thread
From: Ian Campbell @ 2014-05-28 13:38 UTC (permalink / raw)
To: Stefano Stabellini; +Cc: julien.grall, xen-devel
On Sun, 2014-05-25 at 19:06 +0100, Stefano Stabellini wrote:
> vgic_enable_irqs should enable irq delivery to the vcpu specified by
> GICD_ITARGETSR, rather than the vcpu that wrote to GICD_ISENABLER.
> Similarly vgic_disable_irqs should use the target vcpu specified by
> itarget to disable irqs.
>
> Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
> ---
> xen/arch/arm/vgic.c | 42 ++++++++++++++++++++++++++++++++++--------
> 1 file changed, 34 insertions(+), 8 deletions(-)
>
> diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
> index e4f38a0..0f0ba1d 100644
> --- a/xen/arch/arm/vgic.c
> +++ b/xen/arch/arm/vgic.c
> @@ -376,12 +376,25 @@ static void vgic_disable_irqs(struct vcpu *v, uint32_t r, int n)
> unsigned int irq;
> unsigned long flags;
> int i = 0;
> + int target;
> + struct vcpu *v_target;
> + struct vgic_irq_rank *rank;
>
> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> irq = i + (32 * n);
> - p = irq_to_pending(v, irq);
> + rank = vgic_irq_rank(v, 1, irq/32);
> + vgic_lock_rank(v, rank);
> + if ( irq >= 32 )
> + {
> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> + target &= 0xff;
This is byte_read(), isn't it?
> + v_target = v->domain->vcpu[target];
There needs to be some sort of range check here I think. Else you are
setting a trap for whoever implements itargets properly.
> + } else
> + v_target = v;
> + vgic_unlock_rank(v, rank);
> + p = irq_to_pending(v_target, irq);
> clear_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
> - gic_remove_from_queues(v, irq);
> + gic_remove_from_queues(v_target, irq);
> if ( p->desc != NULL )
> {
> spin_lock_irqsave(&p->desc->lock, flags);
> @@ -399,21 +412,34 @@ static void vgic_enable_irqs(struct vcpu *v, uint32_t r, int n)
> unsigned int irq;
> unsigned long flags;
> int i = 0;
> + int target;
> + struct vcpu *v_target;
> + struct vgic_irq_rank *rank;
>
> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> irq = i + (32 * n);
> - p = irq_to_pending(v, irq);
> + rank = vgic_irq_rank(v, 1, irq/32);
> + vgic_lock_rank(v, rank);
> + if ( irq >= 32 )
> + {
> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> + target &= 0xff;
> + v_target = v->domain->vcpu[target];
> + } else
> + v_target = v;
This is the same code as above -- there should be a helper
(get_target_vcpu or some such).
> + vgic_unlock_rank(v, rank);
> + p = irq_to_pending(v_target, irq);
> set_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
> - if ( irq == v->domain->arch.evtchn_irq &&
> + if ( irq == v_target->domain->arch.evtchn_irq &&
> vcpu_info(current, evtchn_upcall_pending) &&
> list_empty(&p->inflight) )
> - vgic_vcpu_inject_irq(v, irq);
> + vgic_vcpu_inject_irq(v_target, irq);
> else {
> unsigned long flags;
> - spin_lock_irqsave(&v->arch.vgic.lock, flags);
> + spin_lock_irqsave(&v_target->arch.vgic.lock, flags);
> if ( !list_empty(&p->inflight) && !test_bit(GIC_IRQ_GUEST_VISIBLE, &p->status) )
> - gic_raise_guest_irq(v, irq, p->priority);
> - spin_unlock_irqrestore(&v->arch.vgic.lock, flags);
> + gic_raise_guest_irq(v_target, irq, p->priority);
> + spin_unlock_irqrestore(&v_target->arch.vgic.lock, flags);
> }
> if ( p->desc != NULL )
> {
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-28 13:38 ` Ian Campbell
@ 2014-06-03 14:03 ` Stefano Stabellini
0 siblings, 0 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-06-03 14:03 UTC (permalink / raw)
To: Ian Campbell; +Cc: julien.grall, xen-devel, Stefano Stabellini
On Wed, 28 May 2014, Ian Campbell wrote:
> On Sun, 2014-05-25 at 19:06 +0100, Stefano Stabellini wrote:
> > vgic_enable_irqs should enable irq delivery to the vcpu specified by
> > GICD_ITARGETSR, rather than the vcpu that wrote to GICD_ISENABLER.
> > Similarly vgic_disable_irqs should use the target vcpu specified by
> > itarget to disable irqs.
> >
> > Signed-off-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
> > ---
> > xen/arch/arm/vgic.c | 42 ++++++++++++++++++++++++++++++++++--------
> > 1 file changed, 34 insertions(+), 8 deletions(-)
> >
> > diff --git a/xen/arch/arm/vgic.c b/xen/arch/arm/vgic.c
> > index e4f38a0..0f0ba1d 100644
> > --- a/xen/arch/arm/vgic.c
> > +++ b/xen/arch/arm/vgic.c
> > @@ -376,12 +376,25 @@ static void vgic_disable_irqs(struct vcpu *v, uint32_t r, int n)
> > unsigned int irq;
> > unsigned long flags;
> > int i = 0;
> > + int target;
> > + struct vcpu *v_target;
> > + struct vgic_irq_rank *rank;
> >
> > while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> > irq = i + (32 * n);
> > - p = irq_to_pending(v, irq);
> > + rank = vgic_irq_rank(v, 1, irq/32);
> > + vgic_lock_rank(v, rank);
> > + if ( irq >= 32 )
> > + {
> > + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> > + target &= 0xff;
>
> This is byte_read(), isn't it?
yes, I'll use it
> > + v_target = v->domain->vcpu[target];
>
> There needs to be some sort of range check here I think. Else you are
> setting a trap for whoever implements itargets properly.
The check should be at the point where we write itargets, not here.
The previous patch already introduces a check for itargets to always be
zero.
> > + } else
> > + v_target = v;
> > + vgic_unlock_rank(v, rank);
> > + p = irq_to_pending(v_target, irq);
> > clear_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
> > - gic_remove_from_queues(v, irq);
> > + gic_remove_from_queues(v_target, irq);
> > if ( p->desc != NULL )
> > {
> > spin_lock_irqsave(&p->desc->lock, flags);
> > @@ -399,21 +412,34 @@ static void vgic_enable_irqs(struct vcpu *v, uint32_t r, int n)
> > unsigned int irq;
> > unsigned long flags;
> > int i = 0;
> > + int target;
> > + struct vcpu *v_target;
> > + struct vgic_irq_rank *rank;
> >
> > while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> > irq = i + (32 * n);
> > - p = irq_to_pending(v, irq);
> > + rank = vgic_irq_rank(v, 1, irq/32);
> > + vgic_lock_rank(v, rank);
> > + if ( irq >= 32 )
> > + {
> > + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> > + target &= 0xff;
> > + v_target = v->domain->vcpu[target];
> > + } else
> > + v_target = v;
>
> This is the same code as above -- there should be a helper
> (get_target_vcpu or some such).
Good idea
> > + vgic_unlock_rank(v, rank);
> > + p = irq_to_pending(v_target, irq);
> > set_bit(GIC_IRQ_GUEST_ENABLED, &p->status);
> > - if ( irq == v->domain->arch.evtchn_irq &&
> > + if ( irq == v_target->domain->arch.evtchn_irq &&
> > vcpu_info(current, evtchn_upcall_pending) &&
> > list_empty(&p->inflight) )
> > - vgic_vcpu_inject_irq(v, irq);
> > + vgic_vcpu_inject_irq(v_target, irq);
> > else {
> > unsigned long flags;
> > - spin_lock_irqsave(&v->arch.vgic.lock, flags);
> > + spin_lock_irqsave(&v_target->arch.vgic.lock, flags);
> > if ( !list_empty(&p->inflight) && !test_bit(GIC_IRQ_GUEST_VISIBLE, &p->status) )
> > - gic_raise_guest_irq(v, irq, p->priority);
> > - spin_unlock_irqrestore(&v->arch.vgic.lock, flags);
> > + gic_raise_guest_irq(v_target, irq, p->priority);
> > + spin_unlock_irqrestore(&v_target->arch.vgic.lock, flags);
> > }
> > if ( p->desc != NULL )
> > {
>
>
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs
2014-05-27 17:10 ` Julien Grall
@ 2014-06-03 14:24 ` Stefano Stabellini
0 siblings, 0 replies; 13+ messages in thread
From: Stefano Stabellini @ 2014-06-03 14:24 UTC (permalink / raw)
To: Julien Grall; +Cc: julien.grall, xen-devel, Ian.Campbell, Stefano Stabellini
On Tue, 27 May 2014, Julien Grall wrote:
> On 05/27/2014 06:02 PM, Stefano Stabellini wrote:
> > On Tue, 27 May 2014, Julien Grall wrote:
> >> Hi Stefano,
> >>
> >> On 05/25/2014 07:06 PM, Stefano Stabellini wrote:
> >>> while ( (i = find_next_bit(&mask, 32, i)) < 32 ) {
> >>> irq = i + (32 * n);
> >>> - p = irq_to_pending(v, irq);
> >>> + rank = vgic_irq_rank(v, 1, irq/32);
> >>> + vgic_lock_rank(v, rank);
> >>> + if ( irq >= 32 )
> >>> + {
> >>> + target = rank->itargets[(irq%32)/4] >> (8*(irq % 4));
> >>> + target &= 0xff;
> >>> + v_target = v->domain->vcpu[target];
> >>
> >> Without looking to the target stuff (see comment on patch #1), I don't
> >> need to do a specific case for SPIs.
> >>
> >> It will avoid diverging following the IRQ type.
> >
> > Sooner or later we'll implement SPI delivery to vcpu != 0. When we do
> > we'll actually need this patch, that is correct even without SPI
> > delivery to vcpu != 0.
> >
>
> To be clear, I didn't say this patch was not useful. I just say we can
> merge the code and do use the same path for non-SPIs.
Ah OK
^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2014-06-03 14:24 UTC | newest]
Thread overview: 13+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2014-05-25 18:06 [PATCH 0/2] vgic emulation and GICD_ITARGETSR Stefano Stabellini
2014-05-25 18:06 ` [PATCH 1/2] xen/arm: add a warning if the guest asks for SPI delivery to vcpu != 0 Stefano Stabellini
2014-05-25 19:01 ` Julien Grall
2014-05-27 16:24 ` Stefano Stabellini
2014-05-25 18:06 ` [PATCH 2/2] xen/arm: observe itarget setting in vgic_enable_irqs and vgic_disable_irqs Stefano Stabellini
2014-05-27 16:54 ` Julien Grall
2014-05-27 17:02 ` Stefano Stabellini
2014-05-27 17:09 ` Julien Grall
2014-05-27 17:10 ` Julien Grall
2014-06-03 14:24 ` Stefano Stabellini
2014-05-28 13:38 ` Ian Campbell
2014-06-03 14:03 ` Stefano Stabellini
2014-05-28 13:33 ` [PATCH 0/2] vgic emulation and GICD_ITARGETSR Ian Campbell
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).