使用最大可变大小32位在c中获取时间戳(以微秒为单位)

时间:2019-07-09 11:51:07

标签: c timestamp

我需要获得一个毫秒级的时间戳。我发现了诸如使用timeval结构和调用gettimeofday之类的选项。问题在于所有结构中都包含长变量,而我只能使用32位变量。

如何仅使用32位变量获取时间戳(在c中)?

2 个答案:

答案 0 :(得分:1)

This site 通常是与时间和时钟相关的编程的很好参考,包括函数原型,结构定义以及与您的请求相关的编程示例。你应该看看。

here 中有一些答案可能适合您的需求。可接受的答案是通用的:

  

对于32位系统:

fprintf(stdout, "%u\n", (unsigned)time(NULL)); )_

answer for the same question ,专门解决了我们的分辨率。但是,它是POSIX特定的,并且可能违反您的规范。 :

#include <stdio.h>
#include <time.h>
#include <stdint.h>
#include <inttypes.h>
int main(void) {

    struct timespec tms;

    /* The C11 way */
    /* if (! timespec_get(&tms, TIME_UTC)) { */

    /* POSIX.1-2008 way */
    if (clock_gettime(CLOCK_REALTIME,&tms)) {
        return -1;
    }
    /* seconds, multiplied with 1 million */
    int64_t micros = tms.tv_sec * 1000000;
    /* Add full microseconds */
    micros += tms.tv_nsec/1000;
    /* round up if necessary */
    if (tms.tv_nsec % 1000 >= 500) {
        ++micros;
    }
    printf("Microseconds: %"PRId64"\n",micros);
    return 0;
}

答案 1 :(得分:0)

如果struct timeval字段是32位格式的long整数格式(可以是或不能),则是因为您需要具有该大小。一些分析:我以NTP格式获取此时间戳,并在系统上将其转换为struct timeval格式(用于 now 时间戳):

ntpts.c:120:process:  NTP(dec): 3771731346.612550000
ntpts.c:121:process:  NTP(hex): 0xe0d00d92.9cd013a9
ntpts.c:123:process:      UNIX: 1562742546/0x5d258f12
ntpts.c:135:process:    gmtime: 10/jul/2019, 07:09:06.612550000
ntpts.c:136:process: localtime: 10/jul/2019, 10:09:06.612550000

tv_sec  ==> 1562742546
tv_usec ==>     612550

因此,要获得具有该分辨率的单个时间戳(自1970年1月1日00:00h起的秒数,以毫秒为单位),则至少需要52位(好,通常tv_sec是{{1} }或long long 64位字段,因为2038年2月将发生溢出,并且某些系统已经对此进行了修补),long可能适合24位变量( usec从0到999999,因此它们至少需要20位),但是编译器填充将使其至少达到32位大小。

如果要保留32位的完整usec分辨率,则至少需要20位来表示几分之一秒,而只有12位来表示整数部分。在这种情况下,您将只能表示从0到4095的秒数,这表示一个多小时(01h8m16s)。这可以处理,但是要使该时间戳记为绝对值,则需要引用该时间戳记属于历史记录中的绝对小时数。

另一方面,如果将粒度减小到毫秒,则可以获得超过1000小时的参考窗口,您需要考虑这一点,以便最终决定下一步要做什么。

修订

顺便说一下,tv_usec系统调用实际上已被弃用。当今几乎所有正在使用的系统都使用gettimeofday(2)系统调用,该系统调用具有纳秒级的分辨率,并允许您选择适当的系统时钟来获取时间戳。