FSRW - modified date not working
MJHanagan
Posts: 189
in Propeller 1
I am having a problem with the file modification date using FSRW Version 2.6. When you use "popen(s, mode)" with mode="a" for append or "w" for write the file's "last modified date and time" should be updated. I am using "setdate(year, month, day, hour, minute, second)" prior to the popen command to set up the date and time values. This works because if I use popen to create a new file its creation date and time are correctly written.
When I use my laptop running Windows 10 to view the SD card directory the file's modification date and time is the same as its creation date and time even though I have written or append data to it days after its creation. If I am looking at the code correctly the creation date and time is set by
How could one work correctly without the other? Can anyone suggest where I am missing the boat?
Here is the code within fsrw:
And this is my code for setting the date and time:
When I use my laptop running Windows 10 to view the SD card directory the file's modification date and time is the same as its creation date and time even though I have written or append data to it days after its creation. If I am looking at the code correctly the creation date and time is set by
brwlong(s+$e, i) ' write create time and dateand the modification date and time are set using
brwlong(s+$16, i) ' write last modified date and time
How could one work correctly without the other? Can anyone suggest where I am missing the boat?
Here is the code within fsrw:
pub setdate(year, month, day, hour, minute, second)
{{
' Set the current date and time, as a long, in the format
' required by FAT16. Various limits are not checked.
}}
pdate := ((year-1980) << 25) + (month << 21) + (day << 16)
pdate += (hour << 11) + (minute << 5) + (second >> 1)
pub popen(s, mode) : r | i, sentinel, dirptr, freeentry
{{
' Close any currently open file, and open a new one with the given
' file name and mode. Mode can be "r" "w" "a" or "d" (delete).
' If the file is opened successfully, 0 will be returned. If the
' file did not exist, and the mode was not "w" or "a", -1 will be
' returned. Otherwise abort will be called with a negative error
' code.
}}
pclose
i := 0
repeat while (i<8 and byte[s] and byte[s] <> ".")
padname[i++] := uc(byte[s++])
repeat while (i<8)
padname[i++] := " "
repeat while (byte[s] and byte[s] <> ".")
s++
if (byte[s] == ".")
s++
repeat while (i<11 and byte[s])
padname[i++] := uc(byte[s++])
repeat while (i < 11)
padname[i++] := " "
sentinel := 0
freeentry := 0
repeat dirptr from rootdir to rootdirend - DIRSIZE step DIRSIZE
s := readbytec(dirptr)
if (freeentry == 0 and (byte[s] == 0 or byte[s] == $e5))
freeentry := dirptr
if (byte[s] == 0)
sentinel := dirptr
quit
repeat i from 0 to 10
if (padname[i] <> byte[s][i])
quit
if (i == 11 and 0 == (byte[s][$0b] & $18)) ' this always returns
fclust := brword(s+$1a)
if (filesystem == 2)
fclust += brword(s+$14) << 16
firstcluster := fclust
filesize := brlong(s+$1c)
if (mode == "r")
frem := (clustersize) <# (filesize)
return 0
if (byte[s][11] & $d9)
abort(-6) ' no permission to write
if (mode == "d")
brwword(s, $e5)
if (fclust)
freeclusters(fclust)
flushifdirty
return 0
if (mode == "w")
brwword(s+$1a, 0)
brwword(s+$14, 0)
brwlong(s+$1c, 0)
writelink := 0
direntry := dirptr
if (fclust)
freeclusters(fclust)
bufend := SECTORSIZE
fclust := 0
filesize := 0
frem := 0
return 0
elseif (mode == "a")
' this code will eventually be moved to seek
frem := filesize
freeentry := clustersize
if (fclust => endofchain)
fclust := 0
repeat while (frem > freeentry)
if (fclust < 2)
abort(-7) ' eof repeat while following chain
fclust := nextcluster
frem -= freeentry
floc := filesize & constant(!(SECTORSIZE - 1))
bufend := SECTORSIZE
bufat := frem & constant(SECTORSIZE - 1)
writelink := 0
direntry := dirptr
if (bufat)
sdspi.readblock(datablock, @buf)
frem := freeentry - (floc & (freeentry - 1))
else
if (fclust < 2 or frem == freeentry)
frem := 0
else
frem := freeentry - (floc & (freeentry - 1))
if (fclust => 2)
followchain
return 0
else
abort(-3) ' bad argument
if (mode <> "w" and mode <> "a")
return -1 ' not found
direntry := freeentry
if (direntry == 0)
abort(-2) ' no empty directory entry
' write (or new append): create valid directory entry
s := readbytec(direntry)
bytefill(s, 0, DIRSIZE)
bytemove(s, @padname, 11)
brwword(s+$1a, 0)
brwword(s+$14, 0)
i := pdate
brwlong(s+$e, i) ' write create time and date
brwlong(s+$16, i) ' write last modified date and time
if (direntry == sentinel and direntry + DIRSIZE < rootdirend)
brwword(readbytec(direntry+DIRSIZE), 0)
flushifdirty
writelink := 0
fclust := 0
bufend := SECTORSIZE
' return r (default return)
And this is my code for setting the date and time:
PUB SetSDcardTime 'Read the current time and date from the RTC RTC.readtime 'Set date and time variable in SDcard utility setdate(year, month, day, hour, minute, second) SDcard.setdate( RTC.clockYear, RTC.clockMonth, RTC.clockDate, RTC.clockHour, RTC.clockMinute, RTC.clockSecond ) RETURN

Comments
v2.6A TTA formatting, comments moved under method, some edited. Methods capitalized v2.6B TTA Nextfile method captures the create and modified datetimes as longs, methods GetCreated and GetModified return those datetimes as longs. Popen(s, mode) updates the created date location only when file is opened as mode = "w". The "modified" date/time location is updated on either mode="a" or mode="w".Thank you very much!