2

We have a JavaScript function that gets the start and end times of two events:

var startTime = new Date().getTime();
// A long running task occurs
var endTime = new Date().getTime();

The trouble we have found is that getTime() appears to be dependent on the system clock. Unfortunately, we have had a few instances where the user's clock has changed between these two calls, apparently through a Windows NTP time update (i.e. Windows goes out to a time server to get an accurate time, then changes the system clock to the correct time). So we wind up with something like this:

startTime = 12:00:00
// 30 second task is kicked off
// NTP time update detects that the system is one minute ahead and corrects the clock
endTime = 11:59:30 // It ended before it began

Is there any way that I can compare two times in such a way that will survive an NTP time update? Our JavaScript app would not be able to query any servers outside of our corporate firewall, so calling an NTP server ourselves is out of the question.

Thunderforge
  • 19,637
  • 18
  • 83
  • 130
  • 2
    It's not a duplicate of general performance measurement questions, as not all techniques (=answers on those questions) used to measure time performance are agnostic to NTP updates! However, the top rated answer on http://stackoverflow.com/questions/313893/how-to-measure-time-taken-by-a-function-to-execute is still the way to go, since "[...] unlike Date.now(), the values returned by Performance.now() always increase at a constant rate, independent of the system clock (which might be adjusted manually or skewed by software like NTP)." – le_m Mar 17 '17 at 20:29

1 Answers1

0

Just like the cleaning lady: I don't do windows. So my knowledge is of a various ntp daemons on unix (-like) machines over the years.

ntpd is not supposed as a general method to do a step, it's supposed to speed up and slow down the system clock. If it needs to do a step your machine either started out way off, or has a borked clock (or is just crappy hardware - they do exist too).

This means that under ordinary conditions, ntpd will make sure the timescale is effectively continuous and without discontinuities (it might be a bit fast or a bit slow though). It's only when the difference in system time and UTC is far too large that a "step" is considered and those might indeed cause time to go backwards, but typically they can get logged if they happen.

Steps in system time can cause various other issues too: e.g. make can get confused.

Modern ntpd has options to configure the threshold for when a step is performed.

Solutions:

You might figure out where your machines log that they perform an NTP step, and react to that (not going to be easy to do this cross platform).

Use some other measurement of time than system time.

You best bet if you want to avoid it all: query a public NTP server yourself instead of relying on the system time if it's that important.

As you state you cannot do that: query the time of a server with a reliable clock over http(s). It's not going to be easy to get the accuracy of NTP, but if you're measuring orders of magnitude of 30 secs, the variance introduced by using http(s) might be minimal.

If you really do need the accuracy: tunnel NTP over http(s) to a webserver and let NTP deal with the transmission delay. A 'bit' more work, but if you're desperate ...

If you run this in your own corporate environment, you can setup your own ntp servers pretty easy. Also you can buy off the shelf timeservers (just to get you started: google "Meinberg", but there are for sure others as well) and you can even broadcast the time of the local network with ntp just as well.

Now that said: I've a bit of a weird feeling about the need to measure elapsed time in an application.

Background info: http://doc.ntp.org/current-stable/ntpd.html