[PATCH 4/5] posix: refactor cond wait support to defer abstime conversion

Gedare Bloom gedare at rtems.org
Wed Jul 13 17:39:49 UTC 2016


updates #2745
---
 cpukit/posix/include/rtems/posix/condimpl.h |  3 +--
 cpukit/posix/src/condtimedwait.c            | 25 +--------------------
 cpukit/posix/src/condwait.c                 |  3 +--
 cpukit/posix/src/condwaitsupp.c             | 34 +++++++++++++++++++++++++----
 4 files changed, 33 insertions(+), 32 deletions(-)

diff --git a/cpukit/posix/include/rtems/posix/condimpl.h b/cpukit/posix/include/rtems/posix/condimpl.h
index 736f06b..dbeb6e1 100644
--- a/cpukit/posix/include/rtems/posix/condimpl.h
+++ b/cpukit/posix/include/rtems/posix/condimpl.h
@@ -134,8 +134,7 @@ int _POSIX_Condition_variables_Signal_support(
 int _POSIX_Condition_variables_Wait_support(
   pthread_cond_t            *cond,
   pthread_mutex_t           *mutex,
-  Watchdog_Interval          timeout,
-  bool                       already_timedout
+  const struct timespec     *abstime
 );
 
 #ifdef __cplusplus
diff --git a/cpukit/posix/src/condtimedwait.c b/cpukit/posix/src/condtimedwait.c
index 1a2f5ff..6c0b14f 100644
--- a/cpukit/posix/src/condtimedwait.c
+++ b/cpukit/posix/src/condtimedwait.c
@@ -31,32 +31,9 @@ int pthread_cond_timedwait(
   const struct timespec *abstime
 )
 {
-  Watchdog_Interval                            ticks;
-  bool                                         already_timedout;
-  TOD_Absolute_timeout_conversion_results  status;
-
-  /*
-   *  POSIX requires that blocking calls with timeouts that take
-   *  an absolute timeout must ignore issues with the absolute
-   *  time provided if the operation would otherwise succeed.
-   *  So we check the abstime provided, and hold on to whether it
-   *  is valid or not.  If it isn't correct and in the future,
-   *  then we do a polling operation and convert the UNSATISFIED
-   *  status into the appropriate error.
-   */
-  already_timedout = false;
-  status = _TOD_Absolute_timeout_to_ticks(abstime, &ticks);
-  if ( status == TOD_ABSOLUTE_TIMEOUT_INVALID )
-    return EINVAL;
-
-  if ( status == TOD_ABSOLUTE_TIMEOUT_IS_IN_PAST ||
-       status == TOD_ABSOLUTE_TIMEOUT_IS_NOW )
-    already_timedout = true;
-
   return _POSIX_Condition_variables_Wait_support(
     cond,
     mutex,
-    ticks,
-    already_timedout
+    abstime
   );
 }
diff --git a/cpukit/posix/src/condwait.c b/cpukit/posix/src/condwait.c
index 22004f8..9a88287 100644
--- a/cpukit/posix/src/condwait.c
+++ b/cpukit/posix/src/condwait.c
@@ -32,7 +32,6 @@ int pthread_cond_wait(
   return _POSIX_Condition_variables_Wait_support(
     cond,
     mutex,
-    WATCHDOG_NO_TIMEOUT,
-    false
+    NULL
   );
 }
diff --git a/cpukit/posix/src/condwaitsupp.c b/cpukit/posix/src/condwaitsupp.c
index b2ed367..caa3a9a 100644
--- a/cpukit/posix/src/condwaitsupp.c
+++ b/cpukit/posix/src/condwaitsupp.c
@@ -30,8 +30,7 @@ THREAD_QUEUE_OBJECT_ASSERT( POSIX_Condition_variables_Control, Wait_queue );
 int _POSIX_Condition_variables_Wait_support(
   pthread_cond_t            *cond,
   pthread_mutex_t           *mutex,
-  Watchdog_Interval          timeout,
-  bool                       already_timedout
+  const struct timespec     *abstime
 )
 {
   POSIX_Condition_variables_Control *the_cond;
@@ -40,6 +39,9 @@ int _POSIX_Condition_variables_Wait_support(
   int                                mutex_error;
   Per_CPU_Control                   *cpu_self;
   Thread_Control                    *executing;
+  Watchdog_Interval                  timeout;
+  bool                               already_timedout;
+  TOD_Absolute_timeout_conversion_results  status;
 
   if ( mutex == NULL ) {
     return EINVAL;
@@ -51,6 +53,32 @@ int _POSIX_Condition_variables_Wait_support(
     return EINVAL;
   }
 
+  already_timedout = false;
+
+  if ( abstime != NULL ) {
+    /*
+     *  POSIX requires that blocking calls with timeouts that take
+     *  an absolute timeout must ignore issues with the absolute
+     *  time provided if the operation would otherwise succeed.
+     *  So we check the abstime provided, and hold on to whether it
+     *  is valid or not.  If it isn't correct and in the future,
+     *  then we do a polling operation and convert the UNSATISFIED
+     *  status into the appropriate error.
+     */
+    status = _TOD_Absolute_timeout_to_ticks( abstime, &timeout );
+    if ( status == TOD_ABSOLUTE_TIMEOUT_INVALID )
+      return EINVAL;
+
+    if ( status == TOD_ABSOLUTE_TIMEOUT_IS_IN_PAST ||
+        status == TOD_ABSOLUTE_TIMEOUT_IS_NOW ) {
+      already_timedout = true;
+    } else {
+      _Thread_queue_Context_set_relative_timeout( &queue_context, timeout );
+    }
+  } else {
+    _Thread_queue_Context_set_no_timeout( &queue_context );
+  }
+
   _POSIX_Condition_variables_Acquire_critical( the_cond, &queue_context );
 
   if (
@@ -68,8 +96,6 @@ int _POSIX_Condition_variables_Wait_support(
 
   if ( !already_timedout ) {
     _Thread_queue_Context_set_expected_level( &queue_context, 2 );
-    _Thread_queue_Context_set_timeout( &queue_context, timeout );
-    _Thread_queue_Context_set_discipline( &queue_context, WATCHDOG_RELATIVE );
     _Thread_queue_Enqueue_critical(
       &the_cond->Wait_queue.Queue,
       POSIX_CONDITION_VARIABLES_TQ_OPERATIONS,
-- 
1.9.1




More information about the devel mailing list