Issue with Time.now() on Mesh devices

Has anyone attempted to use system time in the setup() function on a mesh device? I find that any call to Time.isValid() returns true even before time has been set. An attempt to call Time.now returns a unix time of midnight, Jan 1 2000.

If I put several seconds of delay in the setup() function, eventually the time usually gets set, but I would not expect Time.isValid to return a true value unitl the time is useful.

This may be a case of “Well, 2000-01-01 is a valid time…”, but it’s not correct. :-\

I’m still waiting for my pre-order gear, but, since you discovered that you could “wait it out” to finally get useful time, have you considered using a “while (unixtime is less than unixtime-as-of-2018-11-27:15:00:00)” loop to try setting the time until it takes hold? It may not be ideal, but it might work well enough. :slight_smile:

The year 2000 is valid for Time.now() only if your mesh network is in your time travel machine!

Yes, I did try some tests for a minimum time value, but, curiously, I got other values in the past as well. So, for my immediate need, I switched to millis(), which is well behaved.

I always use the following code in setup which checks the time is > 01/01/2018

    waitUntil(Particle.connected);

    do
    {
        resetTime = Time.now();
        delay(10);
    } while (resetTime < 1514764800 && millis() < 20000);

Hmm, not sure if the topic title reflects your actual issue.
The problem seems to be related to Time.isValid() reporting validity when it’s not.
When the time stored in the RTC is 1.1.2000 Time.now() reports what it’s supposed to report.

However

  • Does your device have a cloud connection?
  • If so, does Particle.syncTime() help?
  • If not, does Time.now() report the expected time after using Time.setTime()?

The root cause of the problem does appear to be Time.isValid() immediately returning a true value instead of blocking until the clock has actually been set from the cloud. Time.now() is supposed to call Time.isValid(). If Time.isValid() does not wait for good time, then Time.now(), or any other clock time function will be returning the wrong time.

Where does that statement come from?
One might want to call Time.now() irrespective of Time.isValid().
On the other hand, what would that change given the fact that Time.isValid() appears to report a "wrong" state.

However, I guess the reason for that is probably here to be found
https://docs.particle.io/reference/device-os/firmware/photon/#isvalid-

It might well be that the "wrong" time comes from RTC and hence gets accepted, but who checks whether the RTC has actually been set before correctly?
There might be some difference beweent the STM32 RTC validity flag compared to the nRF.

It comes from the published documentation for Time.isValid():

“NOTE: When Xenon is running in AUTOMATIC mode and threading is disabled this function will block if current time is not valid and there is an active connection to Particle Device Cloud. Once Xenon synchronizes the time with Particle Device Cloud or the connection to Particle Device Cloud is lost, Time.isValid() will return its current state. This function is also implicitly called by any Time function that returns current time or date (e.g. Time.hour()/Time.now()/etc).

Quick guess -- You need to make sure you have a Cloud connection before you call the Time functions? It might be that if you are calling it before you have a Cloud connection, Time.valid() is just returning its last known RTC value, instead of blocking until it can fetch the correct time.

You might want to try waiting for Particle.connected() in setup(), then calling Particle.syncTime()?

This is basically what I ended up doing. However, given that the Argon gateway is currently so unreliable, it may be better to not rely on the cloud and, instead, implement a time request over the mesh network and have the Argon (or any other node with valid time) respond. The Xenon could then set time manually and move on. This should help prevent Xenon nodes from blocking execution indefinitely waiting on a cloud connection.

Next is to experiment with getting the Argon to recognize when it no longer has a working cloud connection and if this can be fixed in some way short of rebooting.

Just waking this Thread to understand where you got to.

I have a mesh of Xenons with the gateway Xenon Ethernet enabled and in a Particle Ethernet FeatherWing. The gateway only uses Mesh pub/sub with the (sleepy) endnode Xenons. I have a process which has the end nodes request a time sync from the gateway at startup. Accepting a 1-2 second delay in the process the end nodes all start with their RTC sent to the time on the gateway (which is cloud sync’d) and then go into a cycle of sleeping, waking on the RTC after X seconds and publishing a heartbeat. I have observed that when Xenons are running on battery power their RTC gains time and when they are powered/recharging the RTC does not gain time! Has anyone else observed this?