1.clock_gettime
#include<time.h>
int clock_gettime(clockid_t clk_id,struct timespec *tp);
struct timespec
{
time_t tv_sec; /* 秒*/
long tv_nsec; /* 纳秒*/
}
#include<time.h>
//伪代码
while(1)
{
struct timespec now;
clock_gettime(CLOCK_BOOTTIME, &now);
long long now_time = now.tv_sec * 1000000000 + now.tv_nsec;
printf("now:%lld, sec:%lld, nsec:%lld\n", now_time, now.tv_sec, now.tv_nsec);
usleep(300000);//300ms
return now_time;
}
结构体只有秒和微妙,其中tv_nsec最高位是百毫秒位,可以看到睡眠300毫秒会加在tv_nsec最高位,它满了后,tv_sec就进一位。因此毫秒的计时并没有缺失。
CLOCK_BOOTTIME可以作为音视频帧的pts,因为它不受任何因素影响,开机后就开始计时。
2.gettimeofday
#include <sys/time.h>
int gettimeofday(struct timeval *tv, struct timezone *tz);
struct timeval
{
__time_t tv_sec; /* Seconds. 秒*/
__suseconds_t tv_usec; /* Microseconds. 微秒*/
};
struct timezone
{
int tz_minuteswest; /* Minutes west of GMT. 和Greenwich时间差了多少分钟 */
int tz_dsttime; /* Nonzero if DST is ever in effect. 日光节约时间的状态 */
};
long long get_time()
{
struct timeval tv;
gettimeofday(&tv, NULL);
ZlogInfo("second:%ld\n",tv.tv_sec); //秒
ZlogInfo("millisecond:%ld\n",tv.tv_sec*1000 + tv.tv_usec/1000); //毫秒
ZlogInfo("microsecond:%ld\n",tv.tv_sec*1000000 + tv.tv_usec); //微秒
long long temp_time = tv.tv_sec * 1000000 + tv.tv_usec;
return temp_time;
}
在第二个参数填null,可以看到它有自己的毫秒位,这个函数返回的是从UTC时间,1970/1/1,零点开始计时的时间。它其实也就是随系统时间,也就是如果你手动更改了系统时间,或者系统NTP自动联网校时了,那么这个时间就会发送跳跃。因此如果你把他当做音/视频pts是非常不合理的。
附录:
参考:
linux C时间编程
理解linux时间软硬件