[RFC PATCH v2 8/9] hyper_dmabuf: event-polling mechanism for detecting a new hyper_DMABUF
New method based on polling for a importing VM to know about a new hyper_DMABUF exported to it. For this, the userspace now can poll the device node to check if there a new event, which is created if there's a new hyper_DMABUF available in importing VM (just exported). A poll function call was added to the device driver interface for this new functionality. Event-generation functionalitywas also implemented in all other relavant parts of driver. This "event-polling" mechanism is optional feature and can be enabled by setting a Kernel config option, "HYPER_DMABUF_EVENT_GEN". Signed-off-by: Dongwon KimSigned-off-by: Mateusz Polrola --- drivers/dma-buf/hyper_dmabuf/Kconfig | 20 +++ drivers/dma-buf/hyper_dmabuf/Makefile | 1 + drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c | 146 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.h | 11 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.c | 122 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.h | 38 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_list.c | 1 + drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_msg.c | 11 ++ include/uapi/linux/hyper_dmabuf.h | 11 ++ 9 files changed, 361 insertions(+) create mode 100644 drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.c create mode 100644 drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.h diff --git a/drivers/dma-buf/hyper_dmabuf/Kconfig b/drivers/dma-buf/hyper_dmabuf/Kconfig index 68f3d6ce2c1f..92510731af25 100644 --- a/drivers/dma-buf/hyper_dmabuf/Kconfig +++ b/drivers/dma-buf/hyper_dmabuf/Kconfig @@ -20,6 +20,16 @@ config HYPER_DMABUF_SYSFS The location of sysfs is under "" +config HYPER_DMABUF_EVENT_GEN +bool "Enable event-generation and polling operation" +default n +depends on HYPER_DMABUF +help + With this config enabled, hyper_dmabuf driver on the importer side + generates events and queue those up in the event list whenever a new + shared DMA-BUF is available. Events in the list can be retrieved by + read operation. + config HYPER_DMABUF_XEN bool "Configure hyper_dmabuf for XEN hypervisor" default y @@ -27,4 +37,14 @@ config HYPER_DMABUF_XEN help Enabling Hyper_DMABUF Backend for XEN hypervisor +config HYPER_DMABUF_XEN_AUTO_RX_CH_ADD +bool "Enable automatic rx-ch add with 10 secs interval" +default y +depends on HYPER_DMABUF && HYPER_DMABUF_XEN +help + If enabled, driver reads a node in xenstore every 10 seconds + to check whether there is any tx comm ch configured by another + domain then initialize matched rx comm ch automatically for any + existing tx comm chs. + endmenu diff --git a/drivers/dma-buf/hyper_dmabuf/Makefile b/drivers/dma-buf/hyper_dmabuf/Makefile index 578a669a0d3e..f573dd5c4054 100644 --- a/drivers/dma-buf/hyper_dmabuf/Makefile +++ b/drivers/dma-buf/hyper_dmabuf/Makefile @@ -11,6 +11,7 @@ ifneq ($(KERNELRELEASE),) hyper_dmabuf_id.o \ hyper_dmabuf_remote_sync.o \ hyper_dmabuf_query.o \ +hyper_dmabuf_event.o \ ifeq ($(CONFIG_HYPER_DMABUF_XEN), y) $(TARGET_MODULE)-objs += backends/xen/hyper_dmabuf_xen_comm.o \ diff --git a/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c b/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c index 3320f9dcc769..087f091ccae9 100644 --- a/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c +++ b/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c @@ -41,6 +41,7 @@ #include "hyper_dmabuf_ioctl.h" #include "hyper_dmabuf_list.h" #include "hyper_dmabuf_id.h" +#include "hyper_dmabuf_event.h" #ifdef CONFIG_HYPER_DMABUF_XEN #include "backends/xen/hyper_dmabuf_xen_drv.h" @@ -91,10 +92,138 @@ static int hyper_dmabuf_release(struct inode *inode, struct file *filp) return 0; } +#ifdef CONFIG_HYPER_DMABUF_EVENT_GEN + +static unsigned int hyper_dmabuf_event_poll(struct file *filp, +struct poll_table_struct *wait) +{ + poll_wait(filp, _drv_priv->event_wait, wait); + + if (!list_empty(_drv_priv->event_list)) + return POLLIN | POLLRDNORM; + + return 0; +} + +static ssize_t hyper_dmabuf_event_read(struct file *filp, char __user *buffer, + size_t count, loff_t *offset) +{ + int ret; + + /* only root can read events */ + if (!capable(CAP_DAC_OVERRIDE)) { + dev_err(hy_drv_priv->dev, + "Only root can read events\n"); + return -EPERM; + } + + /* make sure user buffer can be written */ + if (!access_ok(VERIFY_WRITE, buffer, count)) { + dev_err(hy_drv_priv->dev, + "User buffer can't be
[RFC PATCH v2 8/9] hyper_dmabuf: event-polling mechanism for detecting a new hyper_DMABUF
New method based on polling for a importing VM to know about a new hyper_DMABUF exported to it. For this, the userspace now can poll the device node to check if there a new event, which is created if there's a new hyper_DMABUF available in importing VM (just exported). A poll function call was added to the device driver interface for this new functionality. Event-generation functionalitywas also implemented in all other relavant parts of driver. This "event-polling" mechanism is optional feature and can be enabled by setting a Kernel config option, "HYPER_DMABUF_EVENT_GEN". Signed-off-by: Dongwon Kim Signed-off-by: Mateusz Polrola --- drivers/dma-buf/hyper_dmabuf/Kconfig | 20 +++ drivers/dma-buf/hyper_dmabuf/Makefile | 1 + drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c | 146 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.h | 11 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.c | 122 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.h | 38 ++ drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_list.c | 1 + drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_msg.c | 11 ++ include/uapi/linux/hyper_dmabuf.h | 11 ++ 9 files changed, 361 insertions(+) create mode 100644 drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.c create mode 100644 drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_event.h diff --git a/drivers/dma-buf/hyper_dmabuf/Kconfig b/drivers/dma-buf/hyper_dmabuf/Kconfig index 68f3d6ce2c1f..92510731af25 100644 --- a/drivers/dma-buf/hyper_dmabuf/Kconfig +++ b/drivers/dma-buf/hyper_dmabuf/Kconfig @@ -20,6 +20,16 @@ config HYPER_DMABUF_SYSFS The location of sysfs is under "" +config HYPER_DMABUF_EVENT_GEN +bool "Enable event-generation and polling operation" +default n +depends on HYPER_DMABUF +help + With this config enabled, hyper_dmabuf driver on the importer side + generates events and queue those up in the event list whenever a new + shared DMA-BUF is available. Events in the list can be retrieved by + read operation. + config HYPER_DMABUF_XEN bool "Configure hyper_dmabuf for XEN hypervisor" default y @@ -27,4 +37,14 @@ config HYPER_DMABUF_XEN help Enabling Hyper_DMABUF Backend for XEN hypervisor +config HYPER_DMABUF_XEN_AUTO_RX_CH_ADD +bool "Enable automatic rx-ch add with 10 secs interval" +default y +depends on HYPER_DMABUF && HYPER_DMABUF_XEN +help + If enabled, driver reads a node in xenstore every 10 seconds + to check whether there is any tx comm ch configured by another + domain then initialize matched rx comm ch automatically for any + existing tx comm chs. + endmenu diff --git a/drivers/dma-buf/hyper_dmabuf/Makefile b/drivers/dma-buf/hyper_dmabuf/Makefile index 578a669a0d3e..f573dd5c4054 100644 --- a/drivers/dma-buf/hyper_dmabuf/Makefile +++ b/drivers/dma-buf/hyper_dmabuf/Makefile @@ -11,6 +11,7 @@ ifneq ($(KERNELRELEASE),) hyper_dmabuf_id.o \ hyper_dmabuf_remote_sync.o \ hyper_dmabuf_query.o \ +hyper_dmabuf_event.o \ ifeq ($(CONFIG_HYPER_DMABUF_XEN), y) $(TARGET_MODULE)-objs += backends/xen/hyper_dmabuf_xen_comm.o \ diff --git a/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c b/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c index 3320f9dcc769..087f091ccae9 100644 --- a/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c +++ b/drivers/dma-buf/hyper_dmabuf/hyper_dmabuf_drv.c @@ -41,6 +41,7 @@ #include "hyper_dmabuf_ioctl.h" #include "hyper_dmabuf_list.h" #include "hyper_dmabuf_id.h" +#include "hyper_dmabuf_event.h" #ifdef CONFIG_HYPER_DMABUF_XEN #include "backends/xen/hyper_dmabuf_xen_drv.h" @@ -91,10 +92,138 @@ static int hyper_dmabuf_release(struct inode *inode, struct file *filp) return 0; } +#ifdef CONFIG_HYPER_DMABUF_EVENT_GEN + +static unsigned int hyper_dmabuf_event_poll(struct file *filp, +struct poll_table_struct *wait) +{ + poll_wait(filp, _drv_priv->event_wait, wait); + + if (!list_empty(_drv_priv->event_list)) + return POLLIN | POLLRDNORM; + + return 0; +} + +static ssize_t hyper_dmabuf_event_read(struct file *filp, char __user *buffer, + size_t count, loff_t *offset) +{ + int ret; + + /* only root can read events */ + if (!capable(CAP_DAC_OVERRIDE)) { + dev_err(hy_drv_priv->dev, + "Only root can read events\n"); + return -EPERM; + } + + /* make sure user buffer can be written */ + if (!access_ok(VERIFY_WRITE, buffer, count)) { + dev_err(hy_drv_priv->dev, + "User buffer can't be written.\n"); + return -EINVAL; + }