linuxppc-dev.lists.ozlabs.org archive mirror
 help / color / mirror / Atom feed
From: Alexey Kardashevskiy <aik@ozlabs.ru>
To: linuxppc-dev@lists.ozlabs.org
Cc: Alexey Kardashevskiy <aik@ozlabs.ru>,
	Michael Ellerman <michael@ellerman.id.au>,
	Paul Mackerras <paulus@samba.org>,
	Gavin Shan <gwshan@linux.vnet.ibm.com>
Subject: [PATCH v4 12/16] powerpc/pseries/lpar: Enable VFIO
Date: Wed, 30 Jul 2014 19:31:31 +1000	[thread overview]
Message-ID: <1406712695-9491-13-git-send-email-aik@ozlabs.ru> (raw)
In-Reply-To: <1406712695-9491-1-git-send-email-aik@ozlabs.ru>

The previous patch introduced iommu_table_ops::set_and_get() callback
which effectively disabled VFIO on pseries. This implements set_and_get()
for pseries/lpar so VFIO can work under pHyp again.

Since set_and_get() callback must return old TCE, it has to do H_GET_TCE
for every TCE being replaced, therefore VFIO's performance under pHyp
is expected to be slow.

Signed-off-by: Alexey Kardashevskiy <aik@ozlabs.ru>
---
 arch/powerpc/platforms/pseries/iommu.c | 25 +++++++++++++++++++++++--
 1 file changed, 23 insertions(+), 2 deletions(-)

diff --git a/arch/powerpc/platforms/pseries/iommu.c b/arch/powerpc/platforms/pseries/iommu.c
index 793f002..d3cded1 100644
--- a/arch/powerpc/platforms/pseries/iommu.c
+++ b/arch/powerpc/platforms/pseries/iommu.c
@@ -138,13 +138,14 @@ static void tce_freemulti_pSeriesLP(struct iommu_table*, long, long);
 
 static int tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum,
 				long npages, unsigned long uaddr,
