Commit Graph

24 Commits

Author SHA1 Message Date
Stephen Heumann 3551644355 Fix stack handling in localtime.
This was broken by commit 882af9e075.
2023-01-05 20:00:44 -06:00
Stephen Heumann 69765a96ef Use a variable to control use of Time Tool.
This ensures use of the Time Tool is fully under the control of the programmer, rather than potentially being affected by other things that may load it (like the Time Zone CDev). It also avoids calls to tiStatus in the default non-Time Tool code paths, and thereby allows them to work under Golden Gate.
2023-01-02 18:01:28 -06:00
Stephen Heumann c4d485e960 Implement timespec_get (C11).
This follows gmtime in using the Time Tool to get UTC time if it is active, but otherwise just using local time.
2023-01-01 21:33:00 -06:00
Stephen Heumann 44c3078ab3 mktime: force struct tm components to their normal ranges.
This is done by calling ~gmlocaltime after computing the time_t value in mktime.
2022-12-31 22:06:25 -06:00
Stephen Heumann 7e4f067c35 Compute tm_yday and tm_wday directly in ~gmlocaltime.
This avoids calling mktime (future versions of which may call ~gmlocaltime), and also deals correctly with time zones.
2022-12-31 19:10:36 -06:00
Stephen Heumann 882af9e075 Make gmlocaltime take a parameter for the struct tm to use.
This will be needed for gmtime_r/localtime_r, but also is a step toward using this code to normalize the struct tm values for mktime.
2022-12-30 18:46:51 -06:00
Stephen Heumann 3b0c1c2149 Fix gmtime() handling of times very near the limits of time_t.
The UTC time may be several hours before or after local time, and therefore the UTC time/date may be slightly outside the limits of what can be represented as a local time/date. This is now handled correctly.

This also more generally fixes handling of negative seconds/minutes/hours, which is also applicable to mktime().
2022-12-30 17:28:16 -06:00
Stephen Heumann 32c5fd94a1 Handle out-of-range months in mktime() input. 2022-12-29 23:54:10 -06:00
Stephen Heumann f15caf8096 Make gmtime/localtime properly support times near the limits of the time_t range.
They did not properly handle times in 1969 or 2105 (for the latter, they would infinite-loop).
2022-12-29 23:18:48 -06:00
Stephen Heumann b302a85fd6 Switch time "factor" code over to 0-based month indexing.
This matches both struct tm and ReadTimeHex, so it avoids needing to increment the values.

Also, simplify the time() code a little bit.
2022-12-29 22:53:37 -06:00
Stephen Heumann 17faeda1de Rework time "factor" routine to work for the full 32-bit time range.
ORCA/C uses an unsigned 32-bit time_t which should give a range up to 2105, but calculations on it were being done with signed types, causing them not to work correctly beyond 2036-2038. Now the factor routine, mktime(), and time() should work up to 2105. (In the case of time(), this assumes ReadTimeHex reports the time correctly.)

The factor routine actually computes a 64-bit time value. Currently, the rest of the code only takes the bottom 32 bits of it, but this could be extended if we ever wanted to switch to 64-bit time_t.
2022-12-29 22:31:31 -06:00
Stephen Heumann d30ee1a2e5 Adjust comments in time.asm to reflect actual starting date of time_t.
It was clearly supposed to be 1 Jan 1970, but it's actually not, probably because the number of days from 1 Jan 1900 to 1 Jan 1970 was miscalculated. Changing it now could potentially cause compatibility issues (especially for GNO, which uses time_t in some kernel call interfaces and file formats), so for now it is left as is and just documented appropriately.

Nothing in the C standards requires the time_t epoch to be 1 Jan 1970, so this does not cause any standards-compliance problem for the C standards. (It is different from POSIX, though.)
2022-12-29 14:25:24 -06:00
Stephen Heumann e2de990f4d strftime: use Time Tool Set to get time zone offset.
This is used for the %z conversion specifier (giving the time zone offset in +-HHMM format). The %Z conversion specifier (giving the locale's time zone name or abbreviation) also prints the same thing for now.

As with gmtime, this will only use the Time Tool Set if it has already been started. Otherwise, these conversions simply produce no output.
2022-12-28 19:55:48 -06:00
Stephen Heumann 4019e9f370 gmtime: support time zone adjustment with Time Tool Set.
If the Time Tool Set (tool 56, by Geoff Weiss) is present and active, gmtime will use it (plus the DST flag) to determine the local time offset from UTC, allowing it to produce the correct UTC time. If not, it will still treat local time as being equal to UTC, like it did previously.

The library code will not try to load or start the Time Tool Set, so the program will have to do that before calling gmtime if it wants to use this functionality.
2022-12-28 19:46:49 -06:00
Stephen Heumann 84f471474a Use newer, more efficient ph2/ph4 macros throughout ORCALib.
These push DP values with pei, rather than lda+pha as in the old versions of the macros.
2022-06-30 19:01:47 -05:00
Stephen Heumann 5ad86f4a0b Implement strftime.
This is intended to be a complete implementation of strftime as specified in C17, although it lacks meaningful support for time zones or non-C locales.
2021-09-26 20:31:15 -05:00
Stephen Heumann 690ee7137f Add a function to get the proper value of CLOCKS_PER_SEC.
This may be either 50 or 60, depending on the system's video frequency setting (50Hz PAL or 60Hz NTSC). The video setting can be determined by inspecting bit 4 of the LANGSEL soft switch, documented in Appendix E of the Apple IIGS Firmware Reference.
2021-08-23 19:00:09 -05:00
Stephen Heumann e5360c9605 Spellcheck comments. 2020-02-16 13:29:53 -06:00
Stephen Heumann 573bc6efa9 Use consistent indentation within files.
Tabs have been expanded to spaces in several files that use mainly spaces for indentation.

The files ctype.asm, stdio.asm, and string.asm consistently use tabs for indentation. The tabs in these files have been left alone, except that a few tabs between sentences in comments were changed to spaces.  One space-indented line in stdio.asm was changed to use a tab.
2020-02-16 13:28:18 -06:00
Stephen Heumann 44dfc1d1d6 Prevent localtime() from potentially giving incorrect tm_isdst values.
This could happen when it was called for a time other than the present, because it set tm_isdst based on the current value of the DST flag in BRAM, which is valid only for the current time.

Now it works as follows: If localtime() is passed the time_t value that was produced by the most recent call to time(), it gives the DST setting in effect at the time of that call.  Otherwise, it sets tm_isdst to -1, indicating that the correct value is unknown.

This is about the best we can do without having a full timezone library/database. It should give the right tm_isdst value in probably the most common case, and avoids giving an incorrect value in any case (assuming the system's DST flag is right).

This fixes #18.
2020-02-02 12:52:42 -06:00
Stephen Heumann 21d34a30ce mktime: tm_yday should be indexed from 0 for January 1st, not 1.
This fixes the libca07.c test case.
2018-03-09 17:38:55 -06:00
Stephen Heumann a77e44d7b5 Fix asctime() to properly print years 1000 through 9999.
Also, use a leading space rather than a leading 0 in days 1 through 9.

This fixes the libca11.c test case.
2018-03-09 13:10:53 -06:00
Kelvin Sherlock 578bda8439 CR -> LF 2017-10-31 13:14:07 -04:00
mikew50 954c3a02b5 ORCA libraries, from the Opus ][ CD 2017-10-01 18:00:58 -06:00