Timer driver: Add hooks to support signal notification of timer expiration. Commented out because invasive interface changes would also be required to complete the implementation.
This commit is contained in:
parent
ecb2d4cbc1
commit
d4a048c0c6
@ -65,8 +65,13 @@
|
|||||||
|
|
||||||
struct timer_upperhalf_s
|
struct timer_upperhalf_s
|
||||||
{
|
{
|
||||||
uint8_t crefs; /* The number of times the device has been opened */
|
uint8_t crefs; /* The number of times the device has been opened */
|
||||||
FAR char *path; /* Registration path */
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
uint8_t signal; /* The signal number to use in the notification */
|
||||||
|
pid_t pid; /* The ID of the task/thread to receive the signal */
|
||||||
|
FAR void *arg; /* An argument to pass with the signal */
|
||||||
|
#endif
|
||||||
|
FAR char *path; /* Registration path */
|
||||||
|
|
||||||
/* The contained lower-half driver */
|
/* The contained lower-half driver */
|
||||||
|
|
||||||
@ -77,6 +82,12 @@ struct timer_upperhalf_s
|
|||||||
* Private Function Prototypes
|
* Private Function Prototypes
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
/* REVISIT: This function prototype is insufficient to support signaling */
|
||||||
|
|
||||||
|
static bool timer_notifier(FAR uint32_t *next_interval_us);
|
||||||
|
#endif
|
||||||
|
|
||||||
static int timer_open(FAR struct file *filep);
|
static int timer_open(FAR struct file *filep);
|
||||||
static int timer_close(FAR struct file *filep);
|
static int timer_close(FAR struct file *filep);
|
||||||
static ssize_t timer_read(FAR struct file *filep, FAR char *buffer,
|
static ssize_t timer_read(FAR struct file *filep, FAR char *buffer,
|
||||||
@ -110,6 +121,36 @@ static const struct file_operations g_timerops =
|
|||||||
* Private Functions
|
* Private Functions
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
|
/************************************************************************************
|
||||||
|
* Name: timer_notifier
|
||||||
|
*
|
||||||
|
* Description:
|
||||||
|
* Notify the application via a signal when the timer interrupt occurs
|
||||||
|
*
|
||||||
|
* REVISIT: This function prototype is insufficient to support signaling
|
||||||
|
*
|
||||||
|
************************************************************************************/
|
||||||
|
|
||||||
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
static bool timer_notifier(FAR uint32_t *next_interval_us)
|
||||||
|
{
|
||||||
|
FAR struct timer_upperhalf_s *upper = HOW?;
|
||||||
|
#ifdef CONFIG_CAN_PASS_STRUCTS
|
||||||
|
union sigval value;
|
||||||
|
#endif
|
||||||
|
int ret;
|
||||||
|
|
||||||
|
#ifdef CONFIG_CAN_PASS_STRUCTS
|
||||||
|
value.sival_ptr = upper->arg;
|
||||||
|
ret = sigqueue(upper->pid, upper->signo, value);
|
||||||
|
#else
|
||||||
|
ret = sigqueue(upper->pid, upper->signo, upper->arg);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return ret == OK;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/************************************************************************************
|
/************************************************************************************
|
||||||
* Name: timer_open
|
* Name: timer_open
|
||||||
*
|
*
|
||||||
@ -120,10 +161,10 @@ static const struct file_operations g_timerops =
|
|||||||
|
|
||||||
static int timer_open(FAR struct file *filep)
|
static int timer_open(FAR struct file *filep)
|
||||||
{
|
{
|
||||||
FAR struct inode *inode = filep->f_inode;
|
FAR struct inode *inode = filep->f_inode;
|
||||||
FAR struct timer_upperhalf_s *upper = inode->i_private;
|
FAR struct timer_upperhalf_s *upper = inode->i_private;
|
||||||
uint8_t tmp;
|
uint8_t tmp;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
tmrinfo("crefs: %d\n", upper->crefs);
|
tmrinfo("crefs: %d\n", upper->crefs);
|
||||||
|
|
||||||
@ -322,6 +363,36 @@ static int timer_ioctl(FAR struct file *filep, int cmd, unsigned long arg)
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
/* cmd: TCIOC_NOTIFICATION
|
||||||
|
* Description: Notify application via a signal when the timer expires.
|
||||||
|
* Argument: signal number
|
||||||
|
*
|
||||||
|
* NOTE: This ioctl cannot be support in the kernel build mode. In that
|
||||||
|
* case direct callbacks from kernel space into user space is forbidden.
|
||||||
|
*/
|
||||||
|
|
||||||
|
case TCIOC_NOTIFICATION:
|
||||||
|
{
|
||||||
|
FAR struct timer_notify_s *notify =
|
||||||
|
(FAR struct timer_notify_s *)((uintptr_t)arg)
|
||||||
|
|
||||||
|
if (notify != NULL)
|
||||||
|
{
|
||||||
|
upper->signo = notify->signal;
|
||||||
|
upper->get = notify->signal;
|
||||||
|
upper->arg = noify->arg;
|
||||||
|
|
||||||
|
ret = timer_sethandler((FAR void *handle)upper, timer_notifier, NULL);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ret = -EINVAL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Any unrecognized IOCTL commands might be platform-specific ioctl commands */
|
/* Any unrecognized IOCTL commands might be platform-specific ioctl commands */
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@ -500,7 +571,7 @@ int timer_sethandler(FAR void *handle, tccb_t newhandler,
|
|||||||
FAR struct timer_upperhalf_s *upper;
|
FAR struct timer_upperhalf_s *upper;
|
||||||
FAR struct timer_lowerhalf_s *lower;
|
FAR struct timer_lowerhalf_s *lower;
|
||||||
tccb_t tmphandler;
|
tccb_t tmphandler;
|
||||||
|
|
||||||
/* Recover the pointer to the upper-half driver state */
|
/* Recover the pointer to the upper-half driver state */
|
||||||
|
|
||||||
upper = (FAR struct timer_upperhalf_s *)handle;
|
upper = (FAR struct timer_upperhalf_s *)handle;
|
||||||
|
@ -52,6 +52,12 @@
|
|||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Pre-processor Definitions
|
* Pre-processor Definitions
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
/* It would require some interface modifcations in order to support
|
||||||
|
* notifications.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#undef HAVE_NOTIFICATION
|
||||||
|
|
||||||
/* IOCTL Commands ***********************************************************/
|
/* IOCTL Commands ***********************************************************/
|
||||||
/* The timer driver uses a standard character driver framework. However,
|
/* The timer driver uses a standard character driver framework. However,
|
||||||
* since the timer driver is a device control interface and not a data
|
* since the timer driver is a device control interface and not a data
|
||||||
@ -60,14 +66,18 @@
|
|||||||
*
|
*
|
||||||
* These are detected and handled by the "upper half" timer driver.
|
* These are detected and handled by the "upper half" timer driver.
|
||||||
*
|
*
|
||||||
* TCIOC_START - Start the timer
|
* TCIOC_START - Start the timer
|
||||||
* Argument: Ignored
|
* Argument: Ignored
|
||||||
* TCIOC_STOP - Stop the timer
|
* TCIOC_STOP - Stop the timer
|
||||||
* Argument: Ignored
|
* Argument: Ignored
|
||||||
* TCIOC_GETSTATUS - Get the status of the timer.
|
* TCIOC_GETSTATUS - Get the status of the timer.
|
||||||
* Argument: A writeable pointer to struct timer_status_s.
|
* Argument: A writeable pointer to struct timer_status_s.
|
||||||
* TCIOC_SETTIMEOUT - Reset the timer timeout to this value
|
* TCIOC_SETTIMEOUT - Reset the timer timeout to this value
|
||||||
* Argument: A 32-bit timeout value in microseconds.
|
* Argument: A 32-bit timeout value in microseconds.
|
||||||
|
* TCIOC_NOTIFICATION - Set up to notify an application via a signal when
|
||||||
|
* the timer expires.
|
||||||
|
* Argument: A read-only pointer to an instance of
|
||||||
|
* stuct timer_notify_s.
|
||||||
*
|
*
|
||||||
* WARNING: May change TCIOC_SETTIMEOUT to pass pointer to 64bit nanoseconds
|
* WARNING: May change TCIOC_SETTIMEOUT to pass pointer to 64bit nanoseconds
|
||||||
* or timespec structure.
|
* or timespec structure.
|
||||||
@ -82,18 +92,20 @@
|
|||||||
* range.
|
* range.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define TCIOC_START _TCIOC(0x0001)
|
#define TCIOC_START _TCIOC(0x0001)
|
||||||
#define TCIOC_STOP _TCIOC(0x0002)
|
#define TCIOC_STOP _TCIOC(0x0002)
|
||||||
#define TCIOC_GETSTATUS _TCIOC(0x0003)
|
#define TCIOC_GETSTATUS _TCIOC(0x0003)
|
||||||
#define TCIOC_SETTIMEOUT _TCIOC(0x0004)
|
#define TCIOC_SETTIMEOUT _TCIOC(0x0004)
|
||||||
#define TCIOC_SETHANDLER _TCIOC(0x0005)
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
#define TCIOC_NOTIFICATION _TCIOC(0x0005)
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Bit Settings *************************************************************/
|
/* Bit Settings *************************************************************/
|
||||||
/* Bit settings for the struct timer_status_s flags field */
|
/* Bit settings for the struct timer_status_s flags field */
|
||||||
|
|
||||||
#define TCFLAGS_ACTIVE (1 << 0) /* 1=The timer is running */
|
#define TCFLAGS_ACTIVE (1 << 0) /* 1=The timer is running */
|
||||||
#define TCFLAGS_HANDLER (1 << 1) /* 1=Call the user function when the
|
#define TCFLAGS_HANDLER (1 << 1) /* 1=Call the user function when the
|
||||||
* timer expires */
|
* timer expires */
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
* Public Types
|
* Public Types
|
||||||
@ -117,6 +129,17 @@ struct timer_status_s
|
|||||||
* (in microseconds) */
|
* (in microseconds) */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef HAVE_NOTIFICATION
|
||||||
|
/* This is the type of the argument passed to the TCIOC_NOTIFICATION ioctl */
|
||||||
|
|
||||||
|
struct timer_notify_s
|
||||||
|
{
|
||||||
|
FAR void *arg; /* An argument to pass with the signal */
|
||||||
|
pid_t pid; /* The ID of the task/thread to receive the signal */
|
||||||
|
uint8_t signal; /* The signal number to use in the notification */
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
/* This structure provides the "lower-half" driver operations available to
|
/* This structure provides the "lower-half" driver operations available to
|
||||||
* the "upper-half" driver.
|
* the "upper-half" driver.
|
||||||
*/
|
*/
|
||||||
|
Loading…
Reference in New Issue
Block a user