[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] Re: [Xen-devel] [PATCH v9 12/28] ARM: vGIC: advertise LPI support
On Thu, 25 May 2017, Andre Przywara wrote: > Hi, > > On 23/05/17 18:47, Stefano Stabellini wrote: > > On Tue, 23 May 2017, Julien Grall wrote: > >> Hi Stefano, > >> > >> On 22/05/17 23:19, Stefano Stabellini wrote: > >>> On Tue, 16 May 2017, Julien Grall wrote: > >>>>> @@ -436,8 +473,26 @@ static int __vgic_v3_rdistr_rd_mmio_write(struct > >>>>> vcpu > >>>>> *v, mmio_info_t *info, > >>>>> switch ( gicr_reg ) > >>>>> { > >>>>> case VREG32(GICR_CTLR): > >>>>> - /* LPI's not implemented */ > >>>>> - goto write_ignore_32; > >>>>> + { > >>>>> + unsigned long flags; > >>>>> + > >>>>> + if ( !v->domain->arch.vgic.has_its ) > >>>>> + goto write_ignore_32; > >>>>> + if ( dabt.size != DABT_WORD ) goto bad_width; > >>>>> + > >>>>> + vgic_lock(v); /* protects rdists_enabled */ > >>>> > >>>> Getting back to the locking. I don't see any place where we get the > >>>> domain > >>>> vgic lock before vCPU vgic lock. So this raises the question why this > >>>> ordering > >>>> and not moving this lock into vgic_vcpu_enable_lpis. > >>>> > >>>> At least this require documentation in the code and explanation in the > >>>> commit > >>>> message. > >>> > >>> It doesn't look like we need to take the v->arch.vgic.lock here. What is > >>> it protecting? > >> > >> The name of the function is a bit confusion. It does not take the vCPU vgic > >> lock but the domain vgic lock. > >> > >> I believe the vcpu is passed to avoid have v->domain in most of the > >> callers. > >> But we should probably rename the function. > >> > >> In this case it protects vgic_vcpu_enable_lpis because you can configure > >> the > >> number of LPIs per re-distributor but this is a domain wide value. I know > >> the > >> spec is confusing on this. > > > > The quoting here is very unhelpful. In Andre's patch: > > > > @@ -436,8 +473,26 @@ static int __vgic_v3_rdistr_rd_mmio_write(struct vcpu > > *v, mmio_info_t *info, > > switch ( gicr_reg ) > > { > > case VREG32(GICR_CTLR): > > - /* LPI's not implemented */ > > - goto write_ignore_32; > > + { > > + unsigned long flags; > > + > > + if ( !v->domain->arch.vgic.has_its ) > > + goto write_ignore_32; > > + if ( dabt.size != DABT_WORD ) goto bad_width; > > + > > + vgic_lock(v); /* protects rdists_enabled */ > > + spin_lock_irqsave(&v->arch.vgic.lock, flags); > > + > > + /* LPIs can only be enabled once, but never disabled again. */ > > + if ( (r & GICR_CTLR_ENABLE_LPIS) && > > + !(v->arch.vgic.flags & VGIC_V3_LPIS_ENABLED) ) > > + vgic_vcpu_enable_lpis(v); > > + > > + spin_unlock_irqrestore(&v->arch.vgic.lock, flags); > > + vgic_unlock(v); > > + > > + return 1; > > + } > > > > My question is: do we need to take both vgic_lock and v->arch.vgic.lock? > > The domain lock (taken by vgic_lock()) protects rdists_enabled. This > variable stores whether at least one redistributor has LPIs enabled. In > this case the property table gets into use and since the table is shared > across all redistributors, we must not change it anymore, even on > another redistributor which has its LPIs still disabled. > So while this looks like this is a per-redistributor (=per-VCPU) > property, it is actually per domain, hence this lock. > The VGIC VCPU lock is then used to naturally protect the enable bit > against multiple VCPUs accessing this register simultaneously - the > redists are MMIO mapped, but not banked, so this is possible. > > Does that make sense? If the VGIC VCPU lock is only used to protect VGIC_V3_LPIS_ENABLED, couldn't we just read/write the bit atomically? It's just a bit after all, it doesn't need a lock. _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx https://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |