errno = EAGAIN;
__set_errno (EAGAIN);
timer_create (clock_id, evp, timerid)     clockid_t clock_id;     struct sigevent *evp;     timer_t *timerid;{  int retval = -1;  struct timer_node *newtimer = NULL;  struct thread_node *thread = NULL;  if (clock_id != CLOCK_REALTIME#ifdef _POSIX_CPUTIME      && clock_id != CLOCK_PROCESS_CPUTIME_ID#endif#ifdef _POSIX_THREAD_CPUTIME      && clock_id != CLOCK_THREAD_CPUTIME_ID#endif      )    {      errno = EINVAL;      return -1;    }  pthread_once (&__timer_init_once_control, __timer_init_once);  if (__timer_init_failed)    {      errno = ENOMEM;      return -1;    }  pthread_mutex_lock (&__timer_mutex);  newtimer = __timer_alloc ();  if (__builtin_expect (newtimer == NULL, 0))    {      errno = EAGAIN;      goto unlock_bail;    }  if (evp != NULL)    newtimer->event = *evp;  else    {      newtimer->event.sigev_notify = SIGEV_SIGNAL;      newtimer->event.sigev_signo = SIGALRM;      newtimer->event.sigev_value.sival_int = timer_ptr2id (newtimer);      newtimer->event.sigev_notify_function = 0;    }  newtimer->event.sigev_notify_attributes = &newtimer->attr;  newtimer->creator_pid = getpid ();  switch (__builtin_expect (newtimer->event.sigev_notify, SIGEV_SIGNAL))    {    case SIGEV_NONE:      /* This is a strange choice!  */      break;    case SIGEV_SIGNAL:      /* We have a global thread for delivering timed signals.	 If it is not running, try to start it up.  */      switch (clock_id)	{	case CLOCK_REALTIME:	default:	  thread = &__timer_signal_thread_rclk;	  break;#ifdef _POSIX_CPUTIME	case CLOCK_PROCESS_CPUTIME_ID:	  thread = &__timer_signal_thread_pclk;	  break;#endif#ifdef _POSIX_THREAD_CPUTIME	case CLOCK_THREAD_CPUTIME_ID:	  thread = &__timer_signal_thread_tclk;	  break;#endif	}            if (! thread->exists)	{	  if (__builtin_expect (__timer_thread_start (thread),				1) < 0)	    {	      errno = EAGAIN;	      goto unlock_bail;            }        }      break;    case SIGEV_THREAD:      /* Copy over thread attributes or set up default ones.  */      if (evp->sigev_notify_attributes)	newtimer->attr = *(pthread_attr_t *) evp->sigev_notify_attributes;      else	pthread_attr_init (&newtimer->attr);      /* Ensure thread attributes call for deatched thread.  */      pthread_attr_setdetachstate (&newtimer->attr, PTHREAD_CREATE_DETACHED);      /* Try to find existing thread having the right attributes.  */      thread = __timer_thread_find_matching (&newtimer->attr, clock_id);      /* If no existing thread has these attributes, try to allocate one.  */      if (thread == NULL)	thread = __timer_thread_alloc (&newtimer->attr, clock_id);      /* Out of luck; no threads are available.  */      if (__builtin_expect (thread == NULL, 0))	{	  errno = EAGAIN;	  goto unlock_bail;	}      /* If the thread is not running already, try to start it.  */      if (! thread->exists	  && __builtin_expect (! __timer_thread_start (thread), 0))	{	  errno = EAGAIN;	  goto unlock_bail;	}      break;    default:      errno = EINVAL;      goto unlock_bail;    }  newtimer->clock = clock_id;  newtimer->abstime = 0;  newtimer->armed = 0;  newtimer->thread = thread;  *timerid = timer_ptr2id (newtimer);  retval = 0;  if (__builtin_expect (retval, 0) == -1)    {    unlock_bail:      if (thread != NULL)	__timer_thread_dealloc (thread);      if (newtimer != NULL)	__timer_dealloc (newtimer);    }  pthread_mutex_unlock (&__timer_mutex);  return retval;}