From: eric.auger@redhat.com (Auger Eric)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH] KVM: arm64: ITS: move ITS registration into first VCPU run
Date: Thu, 4 Aug 2016 12:11:02 +0200 [thread overview]
Message-ID: <8ef91ad8-d597-bcb7-db46-2a7194f79f32@redhat.com> (raw)
In-Reply-To: <20160803145745.7556-1-andre.przywara@arm.com>
Hi Andre,
On 03/08/2016 16:57, Andre Przywara wrote:
> Currently we register ITS devices upon userland issuing the CTRL_INIT
> ioctl to mark initialization of the ITS as done.
> This deviates from the initialization sequence of the existing GIC
> devices and does not play well with the way QEMU handles things.
> To be more in line with what we are used to, register the ITS(es) just
> before the first VCPU is about to run, so in the map_resources() call.
> This involves iterating through the list of KVM devices and handle each
> ITS that we find.
>
> Signed-off-by: Andre Przywara <andre.przywara@arm.com>
> ---
> Hi,
>
> this is based upon next-20160728 plus Christoffer's kvm_device locking
> fix from today. Please let me know what tree I should base upon and I
> will rebase.
> Eric, Christoffer: does that do what you expect? Can QEMU live with that?
>
> Cheers,
> Andre.
>
> virt/kvm/arm/vgic/vgic-its.c | 56 ++++++++++++++++++++++++++++++++++++--------
> virt/kvm/arm/vgic/vgic-v3.c | 6 +++++
> virt/kvm/arm/vgic/vgic.h | 6 +++++
> 3 files changed, 58 insertions(+), 10 deletions(-)
>
> diff --git a/virt/kvm/arm/vgic/vgic-its.c b/virt/kvm/arm/vgic/vgic-its.c
> index 07411cf..e677a60 100644
> --- a/virt/kvm/arm/vgic/vgic-its.c
> +++ b/virt/kvm/arm/vgic/vgic-its.c
> @@ -1288,13 +1288,13 @@ void vgic_enable_lpis(struct kvm_vcpu *vcpu)
> its_sync_lpi_pending_table(vcpu);
> }
>
> -static int vgic_its_init_its(struct kvm *kvm, struct vgic_its *its)
> +static int vgic_register_its_iodev(struct kvm *kvm, struct vgic_its *its)
> {
> struct vgic_io_device *iodev = &its->iodev;
> int ret;
>
> - if (its->initialized)
> - return 0;
> + if (!its->initialized)
> + return -EBUSY;
>
> if (IS_VGIC_ADDR_UNDEF(its->vgic_its_base))
> return -ENXIO;
> @@ -1311,9 +1311,6 @@ static int vgic_its_init_its(struct kvm *kvm, struct vgic_its *its)
> KVM_VGIC_V3_ITS_SIZE, &iodev->dev);
> mutex_unlock(&kvm->slots_lock);
>
> - if (!ret)
> - its->initialized = true;
> -
> return ret;
> }
>
> @@ -1435,9 +1432,6 @@ static int vgic_its_set_attr(struct kvm_device *dev,
> if (type != KVM_VGIC_ITS_ADDR_TYPE)
> return -ENODEV;
>
> - if (its->initialized)
> - return -EBUSY;
> -
> if (copy_from_user(&addr, uaddr, sizeof(addr)))
> return -EFAULT;
>
> @@ -1453,7 +1447,9 @@ static int vgic_its_set_attr(struct kvm_device *dev,
> case KVM_DEV_ARM_VGIC_GRP_CTRL:
> switch (attr->attr) {
> case KVM_DEV_ARM_VGIC_CTRL_INIT:
> - return vgic_its_init_its(dev->kvm, its);
> + its->initialized = true;
> +
> + return 0;
> }
> break;
> }
> @@ -1498,3 +1494,43 @@ int kvm_vgic_register_its_device(void)
> return kvm_register_device_ops(&kvm_arm_vgic_its_ops,
> KVM_DEV_TYPE_ARM_VGIC_ITS);
> }
> +
> +/*
> + * Registers all ITSes with the kvm_io_bus framework.
> + * To follow the existing VGIC initialization sequence, this has to be
> + * done as late as possible, just before the first VCPU runs.
> + */
> +int vgic_register_its_iodevs(struct kvm *kvm)
> +{
> + struct kvm_device *dev;
> + int ret = 0;
> +
> + mutex_lock(&kvm->devices_lock);
> +
> + list_for_each_entry(dev, &kvm->devices, vm_node) {
> + if (dev->ops != &kvm_arm_vgic_its_ops)
> + continue;
> +
> + ret = vgic_register_its_iodev(kvm, dev->private);
> + if (ret)
> + break;
> + }
> +
> + if (ret) {
> + /* Iterate backwards to roll back previous registrations. */
> + for (dev = list_prev_entry(dev, vm_node);
> + &dev->vm_node != &kvm->devices;
> + dev = list_prev_entry(dev, vm_node)) {
> + struct vgic_its *its = dev->private;
> +
> + if (dev->ops != &kvm_arm_vgic_its_ops)
> + continue;
> +
> + kvm_io_bus_unregister_dev(kvm, KVM_MMIO_BUS,
> + &its->iodev.dev);
> + }
> + }
> +
> + mutex_unlock(&kvm->devices_lock);
> + return ret;
> +}
> diff --git a/virt/kvm/arm/vgic/vgic-v3.c b/virt/kvm/arm/vgic/vgic-v3.c
> index 0506543..f0d9b2b 100644
> --- a/virt/kvm/arm/vgic/vgic-v3.c
> +++ b/virt/kvm/arm/vgic/vgic-v3.c
> @@ -289,6 +289,12 @@ int vgic_v3_map_resources(struct kvm *kvm)
> goto out;
> }
>
don't you need to check vgic_has_its() first
Thanks
Eric
> + ret = vgic_register_its_iodevs(kvm);
> + if (ret) {
> + kvm_err("Unable to register VGIC ITS MMIO regions\n");
> + goto out;
> + }
> +
> dist->ready = true;
>
> out:
> diff --git a/virt/kvm/arm/vgic/vgic.h b/virt/kvm/arm/vgic/vgic.h
> index 1d8e21d..6c4625c 100644
> --- a/virt/kvm/arm/vgic/vgic.h
> +++ b/virt/kvm/arm/vgic/vgic.h
> @@ -84,6 +84,7 @@ void vgic_v3_enable(struct kvm_vcpu *vcpu);
> int vgic_v3_probe(const struct gic_kvm_info *info);
> int vgic_v3_map_resources(struct kvm *kvm);
> int vgic_register_redist_iodevs(struct kvm *kvm, gpa_t dist_base_address);
> +int vgic_register_its_iodevs(struct kvm *kvm);
> bool vgic_has_its(struct kvm *kvm);
> int kvm_vgic_register_its_device(void);
> void vgic_enable_lpis(struct kvm_vcpu *vcpu);
> @@ -140,6 +141,11 @@ static inline int vgic_register_redist_iodevs(struct kvm *kvm,
> return -ENODEV;
> }
>
> +static inline int vgic_register_its_iodevs(struct kvm *kvm)
> +{
> + return -ENODEV;
> +}
> +
> static inline bool vgic_has_its(struct kvm *kvm)
> {
> return false;
>
next prev parent reply other threads:[~2016-08-04 10:11 UTC|newest]
Thread overview: 13+ messages / expand[flat|nested] mbox.gz Atom feed top
2016-08-03 14:57 [PATCH] KVM: arm64: ITS: move ITS registration into first VCPU run Andre Przywara
2016-08-03 17:11 ` Christoffer Dall
2016-08-03 17:18 ` Andre Przywara
2016-08-03 17:48 ` Auger Eric
2016-08-03 17:56 ` Auger Eric
2016-08-03 18:11 ` Auger Eric
2016-08-03 17:56 ` Christoffer Dall
2016-08-03 17:48 ` Christoffer Dall
2016-08-03 17:13 ` Christoffer Dall
2016-08-03 18:15 ` kbuild test robot
2016-08-04 10:11 ` Auger Eric [this message]
2016-08-04 10:17 ` Andre Przywara
2016-08-04 10:26 ` Auger Eric
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=8ef91ad8-d597-bcb7-db46-2a7194f79f32@redhat.com \
--to=eric.auger@redhat.com \
--cc=linux-arm-kernel@lists.infradead.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