Esempio n. 1
0
int pthread_cond_timedwait(
  pthread_cond_t        *cond,
  pthread_mutex_t       *mutex,
  const struct timespec *abstime
)
{
  Watchdog_Interval                            ticks;
  bool                                         already_timedout;
  POSIX_Absolute_timeout_conversion_results_t  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 = _POSIX_Absolute_timeout_to_ticks(abstime, &ticks);
  if ( status == POSIX_ABSOLUTE_TIMEOUT_INVALID )
    return EINVAL;

  if ( status == POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST ||
       status == POSIX_ABSOLUTE_TIMEOUT_IS_NOW )
    already_timedout = true;

  return _POSIX_Condition_variables_Wait_support(
    cond,
    mutex,
    ticks,
    already_timedout
  );
}
Esempio n. 2
0
int sem_timedwait(
  sem_t                 *sem,
  const struct timespec *abstime
)
{
  Watchdog_Interval                            ticks;
  bool                                         do_wait = true;
  POSIX_Absolute_timeout_conversion_results_t  status;
  int                                          lock_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.
   *
   *  If the status is POSIX_ABSOLUTE_TIMEOUT_INVALID,
   *  POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST, or POSIX_ABSOLUTE_TIMEOUT_IS_NOW,
   *  then we should not wait.
   */
  status = _POSIX_Absolute_timeout_to_ticks( abstime, &ticks );
  if ( status != POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE )
    do_wait = false;

  lock_status = _POSIX_Semaphore_Wait_support( sem, do_wait, ticks );

  /*
   *  This service only gives us the option to block.  We used a polling
   *  attempt to obtain if the abstime was not in the future.  If we did
   *  not obtain the semaphore, then not look at the status immediately,
   *  make sure the right reason is returned.
   */
  if ( !do_wait && (lock_status == EBUSY) ) {
    switch (lock_status) {
      case POSIX_ABSOLUTE_TIMEOUT_INVALID:
        rtems_set_errno_and_return_minus_one( EINVAL );
      case POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST:
      case POSIX_ABSOLUTE_TIMEOUT_IS_NOW:
        rtems_set_errno_and_return_minus_one( ETIMEDOUT );
      case POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE:
        break;
    }
  }

  return lock_status;
}
Esempio n. 3
0
int pthread_mutex_timedlock(
  pthread_mutex_t       *mutex,
  const struct timespec *abstime
)
{
  Watchdog_Interval                            ticks;
  bool                                         do_wait = true;
  POSIX_Absolute_timeout_conversion_results_t  status;
  int                                          lock_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.
   *
   *  If the status is POSIX_ABSOLUTE_TIMEOUT_INVALID,
   *  POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST, or POSIX_ABSOLUTE_TIMEOUT_IS_NOW,
   *  then we should not wait.
   */
  status = _POSIX_Absolute_timeout_to_ticks( abstime, &ticks );
  if ( status != POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE )
    do_wait = false;

  lock_status = _POSIX_Mutex_Lock_support( mutex, do_wait, ticks );
  /*
   *  This service only gives us the option to block.  We used a polling
   *  attempt to lock if the abstime was not in the future.  If we did
   *  not obtain the mutex, then not look at the status immediately,
   *  make sure the right reason is returned.
   */
  if ( !do_wait && (lock_status == EBUSY) ) {
    if ( status == POSIX_ABSOLUTE_TIMEOUT_INVALID )
      return EINVAL;
    if ( status == POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST ||
         status == POSIX_ABSOLUTE_TIMEOUT_IS_NOW )
      return ETIMEDOUT;
  }

  return lock_status;
}
Esempio n. 4
0
ssize_t mq_timedreceive(
  mqd_t                  mqdes,
  char                  *msg_ptr,
  size_t                 msg_len,
  unsigned int          *msg_prio,
  const struct timespec *abstime
)
{
  Watchdog_Interval                            ticks;
  bool                                         do_wait = true;
  POSIX_Absolute_timeout_conversion_results_t  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.
   *
   *  If the status is POSIX_ABSOLUTE_TIMEOUT_INVALID,
   *  POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST, or POSIX_ABSOLUTE_TIMEOUT_IS_NOW,
   *  then we should not wait.
   */
  status = _POSIX_Absolute_timeout_to_ticks( abstime, &ticks );
  if ( status != POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE )
    do_wait = false;

  return _POSIX_Message_queue_Receive_support(
    mqdes,
    msg_ptr,
    msg_len,
    msg_prio,
    do_wait,
    ticks
  );
}
Esempio n. 5
0
int pthread_rwlock_timedwrlock(
  pthread_rwlock_t      *rwlock,
  const struct timespec *abstime
)
{
  POSIX_RWLock_Control                        *the_rwlock;
  Objects_Locations                            location;
  Watchdog_Interval                            ticks;
  bool                                         do_wait = true;
  POSIX_Absolute_timeout_conversion_results_t  status;

  if ( !rwlock )
    return EINVAL;

  /*
   *  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.
   *
   *  If the status is POSIX_ABSOLUTE_TIMEOUT_INVALID,
   *  POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST, or POSIX_ABSOLUTE_TIMEOUT_IS_NOW,
   *  then we should not wait.
   */
  status = _POSIX_Absolute_timeout_to_ticks( abstime, &ticks );
  if ( status != POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE )
    do_wait = false;

  the_rwlock = _POSIX_RWLock_Get( rwlock, &location );
  switch ( location ) {

    case OBJECTS_LOCAL:

      _CORE_RWLock_Obtain_for_writing(
	&the_rwlock->RWLock,
	*rwlock,
	do_wait,
	ticks,
	NULL
      );

      _Thread_Enable_dispatch();
      if ( !do_wait &&
           (_Thread_Executing->Wait.return_code == CORE_RWLOCK_UNAVAILABLE) ) {
	if ( status == POSIX_ABSOLUTE_TIMEOUT_INVALID )
	  return EINVAL;
	if ( status == POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST ||
	     status == POSIX_ABSOLUTE_TIMEOUT_IS_NOW )
	  return ETIMEDOUT;
      }

      return _POSIX_RWLock_Translate_core_RWLock_return_code(
        (CORE_RWLock_Status) _Thread_Executing->Wait.return_code
      );

#if defined(RTEMS_MULTIPROCESSING)
    case OBJECTS_REMOTE:
#endif
    case OBJECTS_ERROR:
      break;
  }

  return EINVAL;
}
Esempio n. 6
0
  int                                          lock_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.
   *
   *  If the status is POSIX_ABSOLUTE_TIMEOUT_INVALID,
   *  POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST, or POSIX_ABSOLUTE_TIMEOUT_IS_NOW,
   *  then we should not wait.
   */
  status = _POSIX_Absolute_timeout_to_ticks( abstime, &ticks );
  if ( status != POSIX_ABSOLUTE_TIMEOUT_IS_IN_FUTURE )
    do_wait = false;

  lock_status = _POSIX_Semaphore_Wait_support( sem, do_wait, ticks );

  /*
   *  This service only gives us the option to block.  We used a polling
   *  attempt to obtain if the abstime was not in the future.  If we did
   *  not obtain the semaphore, then not look at the status immediately,
   *  make sure the right reason is returned.
   */
  if ( !do_wait && (lock_status == EBUSY) ) {
    if ( lock_status == POSIX_ABSOLUTE_TIMEOUT_INVALID )
      rtems_set_errno_and_return_minus_one( EINVAL );
    if ( lock_status == POSIX_ABSOLUTE_TIMEOUT_IS_IN_PAST ||