CC a few extra lists I missed.
Regards,
Andres
On 2017-04-25 09:36 PM, Andres Rodriguez wrote:
> When a timeout of zero is specified, the caller is only interested in
> the fence status.
>
> In the current implementation, dma_fence_default_wait will always call
> schedule_timeout() at least once for an unsignaled fence. This adds a
> significant overhead to a fence status query.
>
> Avoid this overhead by returning early if a zero timeout is specified.
>
> Signed-off-by: Andres Rodriguez <andresx7(a)gmail.com>
> ---
>
> This heavily affects the performance of the Source2 engine running on
> radv.
>
> This patch improves dota2(radv) perf on a i7-6700k+RX480 system from
> 72fps->81fps.
>
> drivers/dma-buf/dma-fence.c | 3 +++
> 1 file changed, 3 insertions(+)
>
> diff --git a/drivers/dma-buf/dma-fence.c b/drivers/dma-buf/dma-fence.c
> index 0918d3f..348e9e2 100644
> --- a/drivers/dma-buf/dma-fence.c
> +++ b/drivers/dma-buf/dma-fence.c
> @@ -380,6 +380,9 @@ dma_fence_default_wait(struct dma_fence *fence, bool intr, signed long timeout)
> if (test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, &fence->flags))
> return ret;
>
> + if (!timeout)
> + return 0;
> +
> spin_lock_irqsave(fence->lock, flags);
>
> if (intr && signal_pending(current)) {
>
Hi,
This is v4 of the series to cleanup to Ion. Greg took some of the patches
that weren't CMA related already. There was a minor bisectability problem
with the CMA APIs so this is a new version to address that. I also
addressed some minor comments on the patch to collapse header files.
Thanks,
Laura
Laura Abbott (12):
cma: Store a name in the cma structure
cma: Introduce cma_for_each_area
staging: android: ion: Use CMA APIs directly
staging: android: ion: Stop butchering the DMA address
staging: android: ion: Break the ABI in the name of forward progress
staging: android: ion: Get rid of ion_phys_addr_t
staging: android: ion: Collapse internal header files
staging: android: ion: Rework heap registration/enumeration
staging: android: ion: Drop ion_map_kernel interface
staging: android: ion: Remove ion_handle and ion_client
staging: android: ion: Set query return value
staging/android: Update Ion TODO list
arch/powerpc/kvm/book3s_hv_builtin.c | 3 +-
drivers/base/dma-contiguous.c | 5 +-
drivers/staging/android/TODO | 21 +-
drivers/staging/android/ion/Kconfig | 32 +
drivers/staging/android/ion/Makefile | 11 +-
drivers/staging/android/ion/compat_ion.c | 152 -----
drivers/staging/android/ion/compat_ion.h | 29 -
drivers/staging/android/ion/ion-ioctl.c | 55 +-
drivers/staging/android/ion/ion.c | 812 ++----------------------
drivers/staging/android/ion/ion.h | 386 ++++++++---
drivers/staging/android/ion/ion_carveout_heap.c | 21 +-
drivers/staging/android/ion/ion_chunk_heap.c | 16 +-
drivers/staging/android/ion/ion_cma_heap.c | 120 ++--
drivers/staging/android/ion/ion_heap.c | 68 --
drivers/staging/android/ion/ion_page_pool.c | 3 +-
drivers/staging/android/ion/ion_priv.h | 453 -------------
drivers/staging/android/ion/ion_system_heap.c | 39 +-
drivers/staging/android/uapi/ion.h | 36 +-
include/linux/cma.h | 6 +-
mm/cma.c | 31 +-
mm/cma.h | 1 +
mm/cma_debug.c | 2 +-
22 files changed, 524 insertions(+), 1778 deletions(-)
delete mode 100644 drivers/staging/android/ion/compat_ion.c
delete mode 100644 drivers/staging/android/ion/compat_ion.h
delete mode 100644 drivers/staging/android/ion/ion_priv.h
--
2.7.4
Hi,
This is v3 of the series to do some serious Ion cleanup in preparation for
moving out of staging. I didn't hear much on v2 so I'm going to assume
people are okay with the series as is. I know there were still some open
questions about moving away from /dev/ion but in the interest of small
steps I'd like to go ahead and merge this series assuming there are no more
major objections. More work can happen on top of this.
Changes from v2:
- Dropped the RFC tag
- Minor bisectability fixes
- Sumit's comment about CMA naming
- Updated the TODO list
Thanks,
Laura
Laura Abbott (22):
cma: Store a name in the cma structure
cma: Introduce cma_for_each_area
staging: android: ion: Remove dmap_cnt
staging: android: ion: Remove alignment from allocation field
staging: android: ion: Duplicate sg_table
staging: android: ion: Call dma_map_sg for syncing and mapping
staging: android: ion: Remove page faulting support
staging: android: ion: Remove crufty cache support
staging: android: ion: Remove custom ioctl interface
staging: android: ion: Remove import interface
staging: android: ion: Remove duplicate ION_IOC_MAP
staging: android: ion: Remove old platform support
staging: android: ion: Use CMA APIs directly
staging: android: ion: Stop butchering the DMA address
staging: android: ion: Break the ABI in the name of forward progress
staging: android: ion: Get rid of ion_phys_addr_t
staging: android: ion: Collapse internal header files
staging: android: ion: Rework heap registration/enumeration
staging: android: ion: Drop ion_map_kernel interface
staging: android: ion: Remove ion_handle and ion_client
staging: android: ion: Set query return value
staging/android: Update Ion TODO list
arch/powerpc/kvm/book3s_hv_builtin.c | 3 +-
drivers/base/dma-contiguous.c | 5 +-
drivers/staging/android/TODO | 21 +-
drivers/staging/android/ion/Kconfig | 56 +-
drivers/staging/android/ion/Makefile | 18 +-
drivers/staging/android/ion/compat_ion.c | 195 ----
drivers/staging/android/ion/compat_ion.h | 29 -
drivers/staging/android/ion/hisilicon/Kconfig | 5 -
drivers/staging/android/ion/hisilicon/Makefile | 1 -
drivers/staging/android/ion/hisilicon/hi6220_ion.c | 113 --
drivers/staging/android/ion/ion-ioctl.c | 85 +-
drivers/staging/android/ion/ion.c | 1168 +++-----------------
drivers/staging/android/ion/ion.h | 389 +++++--
drivers/staging/android/ion/ion_carveout_heap.c | 37 +-
drivers/staging/android/ion/ion_chunk_heap.c | 27 +-
drivers/staging/android/ion/ion_cma_heap.c | 125 +--
drivers/staging/android/ion/ion_dummy_driver.c | 155 ---
drivers/staging/android/ion/ion_heap.c | 68 --
drivers/staging/android/ion/ion_of.c | 184 ---
drivers/staging/android/ion/ion_of.h | 37 -
drivers/staging/android/ion/ion_page_pool.c | 6 +-
drivers/staging/android/ion/ion_priv.h | 473 --------
drivers/staging/android/ion/ion_system_heap.c | 53 +-
drivers/staging/android/ion/ion_test.c | 305 -----
drivers/staging/android/ion/tegra/Makefile | 1 -
drivers/staging/android/ion/tegra/tegra_ion.c | 80 --
drivers/staging/android/uapi/ion.h | 86 +-
drivers/staging/android/uapi/ion_test.h | 69 --
include/linux/cma.h | 6 +-
mm/cma.c | 31 +-
mm/cma.h | 1 +
mm/cma_debug.c | 2 +-
32 files changed, 620 insertions(+), 3214 deletions(-)
delete mode 100644 drivers/staging/android/ion/compat_ion.c
delete mode 100644 drivers/staging/android/ion/compat_ion.h
delete mode 100644 drivers/staging/android/ion/hisilicon/Kconfig
delete mode 100644 drivers/staging/android/ion/hisilicon/Makefile
delete mode 100644 drivers/staging/android/ion/hisilicon/hi6220_ion.c
delete mode 100644 drivers/staging/android/ion/ion_dummy_driver.c
delete mode 100644 drivers/staging/android/ion/ion_of.c
delete mode 100644 drivers/staging/android/ion/ion_of.h
delete mode 100644 drivers/staging/android/ion/ion_priv.h
delete mode 100644 drivers/staging/android/ion/ion_test.c
delete mode 100644 drivers/staging/android/ion/tegra/Makefile
delete mode 100644 drivers/staging/android/ion/tegra/tegra_ion.c
delete mode 100644 drivers/staging/android/uapi/ion_test.h
--
2.7.4
On 04/08/2017 11:12 AM, Emil Velikov wrote:
> Hi Laura,
>
> Couple of trivial nitpicks below.
>
> On 3 April 2017 at 19:57, Laura Abbott <labbott(a)redhat.com> wrote:
>
>> --- a/drivers/staging/android/ion/ion.h
>> +++ b/drivers/staging/android/ion/ion.h
>> @@ -1,5 +1,5 @@
>> /*
>> - * drivers/staging/android/ion/ion.h
>> + * drivers/staging/android/ion/ion_priv.h
> Does not match the actual filename.
>
>> *
>> * Copyright (C) 2011 Google, Inc.
>> *
>> @@ -14,24 +14,26 @@
>> *
>> */
>>
>> -#ifndef _LINUX_ION_H
>> -#define _LINUX_ION_H
>> +#ifndef _ION_PRIV_H
>> +#define _ION_PRIV_H
>>
> Ditto.
>
>> +#include <linux/device.h>
>> +#include <linux/dma-direction.h>
>> +#include <linux/kref.h>
>> +#include <linux/mm_types.h>
>> +#include <linux/mutex.h>
>> +#include <linux/rbtree.h>
>> +#include <linux/sched.h>
>> +#include <linux/shrinker.h>
>> #include <linux/types.h>
>> +#include <linux/miscdevice.h>
>>
>> #include "../uapi/ion.h"
>>
> You don't want to use "../" in includes. Perhaps address with another
> patch, if you haven't already ?
>
There isn't a better option until this driver moves out of staging.
Once it moves out it can be fixed up.
Thanks,
Laura
> Regards,
> Emil
>
Hi,
This is v2 of the series to do some serious Ion clean up in preparation for
moving out of staging. I got good feedback last time so this series mostly
attempts to address that feedback and do more still more cleanup. Highlights:
- All calls to DMA APIs should now be with a real actual proper device
structure
- Patch to stop setting sg_dma_address manually now included
- Fix for a bug in the query interface
- Removal of custom ioctl interface
- Removal of import interface
- Removal of any notion of using Ion as an in kernel interface.
- Cleanup of ABI so compat interface is no longer needed
- Deletion of a bit more platform code
- Combined heap enumeration and heap registration code up so there are fewer
layers of abstraction
- Some general cleanup and header reduction.
- Removal of both the ion_client and ion_handle structures since these mostly
become redundant. As a result, Ion only returns a dma_buf fd. The overall
result is that the only Ion interfaces are the query ioctl and the alloc
ioctl.
The following are still TODOs/open problems:
- Sumit's comments about the CMA naming.
- Bindings/platform for chunk and carveout heap
- There was some discussion about making the sg_table duplication generic. I
got bogged down in handling some of the edge cases for generic handling
so I put this aside. Making it generic is still something that should happen.
- More fine-grained support for restricting heap access. There are good
arguments to be made for having a way for having good integration with
selinux and other policy mechanisms.
- While not on the original list, there is still no good good test standalone
test framework. I noticed that the existing ion_test was fairly generic so I
proposed moving it to dma_buf. Daniel Vetter suggested just using the VGEM
module instead. Ideally, the tests can live as part of some other existing
test set (drm tests maybe?)
Feedback appreciated as always.
Thanks,
Laura
Laura Abbott (21):
cma: Store a name in the cma structure
cma: Introduce cma_for_each_area
staging: android: ion: Remove dmap_cnt
staging: android: ion: Remove alignment from allocation field
staging: android: ion: Duplicate sg_table
staging: android: ion: Call dma_map_sg for syncing and mapping
staging: android: ion: Remove page faulting support
staging: android: ion: Remove crufty cache support
staging: android: ion: Remove custom ioctl interface
staging: android: ion: Remove import interface
staging: android: ion: Remove duplicate ION_IOC_MAP
staging: android: ion: Remove old platform support
staging: android: ion: Use CMA APIs directly
staging: android: ion: Stop butchering the DMA address
staging: android: ion: Break the ABI in the name of forward progress
staging: android: ion: Get rid of ion_phys_addr_t
staging: android: ion: Collapse internal header files
staging: android: ion: Rework heap registration/enumeration
staging: android: ion: Drop ion_map_kernel interface
staging: android: ion: Remove ion_handle and ion_client
staging: android: ion: Set query return value
drivers/base/dma-contiguous.c | 5 +-
drivers/staging/android/ion/Kconfig | 56 +-
drivers/staging/android/ion/Makefile | 18 +-
drivers/staging/android/ion/compat_ion.c | 195 ----
drivers/staging/android/ion/compat_ion.h | 29 -
drivers/staging/android/ion/hisilicon/Kconfig | 5 -
drivers/staging/android/ion/hisilicon/Makefile | 1 -
drivers/staging/android/ion/hisilicon/hi6220_ion.c | 113 --
drivers/staging/android/ion/ion-ioctl.c | 85 +-
drivers/staging/android/ion/ion.c | 1164 +++-----------------
drivers/staging/android/ion/ion.h | 393 +++++--
drivers/staging/android/ion/ion_carveout_heap.c | 37 +-
drivers/staging/android/ion/ion_chunk_heap.c | 27 +-
drivers/staging/android/ion/ion_cma_heap.c | 125 +--
drivers/staging/android/ion/ion_dummy_driver.c | 156 ---
drivers/staging/android/ion/ion_heap.c | 68 --
drivers/staging/android/ion/ion_of.c | 184 ----
drivers/staging/android/ion/ion_of.h | 37 -
drivers/staging/android/ion/ion_page_pool.c | 6 +-
drivers/staging/android/ion/ion_priv.h | 473 --------
drivers/staging/android/ion/ion_system_heap.c | 53 +-
drivers/staging/android/ion/ion_test.c | 305 -----
drivers/staging/android/ion/tegra/Makefile | 1 -
drivers/staging/android/ion/tegra/tegra_ion.c | 80 --
drivers/staging/android/uapi/ion.h | 86 +-
drivers/staging/android/uapi/ion_test.h | 69 --
include/linux/cma.h | 6 +-
mm/cma.c | 25 +-
mm/cma.h | 1 +
mm/cma_debug.c | 2 +-
30 files changed, 610 insertions(+), 3195 deletions(-)
delete mode 100644 drivers/staging/android/ion/compat_ion.c
delete mode 100644 drivers/staging/android/ion/compat_ion.h
delete mode 100644 drivers/staging/android/ion/hisilicon/Kconfig
delete mode 100644 drivers/staging/android/ion/hisilicon/Makefile
delete mode 100644 drivers/staging/android/ion/hisilicon/hi6220_ion.c
delete mode 100644 drivers/staging/android/ion/ion_dummy_driver.c
delete mode 100644 drivers/staging/android/ion/ion_of.c
delete mode 100644 drivers/staging/android/ion/ion_of.h
delete mode 100644 drivers/staging/android/ion/ion_priv.h
delete mode 100644 drivers/staging/android/ion/ion_test.c
delete mode 100644 drivers/staging/android/ion/tegra/Makefile
delete mode 100644 drivers/staging/android/ion/tegra/tegra_ion.c
delete mode 100644 drivers/staging/android/uapi/ion_test.h
--
2.7.4
Hi,
There's been some recent discussions[1] about Ion-like frameworks. There's
apparently interest in just keeping Ion since it works reasonablly well.
This series does what should be the final clean ups for it to possibly be
moved out of staging.
This includes the following:
- Some general clean up and removal of features that never got a lot of use
as far as I can tell.
- Fixing up the caching. This is the series I proposed back in December[2]
but never heard any feedback on. It will certainly break existing
applications that rely on the implicit caching. I'd rather make an effort
to move to a model that isn't going directly against the establishement
though.
- Fixing up the platform support. The devicetree approach was never well
recieved by DT maintainers. The proposal here is to think of Ion less as
specifying requirements and more of a framework for exposing memory to
userspace.
- CMA allocations now happen without the need of a dummy device structure.
This fixes a bunch of the reasons why I attempted to add devicetree
support before.
I've had problems getting feedback in the past so if I don't hear any major
objections I'm going to send out with the RFC dropped to be picked up.
The only reason there isn't a patch to come out of staging is to discuss any
other changes to the ABI people might want. Once this comes out of staging,
I really don't want to mess with the ABI.
Feedback appreciated.
Thanks,
Laura
[1] https://marc.info/?l=linux-kernel&m=148699712602105&w=2
[2] https://marc.info/?l=linaro-mm-sig&m=148176050802908&w=2
Laura Abbott (12):
staging: android: ion: Remove dmap_cnt
staging: android: ion: Remove alignment from allocation field
staging: android: ion: Duplicate sg_table
staging: android: ion: Call dma_map_sg for syncing and mapping
staging: android: ion: Remove page faulting support
staging: android: ion: Remove crufty cache support
staging: android: ion: Remove old platform support
cma: Store a name in the cma structure
cma: Introduce cma_for_each_area
staging: android: ion: Use CMA APIs directly
staging: android: ion: Make Ion heaps selectable
staging; android: ion: Enumerate all available heaps
drivers/base/dma-contiguous.c | 5 +-
drivers/staging/android/ion/Kconfig | 51 ++--
drivers/staging/android/ion/Makefile | 14 +-
drivers/staging/android/ion/hisilicon/Kconfig | 5 -
drivers/staging/android/ion/hisilicon/Makefile | 1 -
drivers/staging/android/ion/hisilicon/hi6220_ion.c | 113 ---------
drivers/staging/android/ion/ion-ioctl.c | 6 -
drivers/staging/android/ion/ion.c | 282 ++++++---------------
drivers/staging/android/ion/ion.h | 5 +-
drivers/staging/android/ion/ion_carveout_heap.c | 16 +-
drivers/staging/android/ion/ion_chunk_heap.c | 15 +-
drivers/staging/android/ion/ion_cma_heap.c | 102 ++------
drivers/staging/android/ion/ion_dummy_driver.c | 156 ------------
drivers/staging/android/ion/ion_enumerate.c | 89 +++++++
drivers/staging/android/ion/ion_of.c | 184 --------------
drivers/staging/android/ion/ion_of.h | 37 ---
drivers/staging/android/ion/ion_page_pool.c | 3 -
drivers/staging/android/ion/ion_priv.h | 57 ++++-
drivers/staging/android/ion/ion_system_heap.c | 14 +-
drivers/staging/android/ion/tegra/Makefile | 1 -
drivers/staging/android/ion/tegra/tegra_ion.c | 80 ------
include/linux/cma.h | 6 +-
mm/cma.c | 25 +-
mm/cma.h | 1 +
mm/cma_debug.c | 2 +-
25 files changed, 312 insertions(+), 958 deletions(-)
delete mode 100644 drivers/staging/android/ion/hisilicon/Kconfig
delete mode 100644 drivers/staging/android/ion/hisilicon/Makefile
delete mode 100644 drivers/staging/android/ion/hisilicon/hi6220_ion.c
delete mode 100644 drivers/staging/android/ion/ion_dummy_driver.c
create mode 100644 drivers/staging/android/ion/ion_enumerate.c
delete mode 100644 drivers/staging/android/ion/ion_of.c
delete mode 100644 drivers/staging/android/ion/ion_of.h
delete mode 100644 drivers/staging/android/ion/tegra/Makefile
delete mode 100644 drivers/staging/android/ion/tegra/tegra_ion.c
--
2.7.4
dma-buf is designed to share buffers. Sharing means that there needs to
be another subsystem to accept those buffers. Introduce a simple test
module to act as a dummy system to accept dma_bufs from elsewhere. The
goal is to provide a very simple interface to validate exported buffers
do something reasonable. This is based on ion_test.c that existed for
the Ion framework.
Signed-off-by: Laura Abbott <labbott(a)redhat.com>
---
This is basically a drop in of what was available as
drivers/staging/android/ion/ion_test.c. Given it has no Ion specific
parts it might be useful as a more general test module. RFC mostly
to see if this is generally useful or not.
---
drivers/dma-buf/Kconfig | 9 ++
drivers/dma-buf/Makefile | 1 +
drivers/dma-buf/dma-buf-test.c | 309 ++++++++++++++++++++++++++++++++++++++
include/uapi/linux/dma_buf_test.h | 67 +++++++++
4 files changed, 386 insertions(+)
create mode 100644 drivers/dma-buf/dma-buf-test.c
create mode 100644 include/uapi/linux/dma_buf_test.h
diff --git a/drivers/dma-buf/Kconfig b/drivers/dma-buf/Kconfig
index ed3b785..8b3fdb1 100644
--- a/drivers/dma-buf/Kconfig
+++ b/drivers/dma-buf/Kconfig
@@ -30,4 +30,13 @@ config SW_SYNC
WARNING: improper use of this can result in deadlocking kernel
drivers from userspace. Intended for test and debug only.
+config DMA_BUF_TEST
+ bool "Test module for dma-buf"
+ default n
+ ---help---
+ A test module to validate dma_buf APIs. This should not be
+ enabled for general use.
+
+ Say N here unless you know you want this.
+
endmenu
diff --git a/drivers/dma-buf/Makefile b/drivers/dma-buf/Makefile
index c33bf88..5029608 100644
--- a/drivers/dma-buf/Makefile
+++ b/drivers/dma-buf/Makefile
@@ -1,3 +1,4 @@
obj-y := dma-buf.o dma-fence.o dma-fence-array.o reservation.o seqno-fence.o
obj-$(CONFIG_SYNC_FILE) += sync_file.o
obj-$(CONFIG_SW_SYNC) += sw_sync.o sync_debug.o
+obj-$(CONFIG_DMA_BUF_TEST) += dma-buf-test.o
diff --git a/drivers/dma-buf/dma-buf-test.c b/drivers/dma-buf/dma-buf-test.c
new file mode 100644
index 0000000..3af131c
--- /dev/null
+++ b/drivers/dma-buf/dma-buf-test.c
@@ -0,0 +1,309 @@
+/*
+ * Copyright (C) 2013 Google, Inc.
+ *
+ * This software is licensed under the terms of the GNU General Public
+ * License versdma_buf 2, as published by the Free Software Foundatdma_buf, and
+ * may be copied, distributed, and modified under those terms.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ */
+
+#define pr_fmt(fmt) "dma-buf-test: " fmt
+
+#include <linux/dma-buf.h>
+#include <linux/dma-direction.h>
+#include <linux/fs.h>
+#include <linux/miscdevice.h>
+#include <linux/mm.h>
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/sched.h>
+#include <linux/slab.h>
+#include <linux/uaccess.h>
+#include <linux/vmalloc.h>
+
+#include <uapi/linux/dma_buf_test.h>
+
+struct dma_buf_test_device {
+ struct miscdevice misc;
+};
+
+struct dma_buf_test_data {
+ struct dma_buf *dma_buf;
+ struct device *dev;
+};
+
+static int dma_buf_handle_test_dma(struct device *dev, struct dma_buf *dma_buf,
+ void __user *ptr, size_t offset, size_t size,
+ bool write)
+{
+ int ret = 0;
+ struct dma_buf_attachment *attach;
+ struct sg_table *table;
+ pgprot_t pgprot = pgprot_writecombine(PAGE_KERNEL);
+ enum dma_data_direction dir = write ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
+ struct sg_page_iter sg_iter;
+ unsigned long offset_page;
+
+ attach = dma_buf_attach(dma_buf, dev);
+ if (IS_ERR(attach))
+ return PTR_ERR(attach);
+
+ table = dma_buf_map_attachment(attach, dir);
+ if (IS_ERR(table))
+ return PTR_ERR(table);
+
+ offset_page = offset >> PAGE_SHIFT;
+ offset %= PAGE_SIZE;
+
+ for_each_sg_page(table->sgl, &sg_iter, table->nents, offset_page) {
+ struct page *page = sg_page_iter_page(&sg_iter);
+ void *vaddr = vmap(&page, 1, VM_MAP, pgprot);
+ size_t to_copy = PAGE_SIZE - offset;
+
+ to_copy = min(to_copy, size);
+ if (!vaddr) {
+ ret = -ENOMEM;
+ goto err;
+ }
+
+ if (write)
+ ret = copy_from_user(vaddr + offset, ptr, to_copy);
+ else
+ ret = copy_to_user(ptr, vaddr + offset, to_copy);
+
+ vunmap(vaddr);
+ if (ret) {
+ ret = -EFAULT;
+ goto err;
+ }
+ size -= to_copy;
+ if (!size)
+ break;
+ ptr += to_copy;
+ offset = 0;
+ }
+
+err:
+ dma_buf_unmap_attachment(attach, table, dir);
+ dma_buf_detach(dma_buf, attach);
+ return ret;
+}
+
+static int dma_buf_handle_test_kernel(struct dma_buf *dma_buf, void __user *ptr,
+ size_t offset, size_t size, bool write)
+{
+ int ret;
+ unsigned long page_offset = offset >> PAGE_SHIFT;
+ size_t copy_offset = offset % PAGE_SIZE;
+ size_t copy_size = size;
+ enum dma_data_direction dir = write ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
+
+ if (offset > dma_buf->size || size > dma_buf->size - offset)
+ return -EINVAL;
+
+ ret = dma_buf_begin_cpu_access(dma_buf, dir);
+ if (ret)
+ return ret;
+
+ while (copy_size > 0) {
+ size_t to_copy;
+ void *vaddr = dma_buf_kmap(dma_buf, page_offset);
+
+ if (!vaddr)
+ goto err;
+
+ to_copy = min_t(size_t, PAGE_SIZE - copy_offset, copy_size);
+
+ if (write)
+ ret = copy_from_user(vaddr + copy_offset, ptr, to_copy);
+ else
+ ret = copy_to_user(ptr, vaddr + copy_offset, to_copy);
+
+ dma_buf_kunmap(dma_buf, page_offset, vaddr);
+ if (ret) {
+ ret = -EFAULT;
+ goto err;
+ }
+
+ copy_size -= to_copy;
+ ptr += to_copy;
+ page_offset++;
+ copy_offset = 0;
+ }
+err:
+ dma_buf_end_cpu_access(dma_buf, dir);
+ return ret;
+}
+
+static long dma_buf_test_ioctl(struct file *filp, unsigned int cmd,
+ unsigned long arg)
+{
+ struct dma_buf_test_data *test_data = filp->private_data;
+ int ret = 0;
+
+ union {
+ struct dma_buf_test_rw_data test_rw;
+ } data;
+
+ if (_IOC_SIZE(cmd) > sizeof(data))
+ return -EINVAL;
+
+ if (_IOC_DIR(cmd) & _IOC_WRITE)
+ if (copy_from_user(&data, (void __user *)arg, _IOC_SIZE(cmd)))
+ return -EFAULT;
+
+ switch (cmd) {
+ case DMA_BUF_IOC_TEST_SET_FD:
+ {
+ struct dma_buf *dma_buf = NULL;
+ int fd = arg;
+
+ if (fd >= 0) {
+ dma_buf = dma_buf_get((int)arg);
+ if (IS_ERR(dma_buf))
+ return PTR_ERR(dma_buf);
+ }
+ if (test_data->dma_buf)
+ dma_buf_put(test_data->dma_buf);
+ test_data->dma_buf = dma_buf;
+ break;
+ }
+ case DMA_BUF_IOC_TEST_DMA_MAPPING:
+ {
+ ret = dma_buf_handle_test_dma(test_data->dev,
+ test_data->dma_buf,
+ u64_to_user_ptr(data.test_rw.ptr),
+ data.test_rw.offset,
+ data.test_rw.size,
+ data.test_rw.write);
+ break;
+ }
+ case DMA_BUF_IOC_TEST_KERNEL_MAPPING:
+ {
+ ret = dma_buf_handle_test_kernel(test_data->dma_buf,
+ u64_to_user_ptr(data.test_rw.ptr),
+ data.test_rw.offset,
+ data.test_rw.size,
+ data.test_rw.write);
+ break;
+ }
+ default:
+ return -ENOTTY;
+ }
+
+ if (_IOC_DIR(cmd) & _IOC_READ) {
+ if (copy_to_user((void __user *)arg, &data, sizeof(data)))
+ return -EFAULT;
+ }
+ return ret;
+}
+
+static int dma_buf_test_open(struct inode *inode, struct file *file)
+{
+ struct dma_buf_test_data *data;
+ struct miscdevice *miscdev = file->private_data;
+
+ data = kzalloc(sizeof(*data), GFP_KERNEL);
+ if (!data)
+ return -ENOMEM;
+
+ data->dev = miscdev->parent;
+
+ file->private_data = data;
+
+ return 0;
+}
+
+static int dma_buf_test_release(struct inode *inode, struct file *file)
+{
+ struct dma_buf_test_data *data = file->private_data;
+
+ kfree(data);
+
+ return 0;
+}
+
+static const struct file_operations dma_buf_test_fops = {
+ .owner = THIS_MODULE,
+ .unlocked_ioctl = dma_buf_test_ioctl,
+ .compat_ioctl = dma_buf_test_ioctl,
+ .open = dma_buf_test_open,
+ .release = dma_buf_test_release,
+};
+
+static int __init dma_buf_test_probe(struct platform_device *pdev)
+{
+ int ret;
+ struct dma_buf_test_device *testdev;
+
+ testdev = devm_kzalloc(&pdev->dev, sizeof(struct dma_buf_test_device),
+ GFP_KERNEL);
+ if (!testdev)
+ return -ENOMEM;
+
+ testdev->misc.minor = MISC_DYNAMIC_MINOR;
+ testdev->misc.name = "dma_buf-test";
+ testdev->misc.fops = &dma_buf_test_fops;
+ testdev->misc.parent = &pdev->dev;
+ /*
+ * We need to force 'something' for a DMA mask. This isn't an actual
+ * device and won't be doing actual DMA so pick 'something' that
+ * probably won't blow up. Probably.
+ */
+ dma_coerce_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64));
+ ret = misc_register(&testdev->misc);
+ if (ret) {
+ pr_err("failed to register misc device.\n");
+ return ret;
+ }
+
+ platform_set_drvdata(pdev, testdev);
+
+ return 0;
+}
+
+static int dma_buf_test_remove(struct platform_device *pdev)
+{
+ struct dma_buf_test_device *testdev;
+
+ testdev = platform_get_drvdata(pdev);
+ if (!testdev)
+ return -ENODATA;
+
+ misc_deregister(&testdev->misc);
+ return 0;
+}
+
+static struct platform_device *dma_buf_test_pdev;
+static struct platform_driver dma_buf_test_platform_driver = {
+ .remove = dma_buf_test_remove,
+ .driver = {
+ .name = "dma_buf-test",
+ },
+};
+
+static int __init dma_buf_test_init(void)
+{
+ dma_buf_test_pdev = platform_device_register_simple("dma-buf-test",
+ -1, NULL, 0);
+ if (IS_ERR(dma_buf_test_pdev))
+ return PTR_ERR(dma_buf_test_pdev);
+
+ return platform_driver_probe(&dma_buf_test_platform_driver,
+ dma_buf_test_probe);
+}
+
+static void __exit dma_buf_test_exit(void)
+{
+ platform_driver_unregister(&dma_buf_test_platform_driver);
+ platform_device_unregister(dma_buf_test_pdev);
+}
+
+module_init(dma_buf_test_init);
+module_exit(dma_buf_test_exit);
+MODULE_LICENSE("GPL v2");
diff --git a/include/uapi/linux/dma_buf_test.h b/include/uapi/linux/dma_buf_test.h
new file mode 100644
index 0000000..af2d521
--- /dev/null
+++ b/include/uapi/linux/dma_buf_test.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2011 Google, Inc.
+ *
+ * This software is licensed under the terms of the GNU General Public
+ * License versdma_buf 2, as published by the Free Software Foundatdma_buf, and
+ * may be copied, distributed, and modified under those terms.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ */
+
+#ifndef _UAPI_LINUX_DMA_BUF_TEST_H
+#define _UAPI_LINUX_DMA_BUF_TEST_H
+
+#include <linux/ioctl.h>
+#include <linux/types.h>
+
+/**
+ * struct dma_buf_test_rw_data - metadata passed to the kernel to read handle
+ * @ptr: a pointer to an area at least as large as size
+ * @offset: offset into the dma_buf buffer to start reading
+ * @size: size to read or write
+ * @write: 1 to write, 0 to read
+ */
+struct dma_buf_test_rw_data {
+ __u64 ptr;
+ __u64 offset;
+ __u64 size;
+ int write;
+ int __padding;
+};
+
+#define DMA_BUF_IOC_MAGIC 'I'
+
+/**
+ * DOC: DMA_BUF_IOC_TEST_SET_DMA_BUF - attach a dma buf to the test driver
+ *
+ * Attaches a dma buf fd to the test driver. Passing a second fd or -1 will
+ * release the first fd.
+ */
+#define DMA_BUF_IOC_TEST_SET_FD \
+ _IO(DMA_BUF_IOC_MAGIC, 0xf0)
+
+/**
+ * DOC: DMA_BUF_IOC_TEST_DMA_MAPPING - read or write memory from a handle as DMA
+ *
+ * Reads or writes the memory from a handle using an uncached mapping. Can be
+ * used by unit tests to emulate a DMA engine as close as possible. Only
+ * expected to be used for debugging and testing, may not always be available.
+ */
+#define DMA_BUF_IOC_TEST_DMA_MAPPING \
+ _IOW(DMA_BUF_IOC_MAGIC, 0xf1, struct dma_buf_test_rw_data)
+
+/**
+ * DOC: DMA_BUF_IOC_TEST_KERNEL_MAPPING - read or write memory from a handle
+ *
+ * Reads or writes the memory from a handle using a kernel mapping. Can be
+ * used by unit tests to test heap map_kernel functdma_bufs. Only expected to be
+ * used for debugging and testing, may not always be available.
+ */
+#define DMA_BUF_IOC_TEST_KERNEL_MAPPING \
+ _IOW(DMA_BUF_IOC_MAGIC, 0xf2, struct dma_buf_test_rw_data)
+
+#endif /* _UAPI_LINUX_DMA_BUF_TEST_H */
--
2.7.4
On Mon, Mar 06, 2017 at 11:58:05AM +0100, Mark Brown wrote:
> On Mon, Mar 06, 2017 at 11:40:41AM +0100, Daniel Vetter wrote:
>
> > No one gave a thing about android in upstream, so Greg KH just dumped it
> > all into staging/android/. We've discussed ION a bunch of times, recorded
> > anything we'd like to fix in staging/android/TODO, and Laura's patch
> > series here addresses a big chunk of that.
>
> > This is pretty much the same approach we (gpu folks) used to de-stage the
> > syncpt stuff.
>
> Well, there's also the fact that quite a few people have issues with the
> design (like Laurent). It seems like a lot of them have either got more
> comfortable with it over time, or at least not managed to come up with
> any better ideas in the meantime.
See the TODO, it has everything a really big group (look at the patch for
the full Cc: list) figured needs to be improved at LPC 2015. We don't just
merge stuff because merging stuff is fun :-)
Laurent was even in that group ...
-Daniel
--
Daniel Vetter
Software Engineer, Intel Corporation
http://blog.ffwll.ch