How to handle localtime() on old timestamps?

M

maruk2

I have some old data files with old timestamps, where
timestmap=time(NULL), some of them date back to the
year 1999.

I want to my code to print the timestamps and each one to
include hour:minute:second as of the corresponding old day.
The only routine for this job seems to be
localtime(timestmap) - this is Windows Vista,
Visual Studio 2005 C++.


localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.


For example, I run localtime on a timestamp from 3-22-1999
(Daylight Saving Time was not effective yet) today when Daylight
Saving Time is effective and localtime() returns hour:minute:second
one hour later as it should.


Does it mean that the only way around it is to keep transition
dates for Daylight Saving Time for all years and have my code
make the adjustments depending on the old day and the current
day? Is there any utility to do that or any better way?
 
K

Keith Thompson

I have some old data files with old timestamps, where
timestmap=time(NULL), some of them date back to the
year 1999.

I want to my code to print the timestamps and each one to
include hour:minute:second as of the corresponding old day.
The only routine for this job seems to be
localtime(timestmap) - this is Windows Vista,
Visual Studio 2005 C++.

localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.
[...]

It sounds like your system's implementation of localtime() is buggy.
There may not be much you can do to correct it, but workarounds are
possible.
For example, I run localtime on a timestamp from 3-22-1999
(Daylight Saving Time was not effective yet) today when Daylight
Saving Time is effective and localtime() returns hour:minute:second
one hour later as it should.

Does it mean that the only way around it is to keep transition
dates for Daylight Saving Time for all years and have my code
make the adjustments depending on the old day and the current
day? Is there any utility to do that or any better way?

That would be one solution, but it could break if a future version of
your implementation corrects the bug in localtime().

An alternative might be to use gmtime() and do the conversion to local
time yourself. But that requires knowing about the time zone, which
varies from place to place, within a year (as DST comes and goes), and
over history (as DST rules change, either nationally or locally).

I think there are time zone libraries that already include much of
this information (<OT>Googling "tzdata" may be helpful</OT>).

It's also likely that there's a system-specific solution. Try a
newsgroup that deals with Windows and/or with Visual Studio 2005 C++.
 
N

Nelu

I have some old data files with old timestamps, where
timestmap=time(NULL), some of them date back to the
year 1999.

localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.


For example, I run localtime on a timestamp from 3-22-1999
(Daylight Saving Time was not effective yet) today when Daylight
Saving Time is effective and localtime() returns hour:minute:second
one hour later as it should.


Does it mean that the only way around it is to keep transition
dates for Daylight Saving Time for all years and have my code
make the adjustments depending on the old day and the current
day? Is there any utility to do that or any better way?

Check the value of tm_isdst. If the value is positive then DST is
in effect, if it's zero then DST is not in effect. If that value
is negative then that information is not available. Unless you
get a negative value you should have correct DST information
provided that your system has up to date time zone information.
It may not be your case but time_t range and precision are
implementation defined and they can actually be different between
different versions of the same compiler.

Can you give me some timestamps, the tm values you get and the tm
values you expect?
 
W

Walter Roberson

I want to my code to print the timestamps and each one to
include hour:minute:second as of the corresponding old day.
The only routine for this job seems to be
localtime(timestmap) - this is Windows Vista,
Visual Studio 2005 C++.
localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.

I've recently read (in comp.risks I think it was) that this
is a long-standing Windows issue that Microsoft has refused to change.

However, as this is a system-specific behaviour and I could
easily be wrong (or have misinterpreted), you will need to
check in a Windows programming newgroup.
 
M

maruk2

I have some old data files with old timestamps, where
timestmap=time(NULL), some of them date back to the
year 1999.
I want to my code to print the timestamps and each one to
include hour:minute:second as of the corresponding old day.
The only routine for this job seems to be
localtime(timestmap) - this is Windows Vista,
Visual Studio 2005 C++.
localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.

[...]

It sounds like your system's implementation of localtime() is buggy.
There may not be much you can do to correct it, but workarounds are
possible.


So what the non-buggy systems do? They actually save the DST
transition
dates for all past years. I do not think the dates are fixed and may
change
from year to year.
 
M

maruk2

Check the value of tm_isdst. If the value is positive then DST is
in effect, if it's zero then DST is not in effect. If that value
is negative then that information is not available. Unless you
get a negative value you should have correct DST information
provided that your system has up to date time zone information.
It may not be your case but time_t range and precision are
implementation defined and they can actually be different between
different versions of the same compiler.

Can you give me some timestamps, the tm values you get and the tm
values you expect?

isdst field is set to 1, apparently on the basis of *current" DST,
the old timestamp is not supposed to have DST.

localtime() should ignore the current DST, obviously it should
assume some timezone and the current timezone is fine.
 
N

Nelu

isdst field is set to 1, apparently on the basis of *current" DST,
the old timestamp is not supposed to have DST.

Then this may be a bug. The broken down time that localtime
returns should have all the fields reflecting the characteristics
of the calendar time (time_t).
localtime() should ignore the current DST, obviously it should
assume some timezone and the current timezone is fine.

Take a look at this, maybe it applies to your problem, as well:
http://support.microsoft.com/kb/129574
 
J

J. J. Farrell

