Forum > Windows

Req: DateTimeToFileDate replacement

(1/2) > >>

WackaMold:
DateTimeToFileDate cannot handle dates after the year 2099, but I could not find any documentation about that on FPC sites. Confirmation is found at "Year must be 1980 .. 2099" Confirmation in the source is at FPC\3.2.0\Source\rtl\objpas\sysutils\dati.inc line 1249 1242.

FPC needs to be able to handle more file-dates, preferably approaching the same limits/capabilities of the target platform OS. For FileDates outside the range of DateTimeToFileDate, what set of functions is recommended? I know traditional UnixTime quits around 2038. Do I need to skip this part of the RTL and just use functions provided by the OS / Windows API? Because that is a reasonable option.

Conceptually the use-case needs a minimum resolution of whole seconds, and does not want to fuss with fractions of a second. In reality, NTFS stores file Last-Write / Last-Modified DateTime in resolution of two seconds. Annoying but oh well.

The old way is:
  FileAge
  FileDateToDateTime
  IncYear (or whatever)
  DateTimeToFileDate
  FileSetDate

What is the preferred new way?

Thaddy:
Loosing portability is not a reasonable option, imho.

wp:
What is the reason why this function is restricted to be valid only before year 2100? Looking at the source code

--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---Function DateTimeToFileDate(DateTime : TDateTime) : Int64; Var YY,MM,DD,H,m,s,msec : Word; begin  Decodedate (DateTime,YY,MM,DD);  DecodeTime (DateTime,h,m,s,msec);{$if not defined(unix) and not defined(wasi)}  If (YY<1980) or (YY>2099) then    Result:=0  else    begin    Result:=(s shr 1) or (m shl 5) or (h shl 11);    Result:=Result or longint(DD shl 16 or (MM shl 21) or (word(YY-1980) shl 25));    end;{$else unix or wasi}  Result:=LocalToEpoch(yy,mm,dd,h,m,s);{$endif unix or wasi}end;I get the impression that the programmer simply might have thought: "I don't want to care about leap years and leap seconds after 2100 for now"

PascalDragon:

--- Quote from: WackaMold on January 11, 2022, 02:52:10 am ---What is the preferred new way?

--- End quote ---

The development version of FPC already provides support for FileSetDate overloads that take a TDateTime. This won't become part of the 3.2.x series however.


--- Quote from: wp on January 11, 2022, 10:38:19 am ---What is the reason why this function is restricted to be valid only before year 2100? Looking at the source code

--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---Function DateTimeToFileDate(DateTime : TDateTime) : Int64; Var YY,MM,DD,H,m,s,msec : Word; begin  Decodedate (DateTime,YY,MM,DD);  DecodeTime (DateTime,h,m,s,msec);{$if not defined(unix) and not defined(wasi)}  If (YY<1980) or (YY>2099) then    Result:=0  else    begin    Result:=(s shr 1) or (m shl 5) or (h shl 11);    Result:=Result or longint(DD shl 16 or (MM shl 21) or (word(YY-1980) shl 25));    end;{$else unix or wasi}  Result:=LocalToEpoch(yy,mm,dd,h,m,s);{$endif unix or wasi}end;I get the impression that the programmer simply might have thought: "I don't want to care about leap years and leap seconds after 2100 for now"

--- End quote ---

While DateTimeToFileDate returns a Int64 now that wasn't always the case (and was only changed so that the Unix timestamp is handled correctly), but on Windows it is in fact a 32-bit value that can only support the range 1980 to 2099, cause that is how it was originally defined in FAT and is supported by DOS and Windows (see here).

wp:
Thanks. But still, the specs that you cite say that here are 7 bits for the years since 1980 (128 years). This means that physically the range should be extendable to 1980+128 = 2208. Not much, though...

Navigation

[0] Message Index

[#] Next page

Go to full version