- /* gettimeofday() cannot fail given &tv_date is a valid address */
- (void)gettimeofday( &tv_date, NULL );
- return( (mtime_t) tv_date.tv_sec * 1000000 + (mtime_t) tv_date.tv_usec );
-#endif
-}
-
-/**
- * Wait for a date
- *
- * This function uses select() and an system date function to wake up at a
- * precise date. It should be used for process synchronization. If current date
- * is posterior to wished date, the function returns immediately.
- * \param date The date to wake up at
- */
-void mwait( mtime_t date )
-{
-#if defined( HAVE_KERNEL_OS_H )
- mtime_t delay;
-
- delay = date - real_time_clock_usecs();
- if( delay <= 0 )
- {
- return;
- }
- snooze( delay );
-
-#elif defined( WIN32 ) || defined( UNDER_CE )
- mtime_t usec_time, delay;
-
- usec_time = mdate();
- delay = date - usec_time;
- if( delay <= 0 )
- {
- return;
- }
- msleep( delay );
-
-#elif defined (HAVE_CLOCK_NANOSLEEP)
-# if defined (HAVE_TIMER_ABSTIME_THAT_ACTUALLY_WORKS_WELL)
- lldiv_t d = lldiv( date, 1000000 );
- struct timespec ts = { d.quot, d.rem };
-
-# if (_POSIX_MONOTONIC_CLOCK - 0 >= 0)
- if( clock_nanosleep( CLOCK_MONOTONIC, TIMER_ABSTIME, &ts, NULL ) )
-# endif
- clock_nanosleep( CLOCK_REALTIME, TIMER_ABSTIME, &ts, NULL );
-# else
- date -= mdate ();
- if( date <= 0)
- return;
- msleep( date );
-# endif
-#else
-
- struct timeval tv_date;
- mtime_t delay; /* delay in msec, signed to detect errors */
-
- /* see mdate() about gettimeofday() possible errors */
- gettimeofday( &tv_date, NULL );
-
- /* calculate delay and check if current date is before wished date */
- delay = date - (mtime_t) tv_date.tv_sec * 1000000
- - (mtime_t) tv_date.tv_usec
- - 10000;
-
- /* Linux/i386 has a granularity of 10 ms. It's better to be in advance
- * than to be late. */
- if( delay <= 0 ) /* wished date is now or already passed */
- {
- return;
- }
-
-# if defined( PTH_INIT_IN_PTH_H )
- pth_usleep( delay );
-
-# elif defined( ST_INIT_IN_ST_H )
- st_usleep( delay );
-
-# else
-
-# if defined( HAVE_NANOSLEEP )
- {
- struct timespec ts_delay;
- ts_delay.tv_sec = delay / 1000000;
- ts_delay.tv_nsec = (delay % 1000000) * 1000;
-
- nanosleep( &ts_delay, NULL );
- }
-
-# else
- tv_date.tv_sec = delay / 1000000;
- tv_date.tv_usec = delay % 1000000;
- /* see msleep() about select() errors */
- select( 0, NULL, NULL, NULL, &tv_date );
-# endif
-
-# endif
-
-#endif
-}
-
-/**
- * More precise sleep()
- *
- * Portable usleep() function.
- * \param delay the amount of time to sleep
- */
-void msleep( mtime_t delay )
-{
-#if defined( HAVE_KERNEL_OS_H )
- snooze( delay );
-
-#elif defined( PTH_INIT_IN_PTH_H )
- pth_usleep( delay );
-
-#elif defined( ST_INIT_IN_ST_H )
- st_usleep( delay );
-
-#elif defined( WIN32 ) || defined( UNDER_CE )
- Sleep( (int) (delay / 1000) );
-
-#elif defined( HAVE_CLOCK_NANOSLEEP )
- lldiv_t d = lldiv( delay, 1000000 );
- struct timespec ts = { d.quot, d.rem * 1000 };
-
-# if (_POSIX_MONOTONIC_CLOCK - 0 >= 0)
- if( clock_nanosleep( CLOCK_MONOTONIC, 0, &ts, NULL ) )
-# endif
- clock_nanosleep( CLOCK_REALTIME, 0, &ts, NULL );
-
-#elif defined( HAVE_NANOSLEEP )
- struct timespec ts_delay;
-
- ts_delay.tv_sec = delay / 1000000;
- ts_delay.tv_nsec = (delay % 1000000) * 1000;
-
- nanosleep( &ts_delay, NULL );
-
-#else
- struct timeval tv_delay;
-
- tv_delay.tv_sec = delay / 1000000;
- tv_delay.tv_usec = delay % 1000000;
-
- /* select() return value should be tested, since several possible errors
- * can occur. However, they should only happen in very particular occasions
- * (i.e. when a signal is sent to the thread, or when memory is full), and
- * can be ignored. */
- select( 0, NULL, NULL, NULL, &tv_delay );
-
-#endif