2

I'm having a very strange issue. I'm using gettimeofday to control timeouts in an I/O library. I have isolated the problem that a second call to gettimeofday returns a earlier time than first.

I've done a simple test demo that reveals the problem. It only happens in a virtualized machine (virtualbox) that runs Ubuntu 18.04.1 LTS.

#include <unistd.h>
#include <stdio.h>
#include <sys/time.h>

unsigned long GetTickCount()
{
    struct timeval start, end;
    unsigned long myTickCount;
    gettimeofday(&start, NULL);
    myTickCount =start.tv_sec*1000+start.tv_usec/1000;
    return myTickCount;
}


main()
{
        unsigned long a,b;
        while(1) {
                a=GetTickCount();
                usleep(100000);
                b=GetTickCount();
                if(a>b)
                        printf("a: %ld, b:%ld, b-a=%ld\r\n",a,b,b-a);
        }
}

When I run the code I get things like:

a: 1540980716756, b:1540980716090, b-a=-666
a: 1540980748208, b:1540980747542, b-a=-666
a: 1540980779740, b:1540980779074, b-a=-666
a: 1540980811180, b:1540980810513, b-a=-667
a: 1540980842713, b:1540980842047, b-a=-666
a: 1540980874153, b:1540980873487, b-a=-666

If you check it carefully you will see that the glitch is every 31.5s.

Some hint about what's happening? Is it a kind of clock drift adjusted by virtualbox?

jww
  • 97,681
  • 90
  • 411
  • 885
Mquinteiro
  • 1,034
  • 1
  • 11
  • 31
  • 5
    It might be caused by some internal correction of clock drift. I suspected that `gettimeofday()` might not grant to be a monotonic clock and googled a bit. It seems my feeling was right: [gettimeofday() should never be used to measure time](https://blog.habets.se/2010/09/gettimeofday-should-never-be-used-to-measure-time.html). To find more about this (and what to do against), please, google "gettimeofday monotonic" or "linux monotonic clock". – Scheff's Cat Oct 31 '18 at 11:13
  • 1
    Use [`clock_gettime()` instead](http://pubs.opengroup.org/onlinepubs/9699919799/functions/gettimeofday.html): `gettimeofday()` is obsolescent. – pmg Oct 31 '18 at 14:29
  • @Scheff clock_gettime with CLOCK_MONOTONIC/CLOCK_MONOTONIC_RAW looks to be way to do a correct time operations. – Mquinteiro Oct 31 '18 at 14:51
  • @Mquinteiro I didn't look for a duplicate nor did anybody else complain. The latter let me think it would be worth a [self answer](https://stackoverflow.com/help/self-answer). – Scheff's Cat Oct 31 '18 at 14:56
  • 1
    @Scheff it is very close to be a duplicated, https://stackoverflow.com/questions/4801122/how-to-stop-time-from-running-backwards-on-linux/4801176#4801176 – Mquinteiro Oct 31 '18 at 16:16
  • Possible duplicate of [How to stop time from running backwards on Linux?](https://stackoverflow.com/questions/4801122/how-to-stop-time-from-running-backwards-on-linux) – Mquinteiro Oct 31 '18 at 16:17
  • What is `sizeof(long)`? Is it enough to hold the seconds since the Epoch times 1000? – AlexP Oct 31 '18 at 16:59

0 Answers0