+				unsigned long *old_tces,
 				enum dma_data_direction direction,
 				struct dma_attrs *attrs)
 {
 	u64 rc = 0;
 	u64 proto_tce, tce;
 	u64 rpn;
-	int ret = 0;
+	int ret = 0, i = 0;
 	long tcenum_start = tcenum, npages_start = npages;
 
 	rpn = __pa(uaddr) >> TCE_SHIFT;
@@ -154,6 +155,9 @@ static int tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum,
 
 	while (npages--) {
 		tce = proto_tce | (rpn & TCE_RPN_MASK) << TCE_RPN_SHIFT;
+		if (old_tces)
+			plpar_tce_get((u64)tbl->it_index, (u64)tcenum << 12,
+					&old_tces[i++]);
 		rc = plpar_tce_put((u64)tbl->it_index, (u64)tcenum << 12, tce);
 
 		if (unlikely(rc == H_NOT_ENOUGH_RESOURCES)) {
@@ -179,8 +183,9 @@ static int tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum,
 
 static DEFINE_PER_CPU(__be64 *, tce_page);
 
-static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
+static int tce_set_and_get_pSeriesLP(struct iommu_table *tbl, long tcenum,
 				     long npages, unsigned long uaddr,
+				     unsigned long *old_tces,
 				     enum dma_data_direction direction,
 				     struct dma_attrs *attrs)
 {
@@ -195,6 +200,7 @@ static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
 
 	if ((npages == 1) || !firmware_has_feature(FW_FEATURE_MULTITCE)) {
 		return tce_build_pSeriesLP(tbl, tcenum, npages, uaddr,
+					   old_tces,
 		                           direction, attrs);
 	}
 
@@ -211,6 +217,7 @@ static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
 		if (!tcep) {
 			local_irq_restore(flags);
 			return tce_build_pSeriesLP(tbl, tcenum, npages, uaddr,
+					    old_tces,
 					    direction, attrs);
 		}
 		__get_cpu_var(tce_page) = tcep;
@@ -232,6 +239,10 @@ static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
 		for (l = 0; l < limit; l++) {
 			tcep[l] = cpu_to_be64(proto_tce | (rpn & TCE_RPN_MASK) << TCE_RPN_SHIFT);
 			rpn++;
+			if (old_tces)
+				plpar_tce_get((u64)tbl->it_index,
+						(u64)(tcenum + l) << 12,
+						&old_tces[tcenum + l]);
 		}
 
 		rc = plpar_tce_put_indirect((u64)tbl->it_index,
@@ -262,6 +273,15 @@ static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
 	return ret;
 }
 
+static int tce_buildmulti_pSeriesLP(struct iommu_table *tbl, long tcenum,
+				     long npages, unsigned long uaddr,
+				     enum dma_data_direction direction,
+				     struct dma_attrs *attrs)
+{
+	return tce_set_and_get_pSeriesLP(tbl, tcenum, npages, uaddr, NULL,
+			direction, attrs);
+}
+
 static void tce_free_pSeriesLP(struct iommu_table *tbl, long tcenum, long npages)
 {
 	u64 rc;
@@ -637,6 +657,7 @@ static void pci_dma_bus_setup_pSeries(struct pci_bus *bus)
 
 struct iommu_table_ops iommu_table_lpar_multi_ops = {
 	.set = tce_buildmulti_pSeriesLP,
+	.set_and_get = tce_set_and_get_pSeriesLP,
 	.clear = tce_freemulti_pSeriesLP,
 	.get = tce_get_pSeriesLP
 };
-- 
2.0.0

  parent reply	other threads:[~2014-07-30  9:31 UTC|newest]

Thread overview: 22+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-07-30  9:31 [PATCH v4 00/16] powernv: vfio: Add Dynamic DMA windows (DDW) Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 01/16] rcu: Define notrace version of list_for_each_entry_rcu and list_entry_rcu Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 02/16] KVM: PPC: Use RCU for arch.spapr_tce_tables Alexey Kardashevskiy
2014-08-21  5:25   ` Paul Mackerras
2014-07-30  9:31 ` [PATCH v4 03/16] mm: Add helpers for locked_vm Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 04/16] KVM: PPC: Account TCE-containing pages in locked_vm Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 05/16] powerpc/iommu: Fix comments with it_page_shift Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 06/16] powerpc/powernv: Make invalidate() a callback Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 07/16] powerpc/spapr: vfio: Implement spapr_tce_iommu_ops Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 08/16] powerpc/powernv: Convert/move set_bypass() callback to take_ownership() Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 09/16] powerpc/iommu: Fix IOMMU ownership control functions Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 10/16] powerpc: Move tce_xxx callbacks from ppc_md to iommu_table Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 11/16] powerpc/powernv: Release replaced TCE Alexey Kardashevskiy
2014-08-06  6:25   ` Benjamin Herrenschmidt
2014-08-06  6:27   ` Benjamin Herrenschmidt
2014-08-06  6:27   ` Benjamin Herrenschmidt
2014-07-30  9:31 ` Alexey Kardashevskiy [this message]
2014-07-30  9:31 ` [PATCH v4 13/16] powerpc/powernv: Implement Dynamic DMA windows (DDW) for IODA Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 14/16] vfio: powerpc/spapr: Reuse locked_vm accounting helpers Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 15/16] vfio: powerpc/spapr: Use it_page_size Alexey Kardashevskiy
2014-07-30  9:31 ` [PATCH v4 16/16] vfio: powerpc/spapr: Enable Dynamic DMA windows Alexey Kardashevskiy
2014-07-30  9:36   ` Alexey Kardashevskiy

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=1406712695-9491-13-git-send-email-aik@ozlabs.ru \
    --to=aik@ozlabs.ru \
    --cc=gwshan@linux.vnet.ibm.com \
    --cc=linuxppc-dev@lists.ozlabs.org \
    --cc=michael@ellerman.id.au \
    --cc=paulus@samba.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).