From patchwork Mon Mar 27 09:31:10 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Eric Auger X-Patchwork-Id: 9646313 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 00A13602BF for ; Mon, 27 Mar 2017 10:09:31 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id DFD182833B for ; Mon, 27 Mar 2017 10:09:30 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id D4CCE2836D; Mon, 27 Mar 2017 10:09:30 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-1.9 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID autolearn=unavailable version=3.3.1 Received: from bombadil.infradead.org (bombadil.infradead.org [65.50.211.133]) (using TLSv1.2 with cipher AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 8048D2833B for ; Mon, 27 Mar 2017 10:09:30 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20170209; h=Sender: Content-Transfer-Encoding:Content-Type:MIME-Version:Cc:List-Subscribe: List-Help:List-Post:List-Archive:List-Unsubscribe:List-Id:References: In-Reply-To:Message-Id:Date:Subject:To:From:Reply-To:Content-ID: Content-Description:Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc :Resent-Message-ID:List-Owner; bh=IyB6WooSTv7Au6CKJN8jWu/V+HxHpvM8ZB9Xvzg7/g8=; b=jWwl6tzW+hbAClQOLlgvy3nnNp aXF6u++vMobE1IeejLQzHnY+FYoUxHIez1DljLIiSwf1uWpi5mKTIpbBlHRYdJcrmxPPm5nAlWpHU PGzmzrvYtOlHtHrf7SYX8KLOAtxCFoJx6ba2LIe6vzKgn6Ar4csdLnH3CI5aNzJalcjoMTZEFJuJw KSDmSfRmxoeN7aLIrYIijKKQrtIxsY7Du7BxvOQ45oeWnRrL+60rTNI9ZFzCWrh3WsamnijTAnG0j heznoupW9Te3g7kok0RPwpbpzfMnyCjemUIFLMH/v5qr+sUw+fZrXvA+lMfMcfQmtUPUe8HbRRIam KpH5YudA==; Received: from localhost ([127.0.0.1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.87 #1 (Red Hat Linux)) id 1csRaa-0008H4-TG; Mon, 27 Mar 2017 10:09:28 +0000 Received: from merlin.infradead.org ([2001:4978:20e::2]) by bombadil.infradead.org with esmtps (Exim 4.87 #1 (Red Hat Linux)) id 1csRVo-0002YK-1Y for linux-arm-kernel@bombadil.infradead.org; Mon, 27 Mar 2017 10:04:32 +0000 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=infradead.org; s=merlin.20170209; h=References:In-Reply-To:Message-Id:Date: Subject:Cc:To:From:Sender:Reply-To:MIME-Version:Content-Type: Content-Transfer-Encoding:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Id: List-Help:List-Unsubscribe:List-Subscribe:List-Post:List-Owner:List-Archive; bh=lvxPRZcN7OnWUqOcJFmfXVGdNUJ7m+9PT5HJ8HBzlOc=; b=puLr5Yw7a5zMJxZt3O8F3DUnJ Onr7MRq/sL9ghYFS+dHY3dRXkW/5q5hUUkl7Bsta/qyViNZsGkKMS5wdV0rj5a4BFcg91l2LYvkoW ehKcDnX5lS7LivGu2HEHvWffx+rXKcDGTZHEAg+htA9Mo3OWJG8q+DI8spvbVWhjXNqeDy2GDfQ4P CbUdWxurqXbKzLTSWBU7KFrholdTpWwAV+hjsmv0VMurn7cobs5TMhcTFnYhDHGlnF6ReDWdzeWOI nf1u1qz2J+HeQjCv8/RwKMnZBwhAg08LTeZ6Kq2cUp+b1050meicVfjxKm+1GVcEogMsd4cmoBL89 9zalDzr1A==; Received: from mx1.redhat.com ([209.132.183.28]) by merlin.infradead.org with esmtps (Exim 4.87 #1 (Red Hat Linux)) id 1csR1b-0006tH-6c for linux-arm-kernel@lists.infradead.org; Mon, 27 Mar 2017 09:33:20 +0000 Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.phx2.redhat.com [10.5.11.15]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id DB97761D15; Mon, 27 Mar 2017 09:32:59 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.3.2 mx1.redhat.com DB97761D15 Authentication-Results: ext-mx10.extmail.prod.ext.phx2.redhat.com; dmarc=none (p=none dis=none) header.from=redhat.com Authentication-Results: ext-mx10.extmail.prod.ext.phx2.redhat.com; spf=pass smtp.mailfrom=eric.auger@redhat.com DKIM-Filter: OpenDKIM Filter v2.11.0 mx1.redhat.com DB97761D15 Received: from localhost.localdomain.com (ovpn-117-27.ams2.redhat.com [10.36.117.27]) by smtp.corp.redhat.com (Postfix) with ESMTP id 452B217C46; Mon, 27 Mar 2017 09:32:56 +0000 (UTC) From: Eric Auger To: eric.auger.pro@gmail.com, eric.auger@redhat.com, marc.zyngier@arm.com, christoffer.dall@linaro.org, andre.przywara@arm.com, vijayak@caviumnetworks.com, Vijaya.Kumar@cavium.com, peter.maydell@linaro.org, linux-arm-kernel@lists.infradead.org, kvmarm@lists.cs.columbia.edu, kvm@vger.kernel.org Subject: [PATCH v4 20/22] KVM: arm64: ITS: ITT flush and restore Date: Mon, 27 Mar 2017 11:31:10 +0200 Message-Id: <1490607072-21610-21-git-send-email-eric.auger@redhat.com> In-Reply-To: <1490607072-21610-1-git-send-email-eric.auger@redhat.com> References: <1490607072-21610-1-git-send-email-eric.auger@redhat.com> X-Scanned-By: MIMEDefang 2.79 on 10.5.11.15 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.39]); Mon, 27 Mar 2017 09:33:00 +0000 (UTC) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20170327_053319_409085_1FA1E8CE X-CRM114-Status: GOOD ( 17.97 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Prasun.Kapoor@cavium.com, drjones@redhat.com, quintela@redhat.com, dgilbert@redhat.com, pbonzini@redhat.com MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+patchwork-linux-arm=patchwork.kernel.org@lists.infradead.org X-Virus-Scanned: ClamAV using ClamSMTP Introduce routines to flush and restore device ITT and their interrupt table entries (ITE). The routines will be called on device table flush and restore. They will become static in subsequent patches. Signed-off-by: Eric Auger --- v3 -> v4: - lookup_table and compute_next_eventid_offset become static in this patch - remove static along with vgic_its_flush/restore_itt to avoid compilation warnings - next field only computed with a shift (mask removed) - handle the case where the last element has not been found v2 -> v3: - add return 0 in vgic_its_restore_ite (was in subsequent patch) v2: creation --- virt/kvm/arm/vgic/vgic-its.c | 107 +++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 104 insertions(+), 3 deletions(-) diff --git a/virt/kvm/arm/vgic/vgic-its.c b/virt/kvm/arm/vgic/vgic-its.c index b907e3c..02c0694 100644 --- a/virt/kvm/arm/vgic/vgic-its.c +++ b/virt/kvm/arm/vgic/vgic-its.c @@ -1707,7 +1707,7 @@ u32 compute_next_devid_offset(struct list_head *h, struct its_device *dev) return min_t(u32, next_offset, VITS_DTE_MAX_DEVID_OFFSET); } -u32 compute_next_eventid_offset(struct list_head *h, struct its_ite *ite) +static u32 compute_next_eventid_offset(struct list_head *h, struct its_ite *ite) { struct list_head *e = &ite->ite_list; struct its_ite *next; @@ -1749,8 +1749,8 @@ typedef int (*entry_fn_t)(struct vgic_its *its, u32 id, void *addr, * * Return: < 0 on error, 1 if last element identified, 0 otherwise */ -int lookup_table(struct vgic_its *its, gpa_t base, int size, int esz, - int start_id, entry_fn_t fn, void *opaque) +static int lookup_table(struct vgic_its *its, gpa_t base, int size, int esz, + int start_id, entry_fn_t fn, void *opaque) { gpa_t gpa = base, top = base + size - 1; unsigned long len = size; @@ -1815,6 +1815,107 @@ static int vgic_its_restore_pending_tables(struct kvm *kvm) return -ENXIO; } +static int vgic_its_flush_ite(struct vgic_its *its, struct its_device *dev, + struct its_ite *ite, gpa_t gpa) +{ + struct kvm *kvm = its->dev->kvm; + u32 next_offset; + u64 val; + + next_offset = compute_next_eventid_offset(&dev->itt_head, ite); + val = ((u64)next_offset << 48) | ((u64)ite->lpi << 16) | + ite->collection->collection_id; + val = cpu_to_le64(val); + return kvm_write_guest(kvm, gpa, &val, VITS_ESZ); +} + +/** + * vgic_its_restore_ite - restore an interrupt translation entry + * @event_id: id used for indexing + * @ptr: kernel VA where the 8 byte ITE is located + * @opaque: pointer to the its_device + * @next: id offset to the next entry + */ +static int vgic_its_restore_ite(struct vgic_its *its, u32 event_id, + void *ptr, void *opaque, u32 *next) +{ + struct its_device *dev = (struct its_device *)opaque; + struct its_collection *collection; + struct kvm *kvm = its->dev->kvm; + u64 val, *p = (u64 *)ptr; + struct vgic_irq *irq; + u32 coll_id, lpi_id; + struct its_ite *ite; + int ret; + + val = *p; + *next = 1; + + val = le64_to_cpu(val); + + coll_id = val & GENMASK_ULL(15, 0); + lpi_id = (val & GENMASK_ULL(47, 16)) >> 16; + + if (!lpi_id) + return 0; + + *next = val >> 48; + + collection = find_collection(its, coll_id); + if (!collection) + return -EINVAL; + + ret = vgic_its_alloc_ite(dev, &ite, collection, + lpi_id, event_id); + if (ret) + return ret; + + irq = vgic_add_lpi(kvm, lpi_id); + if (IS_ERR(irq)) + return PTR_ERR(irq); + ite->irq = irq; + + /* restore the configuration of the LPI */ + ret = update_lpi_config(kvm, irq, NULL); + if (ret) + return ret; + + update_affinity_ite(kvm, ite); + return 0; +} + +int vgic_its_flush_itt(struct vgic_its *its, struct its_device *device) +{ + gpa_t base = device->itt_addr; + struct its_ite *ite; + int ret; + + list_for_each_entry(ite, &device->itt_head, ite_list) { + gpa_t gpa = base + ite->event_id * VITS_ESZ; + + ret = vgic_its_flush_ite(its, device, ite, gpa); + if (ret) + return ret; + } + return 0; +} + +int vgic_its_restore_itt(struct vgic_its *its, struct its_device *dev) +{ + size_t max_size = BIT_ULL(dev->nb_eventid_bits) * VITS_ESZ; + gpa_t base = dev->itt_addr; + int ret; + + ret = lookup_table(its, base, max_size, VITS_ESZ, 0, + vgic_its_restore_ite, dev); + + if (ret < 0) + return ret; + + /* if the last element has not been found we are in trouble */ + return ret ? 0 : -EINVAL; +} + /** * vgic_its_flush_device_tables - flush the device table and all ITT * into guest RAM