So the other day there was an extended power outage down at the dogg pound, and one of my non-essential server racks had to be taken off-line. This particular server rack only has UPS battery backup, but no generator power (like the others), and upon reboot, the clocks in all my QEMU Linux VM’s were wrong! They kept getting set to UTC time instead of local time… After much searching and testing, I finally found out what was necessary to fix this issue.
First, we need to make sure that all of our time settings are correct. Let’s compare the hardware clock settings to the current real time, which is 11:13AM EST:
[16:13] root@ns3:~ # hwclock Wed 21 Dec 2011 04:13:49 PM EST -0.297984 seconds [16:13] root@ns3:~ # date Wed Dec 21 16:13:07 EST 2011 [16:13] root@ns3:~ #
Well, here we can see that the hardware and system clocks are wrong! KVM/QEMU likes to keep its “hardware time” as UTC, so it takes the time from the host system and adjusts it to UTC, based off of the host system’s timezone setting. The host system shows the correct time (and actually this physical host machine’s hardware time is set to local, not UTC).
Ok, well lets make sure our timezone is set correct. The /etc/localtime file represents the timezone info for your particular time zone. This can either be a symbolic link to the correct file, or a copy of the correct file. On my system, it looks like this:
[16:20] root@ns3:~ # ls -alh /etc/localtime lrwxrwxrwx 1 root root 36 Dec 21 15:14 /etc/localtime -> /usr/share/zoneinfo/America/New_York [16:21] root@ns3:~ #
Now, you can either make a symbolic link using the command
ln -s /usr/share/zoneinfo/America/New_York /etc/localtime
or you can copy the zone file with the command
cp /usr/share/zoneinfo/America/New_York /etc/localtime
There are arguments for and against each method, use whichever method you prefer.
Next, we need to check our /etc/sysconfig/clock file to make sure it is correct. My file looks like this:
ZONE="America/New_York"
Some users will add a line that says UTC="true" (or false), but it isn’t needed and can just add confusion.
Finally, we need to check the /etc/adjtime file; this file was the key! The 3rd line in the file will say either UTC or LOCAL. Since our hardware clock was set to UTC time (as shown above), we need to change our adjtime file to say UTC instead of LOCAL. Here is what mine looks like:
-15185.281863 1324482636 0.000000 1324482636 UTC
So now everything should be set to keep the system time correct after a hard reboot (power off & on), but our current clock is still wrong! Well, we can fix the current time with the following command:
[16:24] root@ns3:~ # hwclock --utc -s [11:24] root@ns3:~ #
This will set our system time from the hardware clock, stating that the hardware clock is kept in UTC time.
Now, in order to test everything, we need to completely power down the virtual machine and restart it. Simply issuing a reboot won’t force our host machine to apply it’s time settings to the VM. Previously, after every hard boot the time would be wrong, but now it’s correct!
You should also set up some NTP time synchronization to keep your time accurate; but this will at least keep the zone correct between power cycles.