Andy,
to make it obvious which version is the latest, here is a branch
The following changes since commit 6a13feb9c82803e2b815eca72fa7a9f5561d7861:
Linux 4.3 (2015-11-01 16:05:25 -0800)
are available in the git repository at:
git://git.kernel.org/pub/scm/linux/kernel/git/borntraeger/linux.git dma
for you to fetch changes up to fc7f9754db6ce0c12281da4055281f731d36bdee:
s390/dma: Allow per device dma ops (2015-11-05 21:02:40 +0100)
----------------------------------------------------------------
Christian Borntraeger (3):
dma: Provide simple noop dma ops
alpha/dma: use common noop dma ops
s390/dma: Allow per device dma ops
arch/alpha/kernel/pci-noop.c | 46 ++---------------------
arch/s390/Kconfig | 7 +---
arch/s390/include/asm/device.h | 6 ++-
arch/s390/include/asm/dma-mapping.h | 6 ++-
arch/s390/pci/pci.c | 1 +
arch/s390/pci/pci_dma.c | 4 +-
include/linux/dma-mapping.h | 2 +
lib/Makefile | 1 +
lib/dma-noop.c | 75 +++++++++++++++++++++++++++++++++++++
9 files changed, 96 insertions(+), 52 deletions(-)
create mode 100644 lib/dma-noop.c
Christian Borntraeger
2015-Nov-05 20:08 UTC
[GIT PULL v4 1/3] dma: Provide simple noop dma ops
We are going to require dma_ops for several common drivers, even for
systems that do have an identity mapping. Lets provide some minimal
no-op dma_ops that can be used for that purpose.
Signed-off-by: Christian Borntraeger <borntraeger at de.ibm.com>
Reviewed-by: Joerg Roedel <jroedel at suse.de>
---
include/linux/dma-mapping.h | 2 ++
lib/Makefile | 1 +
lib/dma-noop.c | 75 +++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 78 insertions(+)
create mode 100644 lib/dma-noop.c
diff --git a/include/linux/dma-mapping.h b/include/linux/dma-mapping.h
index ac07ff0..7912f54 100644
--- a/include/linux/dma-mapping.h
+++ b/include/linux/dma-mapping.h
@@ -66,6 +66,8 @@ struct dma_map_ops {
int is_phys;
};
+extern struct dma_map_ops dma_noop_ops;
+
#define DMA_BIT_MASK(n) (((n) == 64) ? ~0ULL : ((1ULL<<(n))-1))
#define DMA_MASK_NONE 0x0ULL
diff --git a/lib/Makefile b/lib/Makefile
index 13a7c6a..92d6135 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -18,6 +18,7 @@ lib-y := ctype.o string.o vsprintf.o cmdline.o \
obj-$(CONFIG_ARCH_HAS_DEBUG_STRICT_USER_COPY_CHECKS) += usercopy.o
lib-$(CONFIG_MMU) += ioremap.o
lib-$(CONFIG_SMP) += cpumask.o
+lib-$(CONFIG_HAS_DMA) += dma-noop.o
lib-y += kobject.o klist.o
obj-y += lockref.o
diff --git a/lib/dma-noop.c b/lib/dma-noop.c
new file mode 100644
index 0000000..7214564
--- /dev/null
+++ b/lib/dma-noop.c
@@ -0,0 +1,75 @@
+/*
+ * lib/dma-noop.c
+ *
+ * Simple DMA noop-ops that map 1:1 with memory
+ */
+#include <linux/export.h>
+#include <linux/mm.h>
+#include <linux/dma-mapping.h>
+#include <linux/scatterlist.h>
+
+static void *dma_noop_alloc(struct device *dev, size_t size,
+ dma_addr_t *dma_handle, gfp_t gfp,
+ struct dma_attrs *attrs)
+{
+ void *ret;
+
+ ret = (void *)__get_free_pages(gfp, get_order(size));
+ if (ret)
+ *dma_handle = virt_to_phys(ret);
+ return ret;
+}
+
+static void dma_noop_free(struct device *dev, size_t size,
+ void *cpu_addr, dma_addr_t dma_addr,
+ struct dma_attrs *attrs)
+{
+ free_pages((unsigned long)cpu_addr, get_order(size));
+}
+
+static dma_addr_t dma_noop_map_page(struct device *dev, struct page *page,
+ unsigned long offset, size_t size,
+ enum dma_data_direction dir,
+ struct dma_attrs *attrs)
+{
+ return page_to_phys(page) + offset;
+}
+
+static int dma_noop_map_sg(struct device *dev, struct scatterlist *sgl, int
nents,
+ enum dma_data_direction dir, struct dma_attrs *attrs)
+{
+ int i;
+ struct scatterlist *sg;
+
+ for_each_sg(sgl, sg, nents, i) {
+ void *va;
+
+ BUG_ON(!sg_page(sg));
+ va = sg_virt(sg);
+ sg_dma_address(sg) = (dma_addr_t)virt_to_phys(va);
+ sg_dma_len(sg) = sg->length;
+ }
+
+ return nents;
+}
+
+static int dma_noop_mapping_error(struct device *dev, dma_addr_t dma_addr)
+{
+ return 0;
+}
+
+static int dma_noop_supported(struct device *dev, u64 mask)
+{
+ return 1;
+}
+
+struct dma_map_ops dma_noop_ops = {
+ .alloc = dma_noop_alloc,
+ .free = dma_noop_free,
+ .map_page = dma_noop_map_page,
+ .map_sg = dma_noop_map_sg,
+ .mapping_error = dma_noop_mapping_error,
+ .dma_supported = dma_noop_supported,
+};
+
+EXPORT_SYMBOL(dma_noop_ops);
--
2.4.3
Christian Borntraeger
2015-Nov-05 20:08 UTC
[GIT PULL v4 2/3] alpha/dma: use common noop dma ops
Some of the alpha pci noop dma ops are identical to the common ones.
Use them.
Signed-off-by: Christian Borntraeger <borntraeger at de.ibm.com>
Reviewed-by: Joerg Roedel <jroedel at suse.de>
---
arch/alpha/kernel/pci-noop.c | 46 ++++----------------------------------------
1 file changed, 4 insertions(+), 42 deletions(-)
diff --git a/arch/alpha/kernel/pci-noop.c b/arch/alpha/kernel/pci-noop.c
index 2b1f4a1..8e735b5e 100644
--- a/arch/alpha/kernel/pci-noop.c
+++ b/arch/alpha/kernel/pci-noop.c
@@ -123,44 +123,6 @@ static void *alpha_noop_alloc_coherent(struct device *dev,
size_t size,
return ret;
}
-static void alpha_noop_free_coherent(struct device *dev, size_t size,
- void *cpu_addr, dma_addr_t dma_addr,
- struct dma_attrs *attrs)
-{
- free_pages((unsigned long)cpu_addr, get_order(size));
-}
-
-static dma_addr_t alpha_noop_map_page(struct device *dev, struct page *page,
- unsigned long offset, size_t size,
- enum dma_data_direction dir,
- struct dma_attrs *attrs)
-{
- return page_to_pa(page) + offset;
-}
-
-static int alpha_noop_map_sg(struct device *dev, struct scatterlist *sgl, int
nents,
- enum dma_data_direction dir, struct dma_attrs *attrs)
-{
- int i;
- struct scatterlist *sg;
-
- for_each_sg(sgl, sg, nents, i) {
- void *va;
-
- BUG_ON(!sg_page(sg));
- va = sg_virt(sg);
- sg_dma_address(sg) = (dma_addr_t)virt_to_phys(va);
- sg_dma_len(sg) = sg->length;
- }
-
- return nents;
-}
-
-static int alpha_noop_mapping_error(struct device *dev, dma_addr_t dma_addr)
-{
- return 0;
-}
-
static int alpha_noop_supported(struct device *dev, u64 mask)
{
return mask < 0x00ffffffUL ? 0 : 1;
@@ -168,10 +130,10 @@ static int alpha_noop_supported(struct device *dev, u64
mask)
struct dma_map_ops alpha_noop_ops = {
.alloc = alpha_noop_alloc_coherent,
- .free = alpha_noop_free_coherent,
- .map_page = alpha_noop_map_page,
- .map_sg = alpha_noop_map_sg,
- .mapping_error = alpha_noop_mapping_error,
+ .free = dma_noop_free_coherent,
+ .map_page = dma_noop_map_page,
+ .map_sg = dma_noop_map_sg,
+ .mapping_error = dma_noop_mapping_error,
.dma_supported = alpha_noop_supported,
};
--
2.4.3
Christian Borntraeger
2015-Nov-05 20:08 UTC
[GIT PULL v4 3/3] s390/dma: Allow per device dma ops
As virtio-ccw will have dma ops, we can no longer default to the
zPCI ones. Make use of dev_archdata to keep the dma_ops per device.
The pci devices now use that to override the default, and the
default is changed to use the noop ops for everything that does not
specify a device specific one.
To compile without PCI support we will enable HAS_DMA all the time,
via the default config in lib/Kconfig.
Signed-off-by: Christian Borntraeger <borntraeger at de.ibm.com>
Reviewed-by: Joerg Roedel <jroedel at suse.de>
Acked-by: Sebastian Ott <sebott at linux.vnet.ibm.com>
---
arch/s390/Kconfig | 7 ++-----
arch/s390/include/asm/device.h | 6 +++++-
arch/s390/include/asm/dma-mapping.h | 6 ++++--
arch/s390/pci/pci.c | 1 +
arch/s390/pci/pci_dma.c | 4 ++--
5 files changed, 14 insertions(+), 10 deletions(-)
diff --git a/arch/s390/Kconfig b/arch/s390/Kconfig
index 1d57000..e2a885b 100644
--- a/arch/s390/Kconfig
+++ b/arch/s390/Kconfig
@@ -124,6 +124,8 @@ config S390
select HAVE_CMPXCHG_DOUBLE
select HAVE_CMPXCHG_LOCAL
select HAVE_DEBUG_KMEMLEAK
+ select HAVE_DMA_ATTRS
+ select HAVE_DMA_API_DEBUG
select HAVE_DYNAMIC_FTRACE
select HAVE_DYNAMIC_FTRACE_WITH_REGS
select HAVE_FTRACE_MCOUNT_RECORD
@@ -580,7 +582,6 @@ config QDIO
menuconfig PCI
bool "PCI support"
- select HAVE_DMA_ATTRS
select PCI_MSI
help
Enable PCI support.
@@ -620,10 +621,6 @@ config HAS_IOMEM
config IOMMU_HELPER
def_bool PCI
-config HAS_DMA
- def_bool PCI
- select HAVE_DMA_API_DEBUG
-
config NEED_SG_DMA_LENGTH
def_bool PCI
diff --git a/arch/s390/include/asm/device.h b/arch/s390/include/asm/device.h
index d8f9872..4a9f35e 100644
--- a/arch/s390/include/asm/device.h
+++ b/arch/s390/include/asm/device.h
@@ -3,5 +3,9 @@
*
* This file is released under the GPLv2
*/
-#include <asm-generic/device.h>
+struct dev_archdata {
+ struct dma_map_ops *dma_ops;
+};
+struct pdev_archdata {
+};
diff --git a/arch/s390/include/asm/dma-mapping.h
b/arch/s390/include/asm/dma-mapping.h
index b3fd54d..cb05f5c 100644
--- a/arch/s390/include/asm/dma-mapping.h
+++ b/arch/s390/include/asm/dma-mapping.h
@@ -11,11 +11,13 @@
#define DMA_ERROR_CODE (~(dma_addr_t) 0x0)
-extern struct dma_map_ops s390_dma_ops;
+extern struct dma_map_ops s390_pci_dma_ops;
static inline struct dma_map_ops *get_dma_ops(struct device *dev)
{
- return &s390_dma_ops;
+ if (dev && dev->archdata.dma_ops)
+ return dev->archdata.dma_ops;
+ return &dma_noop_ops;
}
static inline void dma_cache_sync(struct device *dev, void *vaddr, size_t size,
diff --git a/arch/s390/pci/pci.c b/arch/s390/pci/pci.c
index 7ef12a3..fa41605 100644
--- a/arch/s390/pci/pci.c
+++ b/arch/s390/pci/pci.c
@@ -649,6 +649,7 @@ int pcibios_add_device(struct pci_dev *pdev)
zdev->pdev = pdev;
pdev->dev.groups = zpci_attr_groups;
+ pdev->dev.archdata.dma_ops = &s390_pci_dma_ops;
zpci_map_resources(pdev);
for (i = 0; i < PCI_BAR_COUNT; i++) {
diff --git a/arch/s390/pci/pci_dma.c b/arch/s390/pci/pci_dma.c
index 37505b8..ea39c3f 100644
--- a/arch/s390/pci/pci_dma.c
+++ b/arch/s390/pci/pci_dma.c
@@ -495,7 +495,7 @@ static int __init dma_debug_do_init(void)
}
fs_initcall(dma_debug_do_init);
-struct dma_map_ops s390_dma_ops = {
+struct dma_map_ops s390_pci_dma_ops = {
.alloc = s390_dma_alloc,
.free = s390_dma_free,
.map_sg = s390_dma_map_sg,
@@ -506,7 +506,7 @@ struct dma_map_ops s390_dma_ops = {
.is_phys = 0,
/* dma_supported is unconditionally true without a callback */
};
-EXPORT_SYMBOL_GPL(s390_dma_ops);
+EXPORT_SYMBOL_GPL(s390_pci_dma_ops);
static int __init s390_iommu_setup(char *str)
{
--
2.4.3
On Thu, Nov 5, 2015 at 12:08 PM, Christian Borntraeger <borntraeger at de.ibm.com> wrote:> Andy, > > to make it obvious which version is the latest, here is a branch > > The following changes since commit 6a13feb9c82803e2b815eca72fa7a9f5561d7861: > > Linux 4.3 (2015-11-01 16:05:25 -0800) > > are available in the git repository at: > > git://git.kernel.org/pub/scm/linux/kernel/git/borntraeger/linux.git dma > > for you to fetch changes up to fc7f9754db6ce0c12281da4055281f731d36bdee: > > s390/dma: Allow per device dma ops (2015-11-05 21:02:40 +0100)Pulled, thanks. --Andy
On Thu, 5 Nov 2015 21:08:56 +0100 Christian Borntraeger <borntraeger at de.ibm.com> wrote:> As virtio-ccw will have dma ops, we can no longer default to the > zPCI ones. Make use of dev_archdata to keep the dma_ops per device. > The pci devices now use that to override the default, and the > default is changed to use the noop ops for everything that does not > specify a device specific one. > To compile without PCI support we will enable HAS_DMA all the time, > via the default config in lib/Kconfig. > > Signed-off-by: Christian Borntraeger <borntraeger at de.ibm.com> > Reviewed-by: Joerg Roedel <jroedel at suse.de> > Acked-by: Sebastian Ott <sebott at linux.vnet.ibm.com> > --- > arch/s390/Kconfig | 7 ++----- > arch/s390/include/asm/device.h | 6 +++++- > arch/s390/include/asm/dma-mapping.h | 6 ++++-- > arch/s390/pci/pci.c | 1 + > arch/s390/pci/pci_dma.c | 4 ++-- > 5 files changed, 14 insertions(+), 10 deletions(-)Reviewed-by: Cornelia Huck <cornelia.huck at de.ibm.com>