I have some old data files with old timestamps, where
timestmap=time(NULL), some of them date back to the
year 1999.
I want to my code to print the timestamps and each one to
include hour:minute:second as of the corresponding old day.
The only routine for this job seems to be
localtime(timestmap) - this is Windows Vista,
Visual Studio 2005 C++.
localtime() seems to consider the presence of Daylight Saving
Time for the current day when it is actually called, but it does
not seem to consider the presence of Daylight Saving Time
for the old day.

It sounds like your system's implementation of localtime() is buggy.
There may not be much you can do to correct it, but workarounds are
possible.

So what the non-buggy systems do? They actually save the DST
transition dates for all past years. I do not think the dates are
fixed and may change from year to year.

<OT>Yes; as keith said (but you cut) 'Googling "tzdata" may be
helpful'</OT>.
 
M

maruk2

isdst field is set to 1, apparently on the basis of *current" DST,
Then this may be a bug. The broken down time that localtime
returns should have all the fields reflecting the characteristics
of the calendar time (time_t).

Why a bug? This could be just an easy way out. This is not
documented one way or another.
Take a look at this, maybe it applies to your problem, as well:http://support.microsoft.com/kb/129574

This link is just a basic explanation of DST impact on the *current*
time.
The issue here is whether Windows is able to find out DST of an *OLD*
time.
 
N

Nelu

Why a bug? This could be just an easy way out. This is not
documented one way or another.

The things about tm_isdst were taken from the C standard (n1124
draft). If they can't figure out the DST they must return -1 and
this would be the easy way out. They can't return 0 or 1 if they
don't know the DST.
This link is just a basic explanation of DST impact on the *current*
time.
The issue here is whether Windows is able to find out DST of an *OLD*
time.

"SUMMARY
When Windows NT automatically adjusts for daylight saving time,
the times on files on Windows NT file system (NTFS) partitions
and the events in the event logs are retroactively shifted by one
hour, even though the files and event records were created before
the daylight saving time change. "

They will most likely not take each file in turn and shift the
time, they will change the meaning of the timestamp, which is
what your problem is and, as I was quoting earlier from the
standard, they are allowed to do this, however, they are not
allowed to lie. This is also the reason why you should never use
the value of time_t returned by the time family of functions to
store dates for long term.
 
N

Nelu

CBFalconer said:
:

Use Linux, without an interfering Windows component. Then Linux
will be keeping all times in GMT, and displaying accordingly (i.e.
as you wish).

That gave me headaches when I had a dual boot system. I think
Vista is still on local clock.
 
A

Army1987

Walter Roberson said:
I've recently read (in comp.risks I think it was) that this
is a long-standing Windows issue that Microsoft has refused to change.

However, as this is a system-specific behaviour and I could
easily be wrong (or have misinterpreted), you will need to
check in a Windows programming newgroup.

I understand that they use this brain-dead way of dealing with DST
to break code dealing with it which is not written by them, but at
least they could set tm_isdst to a negative value, so that code
written by others couldn't work at all rather than mis-working.
 
M

maruk2

That gave me headaches when I had a dual boot system. I think
Vista is still on local clock.


I read some links in more detail and googled the net, it seems to
be a widely reported problem. However, I did not find a comprehensive
comparison of localtime() on Windows and all other systems incl.
Unix/Linux. I am not asking how Unix/Linux displays the timestamps
saved by itself (like filesystem info) because it could easily save
DST
flag with each timestamp. I am asking how localtime() behaves
on any valid timestamp. localtime() would have to keep some kind
of DST info applicable to all possible timestamps.

The best way would be to run tests with localtime()
at least on Linux myself but I do not have a ready Linux
installation.
 
W

Walter Roberson

I read some links in more detail and googled the net, it seems to
be a widely reported problem. However, I did not find a comprehensive
comparison of localtime() on Windows and all other systems incl.
Unix/Linux. I am not asking how Unix/Linux displays the timestamps
saved by itself (like filesystem info) because it could easily save
DST
flag with each timestamp.

No, that wouldn't work. There is no one true system timezone setting,
only per-process timezone settings (possibly inherited from a calling
process.) Slightly off-topic for comp.lang.c, but POSIX.1 indicates
specifically that the user is allowed to override the timezone
settings, and indicates specifically that each process must be allowed
to use different timezone settings.
I am asking how localtime() behaves
on any valid timestamp. localtime() would have to keep some kind
of DST info applicable to all possible timestamps.
The best way would be to run tests with localtime()
at least on Linux myself but I do not have a ready Linux
installation.

You don't need to actually run Linux tests: you can pull
the Linux localtime() source off the net.
 
N

Nelu

I read some links in more detail and googled the net, it seems to
be a widely reported problem. However, I did not find a comprehensive
comparison of localtime() on Windows and all other systems incl.
Unix/Linux. I am not asking how Unix/Linux displays the timestamps
saved by itself (like filesystem info) because it could easily save
DST
flag with each timestamp. I am asking how localtime() behaves
on any valid timestamp. localtime() would have to keep some kind
of DST info applicable to all possible timestamps.

There are different ways of implementing localtime but that's no
longer topical on c.l.c. You should find a group that can explain
these implementation details as this is beyond the scope of this
group (that's not to say that there aren't people here that can
help you, it's just the fact that if someone gives you the wrong
answer there will be no one to contradict him).
The best way would be to run tests with localtime()
at least on Linux myself but I do not have a ready Linux
installation.

Look up the sources and read the code. It should give you a
better idea of what's going on behind the scenes than attempting
to guess through experiments.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,534
Members
45,007
Latest member
obedient dusk

Latest Threads

Top