예제 #1
0
int arp_wait(FAR struct arp_notify_s *notify, FAR struct timespec *timeout)
{
  struct timespec abstime;
  irqstate_t flags;
  int errcode;
  int ret;

  /* And wait for the ARP response (or a timeout).  Interrupts will be re-
   * enabled while we wait.
   */

  flags = irqsave();
  DEBUGVERIFY(clock_gettime(CLOCK_REALTIME, &abstime));

  abstime.tv_sec  += timeout->tv_sec;
  abstime.tv_nsec += timeout->tv_nsec;
  if (abstime.tv_nsec >= 1000000000)
    {
      abstime.tv_sec++;
      abstime.tv_nsec -= 1000000000;
    }

  /* Wait to get either the correct response or a timeout. */

  do
    {
      /* The only errors that we expect would be if the abstime timeout
       * expires or if the wait were interrupted by a signal.
       */

      ret     = net_timedwait(&notify->nt_sem, &abstime);
      errcode = ((ret < 0) ? get_errno() : 0);
    }
  while (ret < 0 && errcode == EINTR);

  /* Then get the real result of the transfer */

  ret = notify->nt_result;

  /* Remove our wait structure from the list (we may no longer be at the
   * head of the list).
   */

  (void)arp_wait_cancel(notify);

  /* Re-enable interrupts and return the result of the wait */

  irqrestore(flags);
  return ret;
}
예제 #2
0
int icmpv6_rwait(FAR struct icmpv6_rnotify_s *notify,
                 FAR struct timespec *timeout)
{
  struct timespec abstime;
  irqstate_t flags;
  int ret;

  ninfo("Waiting...\n");

  /* And wait for the Neighbor Advertisement (or a timeout).  Interrupts will
   * be re-enabled while we wait.
   */

  flags = enter_critical_section();
  DEBUGVERIFY(clock_gettime(CLOCK_REALTIME, &abstime));

  abstime.tv_sec  += timeout->tv_sec;
  abstime.tv_nsec += timeout->tv_nsec;
  if (abstime.tv_nsec >= 1000000000)
    {
      abstime.tv_sec++;
      abstime.tv_nsec -= 1000000000;
    }

  /* REVISIT:  If net_timedwait() is awakened with  signal, we will return
   * the wrong error code.
   */

  (void)net_timedwait(&notify->rn_sem, &abstime);
  ret = notify->rn_result;

  /* Remove our wait structure from the list (we may no longer be at the
   * head of the list).
   */

  (void)icmpv6_rwait_cancel(notify);

  /* Re-enable interrupts and return the result of the wait */

  leave_critical_section(flags);
  return ret;
}