Millis() and rollover tutorial


#21

@peekay123 no, not a specific issue, just about to adapt code from delay() to elapsedMillis() to get rid of delays using mobicle.io (next step maybe Blynk) for my home automation. Tried to read elapsedMillis.h, but was confusing for a beginner like me :thinking:. Thanks for the quick reply.


#22

You shouldn’t have any problems using the sample from the first post to replace delay.
The concept works perfectly and it’s a great tutorial for beginners.


#23

I’m currently writing an application for gardening which will often have long times between function calls, hours or perhaps days depending on the function. I’m trying to decide whether I should be using Software Timers, millis(), or Time.now() in some way to do that.

Reading up on millis(), I am having trouble understanding these two sections which seem to be contrary.

I assume every negative value has a DIFFERENT unsigned equivalent, but not sure what those values would be to understand how comparing them to a value of say 86,400,000 (24hrs in ms) would behave.

Based on the first quoted section, since lastTime is an unsigned long, shouldn’t the result of this statement be -1000 which is then converted to some positive number because it’s unsigned?

Thanks in advance.


#24

For hours or days, the real-time clock Time.now() is probably the best option.

The examples in the original post are specifically for dealing with how millis wraps after 49 days.

Say the time in lastTime was +4294966796, right before rolling over.

The next time you check, millis() (or the now variable in the original post) is now 500 because it rolled over. The formula now - lastTime would be 500 - 4294966796.

In signed math, that’s a negative number, -4294966296. However, that number is stored in memory as 1000. It really is the same bits in a 4-byte value.

The reason this isn’t ambiguous is that -4294966296 can’t really be represented in a 32-bit signed value because the minimum value is -2147483648.

But when you compare against 1000, it works properly.


#25

Yeah, I assumed I was going to have to use time.now() and store the last run times for each function in EEProm to compare to because a reboot would reset both the millis() and Software Timers.

Just to complete wrapping my brain around the millis() question though I had one more question.

If -4294966296 is represented the same as 1000 when stored as an unsigned long, what would it be if the number was -3294966296? It’s still below the minimum value of -2147483648, but is the result different in a predictable way?

Thanks again.


#26

Now that I think about it, a better way of explaining it is that -4294966296 or -3294966296 requires a 33-bit two’s complement integer. But since integer is only 32 bits, the sign bit is lost, making a positive 32-bit integer.

-3294966296 = 0b100111011100110101100110111101000 (33 bits)

Removing the MSB:
0b00111011100110101100110111101000 = 1000001000 (decimal)