You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nuttx.apache.org by xi...@apache.org on 2023/01/10 05:33:19 UTC
[nuttx] branch master updated: drivers/pipe:add PIPEIOC_POLLTHRES to set POLLIN/POLLOUT threshold
This is an automated email from the ASF dual-hosted git repository.
xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git
The following commit(s) were added to refs/heads/master by this push:
new 587305723e drivers/pipe:add PIPEIOC_POLLTHRES to set POLLIN/POLLOUT threshold
587305723e is described below
commit 587305723e85f1dd9aeb6d1aadafb60efc559a90
Author: 田昕 <ti...@xiaomi.com>
AuthorDate: Fri Jan 6 20:51:14 2023 +0800
drivers/pipe:add PIPEIOC_POLLTHRES to set POLLIN/POLLOUT threshold
Signed-off-by: 田昕 <ti...@xiaomi.com>
---
drivers/pipes/pipe_common.c | 84 ++++++++++++++++++++++++++++++++++++---------
drivers/pipes/pipe_common.h | 2 ++
include/nuttx/fs/ioctl.h | 36 ++++++++++++++-----
3 files changed, 97 insertions(+), 25 deletions(-)
diff --git a/drivers/pipes/pipe_common.c b/drivers/pipes/pipe_common.c
index 1ab3ea427c..d68896dd1f 100644
--- a/drivers/pipes/pipe_common.c
+++ b/drivers/pipes/pipe_common.c
@@ -60,6 +60,26 @@
# define pipe_dumpbuffer(m,a,n)
#endif
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: pipecommon_bufferused
+ ****************************************************************************/
+
+static pipe_ndx_t pipecommon_bufferused(FAR struct pipe_dev_s *dev)
+{
+ if (dev->d_wrndx >= dev->d_rdndx)
+ {
+ return dev->d_wrndx - dev->d_rdndx;
+ }
+ else
+ {
+ return dev->d_bufsize + dev->d_wrndx - dev->d_rdndx;
+ }
+}
+
/****************************************************************************
* Public Functions
****************************************************************************/
@@ -417,9 +437,14 @@ ssize_t pipecommon_read(FAR struct file *filep, FAR char *buffer, size_t len)
nread++;
}
- /* Notify all poll/select waiters that they can write to the FIFO */
+ /* Notify all poll/select waiters that they can write to the
+ * FIFO when buffer can accept more than d_polloutthrd bytes.
+ */
- poll_notify(dev->d_fds, CONFIG_DEV_PIPE_NPOLLWAITERS, POLLOUT);
+ if (pipecommon_bufferused(dev) < (dev->d_bufsize - dev->d_polloutthrd))
+ {
+ poll_notify(dev->d_fds, CONFIG_DEV_PIPE_NPOLLWAITERS, POLLOUT);
+ }
/* Notify all waiting writers that bytes have been removed from the
* buffer.
@@ -527,10 +552,14 @@ ssize_t pipecommon_write(FAR struct file *filep, FAR const char *buffer,
if ((size_t)nwritten >= len)
{
/* Notify all poll/select waiters that they can read from the
- * FIFO.
+ * FIFO when buffer used exceeds poll threshold.
*/
- poll_notify(dev->d_fds, CONFIG_DEV_PIPE_NPOLLWAITERS, POLLIN);
+ if (pipecommon_bufferused(dev) > dev->d_pollinthrd)
+ {
+ poll_notify(dev->d_fds, CONFIG_DEV_PIPE_NPOLLWAITERS,
+ POLLIN);
+ }
/* Yes.. Notify all of the waiting readers that more data is
* available.
@@ -661,28 +690,23 @@ int pipecommon_poll(FAR struct file *filep, FAR struct pollfd *fds,
* First, determine how many bytes are in the buffer
*/
- if (dev->d_wrndx >= dev->d_rdndx)
- {
- nbytes = dev->d_wrndx - dev->d_rdndx;
- }
- else
- {
- nbytes = dev->d_bufsize + dev->d_wrndx - dev->d_rdndx;
- }
+ nbytes = pipecommon_bufferused(dev);
- /* Notify the POLLOUT event if the pipe is not full, but only if
+ /* Notify the POLLOUT event if the pipe buffer can accept
+ * more than d_polloutthrd bytes, but only if
* there is readers.
*/
eventset = 0;
- if ((filep->f_oflags & O_WROK) && (nbytes < (dev->d_bufsize - 1)))
+ if ((filep->f_oflags & O_WROK) &&
+ nbytes < (dev->d_bufsize - dev->d_polloutthrd))
{
eventset |= POLLOUT;
}
- /* Notify the POLLIN event if the pipe is not empty */
+ /* Notify the POLLIN event if buffer used exceeds poll threshold */
- if ((filep->f_oflags & O_RDOK) && (nbytes > 0))
+ if ((filep->f_oflags & O_RDOK) && (nbytes > dev->d_pollinthrd))
{
eventset |= POLLIN;
}
@@ -772,6 +796,34 @@ int pipecommon_ioctl(FAR struct file *filep, int cmd, unsigned long arg)
}
break;
+ case PIPEIOC_POLLINTHRD:
+ {
+ pipe_ndx_t threshold = (pipe_ndx_t)arg;
+ if (threshold >= dev->d_bufsize)
+ {
+ ret = -EINVAL;
+ break;
+ }
+
+ dev->d_pollinthrd = threshold;
+ ret = OK;
+ }
+ break;
+
+ case PIPEIOC_POLLOUTTHRD:
+ {
+ pipe_ndx_t threshold = (pipe_ndx_t)arg;
+ if (threshold >= dev->d_bufsize)
+ {
+ ret = -EINVAL;
+ break;
+ }
+
+ dev->d_polloutthrd = threshold;
+ ret = OK;
+ }
+ break;
+
case FIONWRITE: /* Number of bytes waiting in send queue */
case FIONREAD: /* Number of bytes available for reading */
{
diff --git a/drivers/pipes/pipe_common.h b/drivers/pipes/pipe_common.h
index ff579e81f6..eec1bac119 100644
--- a/drivers/pipes/pipe_common.h
+++ b/drivers/pipes/pipe_common.h
@@ -120,6 +120,8 @@ struct pipe_dev_s
pipe_ndx_t d_wrndx; /* Index in d_buffer to save next byte written */
pipe_ndx_t d_rdndx; /* Index in d_buffer to return the next byte read */
pipe_ndx_t d_bufsize; /* allocated size of d_buffer in bytes */
+ pipe_ndx_t d_pollinthrd; /* Buffer threshold for POLLIN to occur */
+ pipe_ndx_t d_polloutthrd; /* Buffer threshold for POLLOUT to occur */
uint8_t d_nwriters; /* Number of reference counts for write access */
uint8_t d_nreaders; /* Number of reference counts for read access */
uint8_t d_flags; /* See PIPE_FLAG_* definitions */
diff --git a/include/nuttx/fs/ioctl.h b/include/nuttx/fs/ioctl.h
index a231e85f82..12e52900ac 100644
--- a/include/nuttx/fs/ioctl.h
+++ b/include/nuttx/fs/ioctl.h
@@ -405,15 +405,33 @@
/* FIFOs and pipe driver ioctl definitions **********************************/
-#define _PIPEIOCVALID(c) (_IOC_TYPE(c)==_PIPEBASE)
-#define _PIPEIOC(nr) _IOC(_PIPEBASE,nr)
-
-#define PIPEIOC_POLICY _PIPEIOC(0x0001) /* Set buffer policy
- * IN: unsigned long integer
- * 0=free on last close
- * (default)
- * 1=fre when empty
- * OUT: None */
+#define _PIPEIOCVALID(c) (_IOC_TYPE(c)==_PIPEBASE)
+#define _PIPEIOC(nr) _IOC(_PIPEBASE,nr)
+
+#define PIPEIOC_POLICY _PIPEIOC(0x0001) /* Set buffer policy
+ * IN: unsigned long integer
+ * 0=free on last close
+ * (default)
+ * 1=fre when empty
+ * OUT: None */
+
+#define PIPEIOC_POLLINTHRD _PIPEIOC(0x0002) /* Set pipe POLLIN
+ * notifty buffer threshold.
+ * IN: unsigned long integer.
+ * POLLIN only occurs when
+ * buffer contains more
+ * bytes than the
+ * threshold.
+ * OUT: None */
+
+#define PIPEIOC_POLLOUTTHRD _PIPEIOC(0x0003) /* Set pipe POLLOUT
+ * notifty buffer threshold.
+ * IN: unsigned long integer.
+ * POLLOUT only occurs
+ * when buffer can accept
+ * more bytes than
+ * threshold.
+ * OUT: None */
/* RTC driver ioctl definitions *********************************************/