Message ID | 20220608152142.14495-2-jason@jlekstrand.net (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | dma-buf: Add an API for exporting sync files (v15) | expand |
Both patches pushed to drm-misc-next, thanks for your contribution!
Hi Jason, Thank you for the patch! Yet something to improve: [auto build test ERROR on tegra-drm/drm/tegra/for-next] [cannot apply to drm-tip/drm-tip linus/master v5.19-rc1 next-20220608] [If your patch is applied to the wrong git tree, kindly drop us a note. And when submitting patch, we suggest to use '--base' as documented in https://git-scm.com/docs/git-format-patch] url: https://github.com/intel-lab-lkp/linux/commits/Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 base: git://anongit.freedesktop.org/tegra/linux.git drm/tegra/for-next config: hexagon-randconfig-r041-20220608 (https://download.01.org/0day-ci/archive/20220609/202206090608.jRFcxzQE-lkp@intel.com/config) compiler: clang version 15.0.0 (https://github.com/llvm/llvm-project b92436efcb7813fc481b30f2593a4907568d917a) reproduce (this is a W=1 build): wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross chmod +x ~/bin/make.cross # https://github.com/intel-lab-lkp/linux/commit/d9d427e1ab310adae7e076f2531d00862d74a120 git remote add linux-review https://github.com/intel-lab-lkp/linux git fetch --no-tags linux-review Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 git checkout d9d427e1ab310adae7e076f2531d00862d74a120 # save the config file mkdir build_dir && cp config build_dir/.config COMPILER_INSTALL_PATH=$HOME/0day COMPILER=clang make.cross W=1 O=build_dir ARCH=hexagon SHELL=/bin/bash drivers/dma-buf/ If you fix the issue, kindly add following tag where applicable Reported-by: kernel test robot <lkp@intel.com> All errors (new ones prefixed by >>): >> drivers/dma-buf/dma-buf.c:337:22: error: variable has incomplete type 'enum dma_resv_usage' enum dma_resv_usage usage; ^ drivers/dma-buf/dma-buf.c:337:7: note: forward declaration of 'enum dma_resv_usage' enum dma_resv_usage usage; ^ >> drivers/dma-buf/dma-buf.c:355:10: error: implicit declaration of function 'dma_resv_usage_rw' [-Werror,-Wimplicit-function-declaration] usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); ^ >> drivers/dma-buf/dma-buf.c:356:8: error: implicit declaration of function 'dma_resv_get_singleton' [-Werror,-Wimplicit-function-declaration] ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); ^ 3 errors generated. vim +337 drivers/dma-buf/dma-buf.c 331 332 #if IS_ENABLED(CONFIG_SYNC_FILE) 333 static long dma_buf_export_sync_file(struct dma_buf *dmabuf, 334 void __user *user_data) 335 { 336 struct dma_buf_export_sync_file arg; > 337 enum dma_resv_usage usage; 338 struct dma_fence *fence = NULL; 339 struct sync_file *sync_file; 340 int fd, ret; 341 342 if (copy_from_user(&arg, user_data, sizeof(arg))) 343 return -EFAULT; 344 345 if (arg.flags & ~DMA_BUF_SYNC_RW) 346 return -EINVAL; 347 348 if ((arg.flags & DMA_BUF_SYNC_RW) == 0) 349 return -EINVAL; 350 351 fd = get_unused_fd_flags(O_CLOEXEC); 352 if (fd < 0) 353 return fd; 354 > 355 usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); > 356 ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); 357 if (ret) 358 goto err_put_fd; 359 360 if (!fence) 361 fence = dma_fence_get_stub(); 362 363 sync_file = sync_file_create(fence); 364 365 dma_fence_put(fence); 366 367 if (!sync_file) { 368 ret = -ENOMEM; 369 goto err_put_fd; 370 } 371 372 arg.fd = fd; 373 if (copy_to_user(user_data, &arg, sizeof(arg))) { 374 ret = -EFAULT; 375 goto err_put_file; 376 } 377 378 fd_install(fd, sync_file->file); 379 380 return 0; 381 382 err_put_file: 383 fput(sync_file->file); 384 err_put_fd: 385 put_unused_fd(fd); 386 return ret; 387 } 388 #endif 389
Hi Jason, Thank you for the patch! Yet something to improve: [auto build test ERROR on tegra-drm/drm/tegra/for-next] [cannot apply to drm-tip/drm-tip linus/master v5.19-rc1 next-20220608] [If your patch is applied to the wrong git tree, kindly drop us a note. And when submitting patch, we suggest to use '--base' as documented in https://git-scm.com/docs/git-format-patch] url: https://github.com/intel-lab-lkp/linux/commits/Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 base: git://anongit.freedesktop.org/tegra/linux.git drm/tegra/for-next config: arc-randconfig-r043-20220608 (https://download.01.org/0day-ci/archive/20220609/202206090724.2BjpdEjC-lkp@intel.com/config) compiler: arceb-elf-gcc (GCC) 11.3.0 reproduce (this is a W=1 build): wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross chmod +x ~/bin/make.cross # https://github.com/intel-lab-lkp/linux/commit/d9d427e1ab310adae7e076f2531d00862d74a120 git remote add linux-review https://github.com/intel-lab-lkp/linux git fetch --no-tags linux-review Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 git checkout d9d427e1ab310adae7e076f2531d00862d74a120 # save the config file mkdir build_dir && cp config build_dir/.config COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-11.3.0 make.cross W=1 O=build_dir ARCH=arc SHELL=/bin/bash drivers/ If you fix the issue, kindly add following tag where applicable Reported-by: kernel test robot <lkp@intel.com> All errors (new ones prefixed by >>): drivers/dma-buf/dma-buf.c: In function 'dma_buf_export_sync_file': >> drivers/dma-buf/dma-buf.c:337:29: error: storage size of 'usage' isn't known 337 | enum dma_resv_usage usage; | ^~~~~ >> drivers/dma-buf/dma-buf.c:355:17: error: implicit declaration of function 'dma_resv_usage_rw' [-Werror=implicit-function-declaration] 355 | usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); | ^~~~~~~~~~~~~~~~~ >> drivers/dma-buf/dma-buf.c:356:15: error: implicit declaration of function 'dma_resv_get_singleton'; did you mean 'dma_resv_test_signaled'? [-Werror=implicit-function-declaration] 356 | ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); | ^~~~~~~~~~~~~~~~~~~~~~ | dma_resv_test_signaled drivers/dma-buf/dma-buf.c:337:29: warning: unused variable 'usage' [-Wunused-variable] 337 | enum dma_resv_usage usage; | ^~~~~ cc1: some warnings being treated as errors vim +337 drivers/dma-buf/dma-buf.c 331 332 #if IS_ENABLED(CONFIG_SYNC_FILE) 333 static long dma_buf_export_sync_file(struct dma_buf *dmabuf, 334 void __user *user_data) 335 { 336 struct dma_buf_export_sync_file arg; > 337 enum dma_resv_usage usage; 338 struct dma_fence *fence = NULL; 339 struct sync_file *sync_file; 340 int fd, ret; 341 342 if (copy_from_user(&arg, user_data, sizeof(arg))) 343 return -EFAULT; 344 345 if (arg.flags & ~DMA_BUF_SYNC_RW) 346 return -EINVAL; 347 348 if ((arg.flags & DMA_BUF_SYNC_RW) == 0) 349 return -EINVAL; 350 351 fd = get_unused_fd_flags(O_CLOEXEC); 352 if (fd < 0) 353 return fd; 354 > 355 usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); > 356 ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); 357 if (ret) 358 goto err_put_fd; 359 360 if (!fence) 361 fence = dma_fence_get_stub(); 362 363 sync_file = sync_file_create(fence); 364 365 dma_fence_put(fence); 366 367 if (!sync_file) { 368 ret = -ENOMEM; 369 goto err_put_fd; 370 } 371 372 arg.fd = fd; 373 if (copy_to_user(user_data, &arg, sizeof(arg))) { 374 ret = -EFAULT; 375 goto err_put_file; 376 } 377 378 fd_install(fd, sync_file->file); 379 380 return 0; 381 382 err_put_file: 383 fput(sync_file->file); 384 err_put_fd: 385 put_unused_fd(fd); 386 return ret; 387 } 388 #endif 389
Hi Jason, Thank you for the patch! Perhaps something to improve: [auto build test WARNING on tegra-drm/drm/tegra/for-next] [cannot apply to drm-tip/drm-tip linus/master v5.19-rc1 next-20220609] [If your patch is applied to the wrong git tree, kindly drop us a note. And when submitting patch, we suggest to use '--base' as documented in https://git-scm.com/docs/git-format-patch] url: https://github.com/intel-lab-lkp/linux/commits/Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 base: git://anongit.freedesktop.org/tegra/linux.git drm/tegra/for-next config: i386-randconfig-a014 (https://download.01.org/0day-ci/archive/20220610/202206100914.FWjiKmaa-lkp@intel.com/config) compiler: gcc-11 (Debian 11.3.0-3) 11.3.0 reproduce (this is a W=1 build): # https://github.com/intel-lab-lkp/linux/commit/d9d427e1ab310adae7e076f2531d00862d74a120 git remote add linux-review https://github.com/intel-lab-lkp/linux git fetch --no-tags linux-review Jason-Ekstrand/dma-buf-Add-an-API-for-exporting-sync-files-v15/20220608-232447 git checkout d9d427e1ab310adae7e076f2531d00862d74a120 # save the config file mkdir build_dir && cp config build_dir/.config make W=1 O=build_dir ARCH=i386 SHELL=/bin/bash drivers/dma-buf/ If you fix the issue, kindly add following tag where applicable Reported-by: kernel test robot <lkp@intel.com> All warnings (new ones prefixed by >>): drivers/dma-buf/dma-buf.c: In function 'dma_buf_export_sync_file': drivers/dma-buf/dma-buf.c:337:29: error: storage size of 'usage' isn't known 337 | enum dma_resv_usage usage; | ^~~~~ drivers/dma-buf/dma-buf.c:355:17: error: implicit declaration of function 'dma_resv_usage_rw' [-Werror=implicit-function-declaration] 355 | usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); | ^~~~~~~~~~~~~~~~~ drivers/dma-buf/dma-buf.c:356:15: error: implicit declaration of function 'dma_resv_get_singleton'; did you mean 'dma_resv_test_signaled'? [-Werror=implicit-function-declaration] 356 | ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); | ^~~~~~~~~~~~~~~~~~~~~~ | dma_resv_test_signaled >> drivers/dma-buf/dma-buf.c:337:29: warning: unused variable 'usage' [-Wunused-variable] 337 | enum dma_resv_usage usage; | ^~~~~ cc1: some warnings being treated as errors vim +/usage +337 drivers/dma-buf/dma-buf.c 331 332 #if IS_ENABLED(CONFIG_SYNC_FILE) 333 static long dma_buf_export_sync_file(struct dma_buf *dmabuf, 334 void __user *user_data) 335 { 336 struct dma_buf_export_sync_file arg; > 337 enum dma_resv_usage usage; 338 struct dma_fence *fence = NULL; 339 struct sync_file *sync_file; 340 int fd, ret; 341 342 if (copy_from_user(&arg, user_data, sizeof(arg))) 343 return -EFAULT; 344 345 if (arg.flags & ~DMA_BUF_SYNC_RW) 346 return -EINVAL; 347 348 if ((arg.flags & DMA_BUF_SYNC_RW) == 0) 349 return -EINVAL; 350 351 fd = get_unused_fd_flags(O_CLOEXEC); 352 if (fd < 0) 353 return fd; 354 355 usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); 356 ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); 357 if (ret) 358 goto err_put_fd; 359 360 if (!fence) 361 fence = dma_fence_get_stub(); 362 363 sync_file = sync_file_create(fence); 364 365 dma_fence_put(fence); 366 367 if (!sync_file) { 368 ret = -ENOMEM; 369 goto err_put_fd; 370 } 371 372 arg.fd = fd; 373 if (copy_to_user(user_data, &arg, sizeof(arg))) { 374 ret = -EFAULT; 375 goto err_put_file; 376 } 377 378 fd_install(fd, sync_file->file); 379 380 return 0; 381 382 err_put_file: 383 fput(sync_file->file); 384 err_put_fd: 385 put_unused_fd(fd); 386 return ret; 387 } 388 #endif 389
diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c index 79795857be3e..6ff54f7e6119 100644 --- a/drivers/dma-buf/dma-buf.c +++ b/drivers/dma-buf/dma-buf.c @@ -20,6 +20,7 @@ #include <linux/debugfs.h> #include <linux/module.h> #include <linux/seq_file.h> +#include <linux/sync_file.h> #include <linux/poll.h> #include <linux/dma-resv.h> #include <linux/mm.h> @@ -192,6 +193,9 @@ static loff_t dma_buf_llseek(struct file *file, loff_t offset, int whence) * Note that this only signals the completion of the respective fences, i.e. the * DMA transfers are complete. Cache flushing and any other necessary * preparations before CPU access can begin still need to happen. + * + * As an alternative to poll(), the set of fences on DMA buffer can be + * exported as a &sync_file using &dma_buf_sync_file_export. */ static void dma_buf_poll_cb(struct dma_fence *fence, struct dma_fence_cb *cb) @@ -326,6 +330,64 @@ static long dma_buf_set_name(struct dma_buf *dmabuf, const char __user *buf) return 0; } +#if IS_ENABLED(CONFIG_SYNC_FILE) +static long dma_buf_export_sync_file(struct dma_buf *dmabuf, + void __user *user_data) +{ + struct dma_buf_export_sync_file arg; + enum dma_resv_usage usage; + struct dma_fence *fence = NULL; + struct sync_file *sync_file; + int fd, ret; + + if (copy_from_user(&arg, user_data, sizeof(arg))) + return -EFAULT; + + if (arg.flags & ~DMA_BUF_SYNC_RW) + return -EINVAL; + + if ((arg.flags & DMA_BUF_SYNC_RW) == 0) + return -EINVAL; + + fd = get_unused_fd_flags(O_CLOEXEC); + if (fd < 0) + return fd; + + usage = dma_resv_usage_rw(arg.flags & DMA_BUF_SYNC_WRITE); + ret = dma_resv_get_singleton(dmabuf->resv, usage, &fence); + if (ret) + goto err_put_fd; + + if (!fence) + fence = dma_fence_get_stub(); + + sync_file = sync_file_create(fence); + + dma_fence_put(fence); + + if (!sync_file) { + ret = -ENOMEM; + goto err_put_fd; + } + + arg.fd = fd; + if (copy_to_user(user_data, &arg, sizeof(arg))) { + ret = -EFAULT; + goto err_put_file; + } + + fd_install(fd, sync_file->file); + + return 0; + +err_put_file: + fput(sync_file->file); +err_put_fd: + put_unused_fd(fd); + return ret; +} +#endif + static long dma_buf_ioctl(struct file *file, unsigned int cmd, unsigned long arg) { @@ -369,6 +431,11 @@ static long dma_buf_ioctl(struct file *file, case DMA_BUF_SET_NAME_B: return dma_buf_set_name(dmabuf, (const char __user *)arg); +#if IS_ENABLED(CONFIG_SYNC_FILE) + case DMA_BUF_IOCTL_EXPORT_SYNC_FILE: + return dma_buf_export_sync_file(dmabuf, (void __user *)arg); +#endif + default: return -ENOTTY; } diff --git a/include/uapi/linux/dma-buf.h b/include/uapi/linux/dma-buf.h index 8e4a2ca0bcbf..46f1e3e98b02 100644 --- a/include/uapi/linux/dma-buf.h +++ b/include/uapi/linux/dma-buf.h @@ -85,6 +85,40 @@ struct dma_buf_sync { #define DMA_BUF_NAME_LEN 32 +/** + * struct dma_buf_export_sync_file - Get a sync_file from a dma-buf + * + * Userspace can perform a DMA_BUF_IOCTL_EXPORT_SYNC_FILE to retrieve the + * current set of fences on a dma-buf file descriptor as a sync_file. CPU + * waits via poll() or other driver-specific mechanisms typically wait on + * whatever fences are on the dma-buf at the time the wait begins. This + * is similar except that it takes a snapshot of the current fences on the + * dma-buf for waiting later instead of waiting immediately. This is + * useful for modern graphics APIs such as Vulkan which assume an explicit + * synchronization model but still need to inter-operate with dma-buf. + */ +struct dma_buf_export_sync_file { + /** + * @flags: Read/write flags + * + * Must be DMA_BUF_SYNC_READ, DMA_BUF_SYNC_WRITE, or both. + * + * If DMA_BUF_SYNC_READ is set and DMA_BUF_SYNC_WRITE is not set, + * the returned sync file waits on any writers of the dma-buf to + * complete. Waiting on the returned sync file is equivalent to + * poll() with POLLIN. + * + * If DMA_BUF_SYNC_WRITE is set, the returned sync file waits on + * any users of the dma-buf (read or write) to complete. Waiting + * on the returned sync file is equivalent to poll() with POLLOUT. + * If both DMA_BUF_SYNC_WRITE and DMA_BUF_SYNC_READ are set, this + * is equivalent to just DMA_BUF_SYNC_WRITE. + */ + __u32 flags; + /** @fd: Returned sync file descriptor */ + __s32 fd; +}; + #define DMA_BUF_BASE 'b' #define DMA_BUF_IOCTL_SYNC _IOW(DMA_BUF_BASE, 0, struct dma_buf_sync) @@ -94,5 +128,6 @@ struct dma_buf_sync { #define DMA_BUF_SET_NAME _IOW(DMA_BUF_BASE, 1, const char *) #define DMA_BUF_SET_NAME_A _IOW(DMA_BUF_BASE, 1, u32) #define DMA_BUF_SET_NAME_B _IOW(DMA_BUF_BASE, 1, u64) +#define DMA_BUF_IOCTL_EXPORT_SYNC_FILE _IOWR(DMA_BUF_BASE, 2, struct dma_buf_export_sync_file) #endif