00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #include <stdio.h>
00034
00035 #include <vlc/vlc.h>
00036
00037 #if defined( PTH_INIT_IN_PTH_H )
00038 # include <pth.h>
00039 #endif
00040
00041 #ifdef HAVE_UNISTD_H
00042 # include <unistd.h>
00043 #endif
00044
00045 #ifdef HAVE_KERNEL_OS_H
00046 # include <kernel/OS.h>
00047 #endif
00048
00049 #if defined( WIN32 ) || defined( UNDER_CE )
00050 # include <windows.h>
00051 #else
00052 # include <sys/time.h>
00053 #endif
00054
00055 #if defined(HAVE_NANOSLEEP) && !defined(HAVE_STRUCT_TIMESPEC)
00056 struct timespec
00057 {
00058 time_t tv_sec;
00059 int32_t tv_nsec;
00060 };
00061 #endif
00062
00063 #if defined(HAVE_NANOSLEEP) && !defined(HAVE_DECL_NANOSLEEP)
00064 int nanosleep(struct timespec *, struct timespec *);
00065 #endif
00066
00077 char *mstrtime( char *psz_buffer, mtime_t date )
00078 {
00079 static mtime_t ll1000 = 1000, ll60 = 60, ll24 = 24;
00080
00081 snprintf( psz_buffer, MSTRTIME_MAX_SIZE, "%02d:%02d:%02d-%03d.%03d",
00082 (int) (date / (ll1000 * ll1000 * ll60 * ll60) % ll24),
00083 (int) (date / (ll1000 * ll1000 * ll60) % ll60),
00084 (int) (date / (ll1000 * ll1000) % ll60),
00085 (int) (date / ll1000 % ll1000),
00086 (int) (date % ll1000) );
00087 return( psz_buffer );
00088 }
00089
00100 char *secstotimestr( char *psz_buffer, int i_seconds )
00101 {
00102 snprintf( psz_buffer, MSTRTIME_MAX_SIZE, "%d:%2.2d:%2.2d",
00103 (int) (i_seconds / (60 *60)),
00104 (int) ((i_seconds / 60) % 60),
00105 (int) (i_seconds % 60) );
00106 return( psz_buffer );
00107 }
00108
00115 mtime_t mdate( void )
00116 {
00117 #if defined( HAVE_KERNEL_OS_H )
00118 return( real_time_clock_usecs() );
00119
00120 #elif defined( WIN32 ) || defined( UNDER_CE )
00121
00122 static mtime_t freq = I64C(-1);
00123 mtime_t usec_time;
00124
00125 if( freq == I64C(-1) )
00126 {
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146 freq = ( QueryPerformanceFrequency( (LARGE_INTEGER *)&freq ) &&
00147 (freq == I64C(1193182) || freq == I64C(3579545) ) )
00148 ? freq : 0;
00149 }
00150
00151 if( freq != 0 )
00152 {
00153
00154 QueryPerformanceCounter( (LARGE_INTEGER *)&usec_time );
00155 return ( usec_time * 1000000 ) / freq;
00156 }
00157 else
00158 {
00159
00160
00161
00162
00163
00164 static CRITICAL_SECTION date_lock;
00165 static mtime_t i_previous_time = I64C(-1);
00166 static int i_wrap_counts = -1;
00167
00168 if( i_wrap_counts == -1 )
00169 {
00170
00171 i_previous_time = I64C(1000) * GetTickCount();
00172 InitializeCriticalSection( &date_lock );
00173 i_wrap_counts = 0;
00174 }
00175
00176 EnterCriticalSection( &date_lock );
00177 usec_time = I64C(1000) *
00178 (i_wrap_counts * I64C(0x100000000) + GetTickCount());
00179 if( i_previous_time > usec_time )
00180 {
00181
00182 i_wrap_counts++;
00183 usec_time += I64C(0x100000000000);
00184 }
00185 i_previous_time = usec_time;
00186 LeaveCriticalSection( &date_lock );
00187
00188 return usec_time;
00189 }
00190
00191 #else
00192 struct timeval tv_date;
00193
00194
00195
00196
00197 gettimeofday( &tv_date, NULL );
00198 return( (mtime_t) tv_date.tv_sec * 1000000 + (mtime_t) tv_date.tv_usec );
00199
00200 #endif
00201 }
00202
00211 void mwait( mtime_t date )
00212 {
00213 #if defined( HAVE_KERNEL_OS_H )
00214 mtime_t delay;
00215
00216 delay = date - real_time_clock_usecs();
00217 if( delay <= 0 )
00218 {
00219 return;
00220 }
00221 snooze( delay );
00222
00223 #elif defined( WIN32 ) || defined( UNDER_CE )
00224 mtime_t usec_time, delay;
00225
00226 usec_time = mdate();
00227 delay = date - usec_time;
00228 if( delay <= 0 )
00229 {
00230 return;
00231 }
00232 msleep( delay );
00233
00234 #else
00235
00236 struct timeval tv_date;
00237 mtime_t delay;
00238
00239
00240 gettimeofday( &tv_date, NULL );
00241
00242
00243 delay = date - (mtime_t) tv_date.tv_sec * 1000000
00244 - (mtime_t) tv_date.tv_usec
00245 - 10000;
00246
00247
00248
00249 if( delay <= 0 )
00250 {
00251 return;
00252 }
00253
00254 # if defined( PTH_INIT_IN_PTH_H )
00255 pth_usleep( delay );
00256
00257 # elif defined( ST_INIT_IN_ST_H )
00258 st_usleep( delay );
00259
00260 # else
00261
00262 # if defined( HAVE_NANOSLEEP )
00263 {
00264 struct timespec ts_delay;
00265 ts_delay.tv_sec = delay / 1000000;
00266 ts_delay.tv_nsec = (delay % 1000000) * 1000;
00267
00268 nanosleep( &ts_delay, NULL );
00269 }
00270
00271 # else
00272 tv_date.tv_sec = delay / 1000000;
00273 tv_date.tv_usec = delay % 1000000;
00274
00275 select( 0, NULL, NULL, NULL, &tv_date );
00276 # endif
00277
00278 # endif
00279
00280 #endif
00281 }
00282
00289 void msleep( mtime_t delay )
00290 {
00291 #if defined( HAVE_KERNEL_OS_H )
00292 snooze( delay );
00293
00294 #elif defined( PTH_INIT_IN_PTH_H )
00295 pth_usleep( delay );
00296
00297 #elif defined( ST_INIT_IN_ST_H )
00298 st_usleep( delay );
00299
00300 #elif defined( WIN32 ) || defined( UNDER_CE )
00301 Sleep( (int) (delay / 1000) );
00302
00303 #elif defined( HAVE_NANOSLEEP )
00304 struct timespec ts_delay;
00305
00306 ts_delay.tv_sec = delay / 1000000;
00307 ts_delay.tv_nsec = (delay % 1000000) * 1000;
00308
00309 nanosleep( &ts_delay, NULL );
00310
00311 #else
00312 struct timeval tv_delay;
00313
00314 tv_delay.tv_sec = delay / 1000000;
00315 tv_delay.tv_usec = delay % 1000000;
00316
00317
00318
00319
00320
00321 select( 0, NULL, NULL, NULL, &tv_delay );
00322
00323 #endif
00324 }
00325
00326
00327
00328
00329
00338 void date_Init( date_t *p_date, uint32_t i_divider_n, uint32_t i_divider_d )
00339 {
00340 p_date->date = 0;
00341 p_date->i_divider_num = i_divider_n;
00342 p_date->i_divider_den = i_divider_d;
00343 p_date->i_remainder = 0;
00344 }
00345
00354 void date_Change( date_t *p_date, uint32_t i_divider_n, uint32_t i_divider_d )
00355 {
00356 p_date->i_divider_num = i_divider_n;
00357 p_date->i_divider_den = i_divider_d;
00358 }
00359
00366 void date_Set( date_t *p_date, mtime_t i_new_date )
00367 {
00368 p_date->date = i_new_date;
00369 p_date->i_remainder = 0;
00370 }
00371
00378 mtime_t date_Get( const date_t *p_date )
00379 {
00380 return p_date->date;
00381 }
00382
00389 void date_Move( date_t *p_date, mtime_t i_difference )
00390 {
00391 p_date->date += i_difference;
00392 }
00393
00402 mtime_t date_Increment( date_t *p_date, uint32_t i_nb_samples )
00403 {
00404 mtime_t i_dividend = (mtime_t)i_nb_samples * 1000000;
00405 p_date->date += i_dividend / p_date->i_divider_num * p_date->i_divider_den;
00406 p_date->i_remainder += (int)(i_dividend % p_date->i_divider_num);
00407
00408 if( p_date->i_remainder >= p_date->i_divider_num )
00409 {
00410
00411 p_date->date += p_date->i_divider_den;
00412 p_date->i_remainder -= p_date->i_divider_num;
00413 }
00414
00415 return p_date->date;
00416 }