Is it possible set a time offset at node up

AFAIK, erlang:system_time(second) is time of node and os:system_time(second) is time of os, when I want to start a node at an special time, I will do like:

  1. modify os time to the special time
  2. start node
  3. modify os time to now

erlang:system_flag(time_offset, X) seem can finish this job, but it’s called after node up, it make me puzzled that if every thing depend on time(like timer, timestamp stroe in process,.etc) will work well

So, Is it possible set a time offset at node up

BTW, there are many lib(like lager) use os module to get the time, If I have any misunderstand about the time design and I should not modify the time to now until node down

1 Like

Well… time is a surprisingly fickle thing, and fiddling with the OS time etc doesn’t make that any better :sweat_smile: Why do you want to do that?

About lager using OS time: It is a logging library, and the timestamps it logs should at least resemble wall clock time to be of any worth to a possible reader.

Even if you don’t, somebody or something else may do just that. So, best advise is to not rely on it.

1 Like

to testing the server and client(time depend on server) at the special date, I’m sorry that 'I cant explain it so well :sweat_smile:

may be these questions is meaningless, because we know the diff and just write what we need:

  1. why use os as default
  2. if there are some standard about it
  3. when I to use erlang or os
1 Like

I’m not sure I understand what you are trying to do.

You are not supposed to, and cannot, set the time offset. The time offset is the difference between Erlang monotonic time and Erlang system time, and is adjusted by the runtime system. How it is adjusted depends on the time mode you are using. There are three different modes which all aim to align Erlang system time with OS system time:

  • Multi Time Warp Mode - The time offset is changed by the runtime system when it detects that the system times are not aligned in order to align them. All Erlang code in the system needs to be time warp safe in order to use this mode. This will be the default as of OTP 26. If your code is not time warp safe, you either need to make it time warp safe or change to one of the other modes.
  • No Time Warp Mode - This is the old style mode where the system times are aligned by changing the frequency of Erlang monotonic time. Time offset is set at runtime system start and after that never changed. A large downside of using this mode is that the system needs to use the wrong frequency in order to align the system times causing time measurements to be wrong. If there is a large change in OS system time, the frequency of Erlang monotonic time will be wrong for a long period of time. This is currently the default, but wont be in OTP 26 (as stated above).
  • Single Time Warp Mode - This works in a fashion very similar to No Time Warp Mode, but one change in time offset is allowed. This will, and can only, happen when erlang:system_flag(time_offset, finalize) is called. The intention of this mode was to allow a large initial adjustment of the time offset while still allowing most Erlang code in the system not to be time warp safe. For example, you boot some embedded system without a clock working when the system is down, so the time at boot will be 1970… After a while the clock is corrected via NTP or by manual interaction, and then you finalize the time offset. This in order to avoid that the frequency of Erlang monotonic time had to be wrong more or less for ever which would be the case when using No Time Warp Mode.

Multi Time Warp Mode in combination with time correction is the preferred configuration. This as the Erlang runtime system have better performance, scale better, and behave better on almost all platforms. Also, the accuracy and precision of time measurements are better. Only Erlang runtime systems executing on ancient platforms benefit from another configuration.

What time (OS system time/Erlang system time/Erlang monotonic time) you want to use depends on what you want to do. When using Multi Time Warp Mode (which you really want to) both OS and Erlang system time may leap forwards and backwards at any time. The difference between them are not that large. One advantage of using Erlang system time is that you can monitor leaps (changes in time offset) using erlang:monitor(time_offset, clock_service).

6 Likes

https://www.erlang.org/doc/apps/erts/time_correction.html#time-warp-safe-code
Time warp safe code can handle a time warp of Erlang system time.

If there are some example code about time not safe code, I can just find out erlang:now/0 is not safe in the document
I was imaging that is send_after, timer… have any relation with time not safe code

1 Like

It is mostly erlang:now/0 that is problematic, but you can run into problems if you use any of the two system times (Erlang or OS) where you really want to use Erlang monotonic time, for example if you want to measure elapsed time. There are some examples of what you want to do and don’t want to do here.

2 Likes

All timers in the system are set against Erlang monotonic time, i.e., they are not effected by time warps.

1 Like

Tanks!
Because of OTP-26 change Time Warp Mode default behavior
So I learn it again and seem typically using the default Time Warp Mode is good enough :grinning:

1 Like

GitHub - wolfcw/libfaketime: libfaketime modifies the system time for a single application works with BEAM just fine, it’s probably the most standard way of running tests like this.

1 Like

Hi,

@rfk23, did you use any special flags when running libfaketime ?