Compare commits

..

971 Commits

Author SHA1 Message Date
Dianne Skoll
2e161a1bc1 Rebuild configure from configure.in 2021-01-12 10:13:13 -05:00
Dianne Skoll
204bb00060 Update docs; prep 3.3.4 release. 2021-01-12 10:13:00 -05:00
Dianne Skoll
d6029a54aa Remove unnecessary line of code; add space after "sub" operator. 2021-01-10 17:38:25 -05:00
Dianne Skoll
f99b5c5a66 Update man page date. 2021-01-05 21:30:21 -05:00
Dianne Skoll
2df4119c1a Fix test. 2021-01-05 19:14:16 -05:00
Dianne Skoll
d06b4e5dcd Update copyright date 2021-01-05 19:13:11 -05:00
Dianne Skoll
bf8a25137d Right-align moon indicators when day numbers are left-aligned. 2021-01-05 19:08:10 -05:00
Dianne Skoll
0f302ad0fc Add clarifying comment. 2021-01-05 17:38:33 -05:00
Dianne Skoll
e3d6b283c5 Fix setpagedevice for landscape mode. 2021-01-05 17:23:47 -05:00
Dianne Skoll
2e3ed09039 Update test for setpagedevice patch. 2021-01-05 17:20:27 -05:00
Dianne Skoll
37971a3f07 Set page size (patch from Jonathan Kamens) 2021-01-05 17:19:20 -05:00
Dianne Skoll
2a1960f257 Add TkRemind option for drawing day numbers on left. 2021-01-05 16:39:57 -05:00
Dianne Skoll
350564c304 Add "-x" option to rem2ps to put day numbers at the top-left of each box.
By default, day numbers are placed at the top-right.
2021-01-05 16:32:20 -05:00
Dianne Skoll
9e2a9fea37 Use "-q" option with inotifywait 2020-12-30 11:01:25 -05:00
Dianne Skoll
3592b43629 If inotifywait is available, use it to react instantly to changes to reminder file/dir. 2020-12-30 10:59:00 -05:00
Dianne Skoll
becf1fc459 Wait 100ms to update after changes. 2020-12-29 12:48:24 -05:00
Dianne Skoll
2bccd058ed Refactor code in TkRemind to prepare for possibly using inotify to react to changes. 2020-12-29 12:46:23 -05:00
Dianne Skoll
12c6621051 Fix typo 2020-11-09 17:32:16 -05:00
Dianne Skoll
504bc6a875 Update docs 2020-11-09 08:25:28 -05:00
Dianne Skoll
9cfdd0b53f Bump version to 3.3.3. 2020-11-09 07:26:14 -05:00
Dianne Skoll
d59024f399 Fix startup crash if ShowTodaysReminders option is set. 2020-11-09 07:23:19 -05:00
Dianne Skoll
24e0178d1a Fix tests for 3.3.2 release. 2020-11-08 16:01:57 -05:00
Dianne Skoll
1ede5775f2 Prep for 3.3.2 release. 2020-11-08 16:01:39 -05:00
Dianne Skoll
a5c9b07052 Fix for calendar alignment for reminders with embedded tabs.
Convert all whitespace chars to space in calendar mode.
2020-11-03 08:41:24 -05:00
Dianne Skoll
22353d4833 Fix typo (patch from Yigit Sever) 2020-11-02 08:31:28 -05:00
Dianne Skoll
7499ada891 Properly fix combining-char-word-wrapping. 2020-11-01 12:05:21 -05:00
Dianne Skoll
3f0a4e5c39 Fix another instance of mis-counting display width. 2020-11-01 10:13:51 -05:00
Dianne Skoll
b8d6472974 Add UTF-8 test. 2020-11-01 10:06:48 -05:00
Dianne Skoll
6358297724 Fix column misalignment with UTF-8 text. 2020-11-01 10:03:32 -05:00
Dianne Skoll
4f6dcde980 Upper-case section references.
Prevent potential null pointer dereference.
2020-10-31 16:57:13 -04:00
Dianne Skoll
8a7985c48e Highlight that longitude sign is opposite from the usual convention. 2020-10-12 18:54:26 -04:00
Dianne Skoll
4ddbe54e55 Fix typo 2020-09-25 22:27:48 -04:00
Dianne Skoll
ef0bf73a29 Document MAYBE-UNCOMPUTABLE. 2020-09-25 22:20:16 -04:00
Dianne Skoll
beda9014d8 Add test for MAYBE-UNCOMPUTABLE 2020-09-25 22:11:56 -04:00
Dianne Skoll
498a429b2c Add MAYBE-UNCOMPUTABLE modifier to trigger. 2020-09-25 22:08:49 -04:00
Dianne Skoll
6aa2aa0fb3 Align system vars in output. 2020-09-20 17:43:51 -04:00
Dianne Skoll
1bef88fccd Update released notes. 2020-09-20 17:40:58 -04:00
Dianne Skoll
8308068067 Don't bother aligning "DUMP" output.
It looks ridiculous with 64-char long variable names.
2020-09-20 17:39:33 -04:00
Dianne Skoll
8385c7f1b0 Update custom.h 2020-09-20 17:35:24 -04:00
Dianne Skoll
0537d02fef Increase max variable length from 16 to 64 characters.
Modern computers have plenty of memory, so meh.
2020-09-20 17:32:22 -04:00
Dianne Skoll
c33a1a3b0b Mention that variables are global. 2020-09-20 12:45:29 -04:00
Dianne Skoll
fd39999128 Fix bugs where month numbers with leading zeros are misinterpreted as octal instead of decimal.
Reported by Peter Geddes.
2020-09-13 12:34:27 -04:00
Dianne Skoll
0aa40094fa Make TwentyFourHourMode global. 2020-08-18 15:24:19 -04:00
Dianne Skoll
e3bbbe07be Respect 24-hour mode option. 2020-08-18 15:24:13 -04:00
Dianne Skoll
5633798d33 Document that time is fed to reminder command. 2020-08-18 15:24:09 -04:00
Dianne Skoll
0e7e1b1b75 When feeding reminder on stdin, prefix with "$time: " 2020-08-18 15:24:04 -04:00
Dianne Skoll
4d3790bc1a More tweaking of defs.rem to remove cruft and modernize usage. 2020-08-18 15:24:00 -04:00
Dianne Skoll
2002c7f1f8 Fix up defs.rem. 2020-08-18 15:23:51 -04:00
Dianne Skoll
1be14e99a2 Update docs for -itkremind=1 and -itkprint=1 options in TkRemind. 2020-06-11 15:06:09 -04:00
Dianne Skoll
78efdaf85f Fix bug that broke printing by putting cmdline options in wrong spot. 2020-06-10 10:26:06 -04:00
Dianne Skoll
0e98a1c656 Always set tkremind=1; set tkprint=1 if we're printing. 2020-06-10 10:22:46 -04:00
Dianne Skoll
7aa483e201 Fix bug reported by Jurgen Bollerhey
I have a
"REM Mon SPECIAL WEEK (W[weekno()])"
in my reminders file.
With tkremind -m the week number is displayed on the 2nd column which is
Tuesday and the date of this Tuesday is taken from the monday of the
next week, sometimes of Monday the same week.
2020-03-30 11:29:19 -04:00
Dianne Skoll
a6dbf05af4 Update WHATSNEW. 2020-03-20 09:18:48 -04:00
Dianne Skoll
8ab78fd8be Suppress compile warnings on Ubuntu 18.04 2020-03-19 20:27:45 -04:00
Dianne Skoll
4f119031a4 One more warning to suppress. 2020-03-19 20:24:53 -04:00
Dianne Skoll
19bdd6c2db Avoid warning about ignoring return value of fgets. 2020-03-19 20:24:01 -04:00
Dianne Skoll
f1557b8243 Try to suppress fallthrough warning. 2020-03-19 20:21:29 -04:00
Dianne Skoll
85f96e2e01 Update man page. 2020-03-14 11:37:11 -04:00
Dianne Skoll
47331cd919 Make ampm() function accept a DATETIME and obey $TimeSep, $DateSep and $DateTimeSep 2020-03-14 11:32:35 -04:00
Dianne Skoll
d9f18ed6a7 Don't use many-json2dict 2020-03-03 11:43:54 -05:00
Dianne Skoll
efa4816371 Properly-form JSON output. 2020-03-03 10:36:01 -05:00
Dianne Skoll
2dc8c63adb Proper prefix for beta versions. 2020-02-29 09:38:51 -05:00
Dianne Skoll
c3c1781021 Update COPYRIGHT date. 2020-02-28 08:56:49 -05:00
Dianne Skoll
cd39480a98 Remove extraneous spaces. 2020-02-27 16:50:44 -05:00
Dianne Skoll
281a1a206e Implement JSONQUEUE daemon command. 2020-02-27 15:18:23 -05:00
Dianne Skoll
cbff2a7bf2 Document ampm() 2020-02-27 08:39:21 -05:00
Dianne Skoll
2a08be8fd0 Fix up unit tests. 2020-02-26 17:43:47 -05:00
Dianne Skoll
0826678209 Make coerce from string to time and datetime accept ampm 2020-02-26 17:41:51 -05:00
Dianne Skoll
f2e421bfa5 Add acceptance tests for ampm() function. 2020-02-26 17:25:09 -05:00
Dianne Skoll
ce53a9b91a Add "ampm" built-in function. 2020-02-26 17:21:34 -05:00
Dianne Skoll
b166b1cf82 Fix up test file. 2020-02-24 15:17:07 -05:00
Dianne Skoll
d09fbb03b2 Bump version to 3.3.1. 2020-02-24 15:16:20 -05:00
Dianne Skoll
7a835f3b10 Update docs. 2020-02-23 16:02:59 -05:00
Dianne Skoll
6b991cdf9c Refactor saving of trigger info. 2020-02-23 11:38:17 -05:00
Dianne Skoll
018e9d0323 JSON can handle newlines (the literal newlines will be escaped to "\n" by the JSON writer.) 2020-02-23 11:17:59 -05:00
Dianne Skoll
f499ae096f Don't include filename or line number in synthesized tag. 2020-02-23 11:15:38 -05:00
Dianne Skoll
725e046a15 Fix bug in recording trigdate() for SATISFY-type reminders. :( 2020-02-22 19:15:24 -05:00
Dianne Skoll
275b1f62b6 For overlapping reminders, prefer the *later* version. 2020-02-22 16:50:42 -05:00
Dianne Skoll
6e58dea198 Handle overlapping events better. 2020-02-22 16:30:08 -05:00
Dianne Skoll
ad4e62c8c3 Test specifying DURATION as an integer. 2020-02-22 12:48:07 -05:00
Dianne Skoll
a5768d55d8 Update man page to document integer form of DURATION. 2020-02-22 12:46:57 -05:00
Dianne Skoll
7db49971c8 Update man page. 2020-02-22 12:40:32 -05:00
Dianne Skoll
45ca6631ac Make sure AM/PM is case-insensitive. 2020-02-22 12:32:52 -05:00
Dianne Skoll
d51944f36c Allow duration to be specified as a single number, meaning minutes.
Don't convert 90-99 to 1990-1999 when parsing numbers.
2020-02-22 12:31:17 -05:00
Dianne Skoll
037c79fb0f Allow times to have am/pm specifications. 2020-02-22 12:24:37 -05:00
Dianne Skoll
993373414f Parse times and datetimes with trailing am/pm 2020-02-22 12:14:18 -05:00
Dianne Skoll
38a0a9992a Leave a space after the asterisk row. 2020-02-12 11:19:30 -05:00
Dianne Skoll
a82bbe3776 Highlight today in month mode also. 2020-02-12 11:17:21 -05:00
Dianne Skoll
a32ba217ba Update man page. 2020-02-08 15:11:15 -05:00
Dianne Skoll
d322cf54ac Allow $FormWidth to be as large as 500. 2020-02-08 15:10:48 -05:00
Dianne Skoll
b1d07a231d Document $FormWidth. 2020-02-08 15:06:09 -05:00
Dianne Skoll
97851a08e6 Clamp min cal width at 72 2020-02-08 15:04:59 -05:00
Dianne Skoll
8547b30a8f Set $FormWidth to terminal width - 8 on startup. 2020-02-08 15:04:48 -05:00
Dianne Skoll
405c7d9ed0 Set release date. 2020-01-31 11:17:55 -05:00
Dianne Skoll
ac5b641d93 Note that back-ends MUST ignore unknown SPECIALs. 2020-01-30 16:07:57 -05:00
Dianne Skoll
06a79989c0 Minor tweaks. 2020-01-28 15:16:41 -05:00
Dianne Skoll
671db64436 Fix various typos. 2020-01-28 09:51:12 -05:00
Dianne Skoll
33344cefe6 Fix typo 2020-01-28 09:47:06 -05:00
Dianne Skoll
5ef0341537 Avoid memory leak. 2020-01-28 09:43:42 -05:00
Dianne Skoll
6abca08189 Add test to ensure rem2ps ignores unknown SPECIALs. 2020-01-28 09:42:13 -05:00
Dianne Skoll
35670ce651 Update docs 2020-01-28 09:38:06 -05:00
Dianne Skoll
e230d53d84 Ignore unknown SPECIALs in rem2ps. 2020-01-28 09:37:35 -05:00
Dianne Skoll
88537a3471 Remove ancient pointer to doe.carleton.ca 2020-01-28 09:29:42 -05:00
Dianne Skoll
7c9d74da73 Fix typo 2020-01-27 16:46:57 -05:00
Dianne Skoll
3b582935ee Sign beta tarballs too. 2020-01-27 16:46:07 -05:00
Dianne Skoll
508fafb875 Update WHATSNEW. 2020-01-27 16:28:57 -05:00
Dianne Skoll
6f718f0fe5 Update rem2ps man page. 2020-01-27 13:29:33 -05:00
Dianne Skoll
53acbf2052 Don't swallow %" %" markers in -ppp mode. 2020-01-27 13:21:48 -05:00
Dianne Skoll
1606dbbe77 Rework -@ option and tests. 2020-01-27 11:49:41 -05:00
Dianne Skoll
adced3ac6c Rework -@ option to be n,m 2020-01-27 11:44:16 -05:00
Dianne Skoll
14f207140a Better clamping algorithm for true colors 2020-01-27 11:31:57 -05:00
Dianne Skoll
d2da32de6c Don't hard-code number. 2020-01-26 18:26:03 -05:00
Dianne Skoll
e5d6a36f05 Update WHATSNEW 2020-01-26 18:10:11 -05:00
Dianne Skoll
68ecfcf876 Update test for change to rem2ps 2020-01-26 18:09:27 -05:00
Dianne Skoll
fcb14b9dfe Add PageBoundingBox comment. 2020-01-26 18:09:06 -05:00
Dianne Skoll
6a4b4257a6 Fix compilation failure on pre-C99 compilers. 2020-01-26 17:47:00 -05:00
Dianne Skoll
385b57e269 Update whatsnew 2020-01-25 17:43:10 -05:00
Dianne Skoll
a8e81e3984 Update WHATSNEW. 2020-01-25 17:41:47 -05:00
Dianne Skoll
46c5f0e752 Update man page for exact color setting. 2020-01-25 16:18:09 -05:00
Dianne Skoll
454d859fdd Support true RGB coloring. 2020-01-25 16:16:51 -05:00
Dianne Skoll
57134a182c Make SPECIALs case-insensitive. 2020-01-25 16:07:18 -05:00
Dianne Skoll
5801e143ea Make specials case-insensitive. 2020-01-25 16:04:53 -05:00
Dianne Skoll
4e0d0ff98b Test Xterm 256-color mode. 2020-01-25 15:16:30 -05:00
Dianne Skoll
d4ac1849ae Add comment for Xterm 256 colors. 2020-01-25 15:12:13 -05:00
Dianne Skoll
c16ac1bd8c Support 256-color mode on XTerm and other terminals. 2020-01-25 15:06:43 -05:00
Dianne Skoll
16222ac3bc Fix to man page. 2020-01-25 14:35:20 -05:00
Dianne Skoll
8d88931fb1 Fix indentation. 2020-01-25 14:27:25 -05:00
Dianne Skoll
63f0356e70 Fix man page wording. 2020-01-25 14:26:32 -05:00
Dianne Skoll
786b0dee6f Add test for =@ 2020-01-25 14:23:52 -05:00
Dianne Skoll
e7ef9dc295 Document -@ 2020-01-25 14:12:56 -05:00
Dianne Skoll
f59461b95d Convert black-on-black or white-on-white to grey. 2020-01-25 14:00:28 -05:00
Dianne Skoll
566a86b9fd Obey default color settings. 2020-01-25 11:29:06 -05:00
Dianne Skoll
8589a3730d Put -@[n] in help. 2020-01-25 11:13:50 -05:00
Dianne Skoll
c05fd366df Implement -@, -@0 and -@1 options to colorize reminders. 2020-01-25 11:12:10 -05:00
Dianne Skoll
fc9fd1e53c Start adding support for colored reminders in Agenda Mode. 2020-01-24 16:31:01 -05:00
Dianne Skoll
a5e6eb9f7c Add -@ commandline option. Yuck. 2020-01-24 16:26:55 -05:00
Dianne Skoll
a9430fea5f Make Remind adjust calendar to fit terminal. 2020-01-18 15:11:28 -05:00
Dianne Skoll
828a0d6589 Emit prevmonthyear and nextmonthyear items in -ppp format. 2020-01-18 14:52:17 -05:00
Dianne Skoll
32601da748 Update tests. 2020-01-18 14:48:27 -05:00
Dianne Skoll
ac50f119cf Document that -pp and -ppp enable -l 2020-01-18 14:45:23 -05:00
Dianne Skoll
7622ebaa0a Document remind -ppp format. 2020-01-18 14:43:21 -05:00
Dianne Skoll
a586d5cd37 Fix bug that incorrectly printed # fileinfo lines for -ppp format. 2020-01-18 14:43:04 -05:00
Dianne Skoll
edbc88bd19 Reformat error message. 2020-01-16 20:00:38 -05:00
Dianne Skoll
94f99f3414 Make rem2ps bail out if fed "-ppp"-format. 2020-01-16 19:59:30 -05:00
Dianne Skoll
fd4f84349e Include filename and lineno in tag synthesis. 2020-01-16 19:19:13 -05:00
Dianne Skoll
f86350b2ff More man page tweakage. 2020-01-16 18:56:28 -05:00
Dianne Skoll
564b72066a Document $DefaultColor 2020-01-16 18:53:30 -05:00
Dianne Skoll
2890c52090 Fix typo in man page 2020-01-15 11:27:43 -05:00
Dianne Skoll
c1d45485c1 Update test suite. 2020-01-15 09:20:31 -05:00
Dianne Skoll
8b2a69cf8d Do a small bit of refactoring to get rid of some copy/paste code. 2020-01-15 09:18:32 -05:00
Dianne Skoll
034c1341b3 Fix typos. 2020-01-14 21:47:26 -05:00
Dianne Skoll
29bbf1a030 Be strict in what we accept for SET $DefaultColor "r g b" 2020-01-14 21:44:08 -05:00
Dianne Skoll
be6661d6be Don't assume a potentially-colored reminder unless it's MSG/MSF/CAL type. 2020-01-14 21:43:46 -05:00
Dianne Skoll
3f876e792c Reset $DefaultColor each time we iterate. 2020-01-14 21:15:27 -05:00
Dianne Skoll
f2457b90ff Add patch for $DefaultColor, courtesy of Tim Chase. 2020-01-14 21:07:20 -05:00
Dianne Skoll
e999e9009b Minor formatting tweak. 2020-01-14 20:17:38 -05:00
Dianne Skoll
46326c001b Output true JSON if you invoke as "remind -ppp" 2020-01-14 20:09:24 -05:00
Dianne Skoll
b84c2c403c Add more balloon help. 2020-01-13 21:19:45 -05:00
Dianne Skoll
861ad72187 Add popup help. 2020-01-13 18:26:40 -05:00
Dianne Skoll
7dbbc34ccc Make Remind compile on older gcc that doesn't allow declarations in for(...) 2020-01-13 10:00:25 -05:00
Dianne Skoll
4ea45d1d14 Update rem2ps man page. 2020-01-12 20:03:43 -05:00
Dianne Skoll
c1b9243e2f Document new REM2PS format. 2020-01-12 19:56:45 -05:00
Dianne Skoll
a41c40c7a4 Document -pp option. 2020-01-12 19:24:21 -05:00
Dianne Skoll
318d4547ef Use r, g, b settings from SHADE special. 2020-01-12 18:11:35 -05:00
Dianne Skoll
6f98b60a6a Output "r", "g", "b" for shade-style reminders. 2020-01-12 18:09:41 -05:00
Dianne Skoll
baa8f7f3c4 Add test that OMITFUNC raises nonconst_expr indicator. 2020-01-12 17:51:06 -05:00
Dianne Skoll
6297622072 Write JSON using English day names. 2020-01-12 17:47:41 -05:00
Dianne Skoll
9f3ba0bf2b More intelligent filling out of GUI. 2020-01-12 17:27:50 -05:00
Dianne Skoll
9591dec708 Write out fully-specified dates in Reminders more compactly. 2020-01-12 17:15:38 -05:00
Dianne Skoll
ee2d0b7518 Production file location! 2020-01-12 14:05:55 -05:00
Dianne Skoll
2d46749c58 Add blank line when *first* creating AppendFile. 2020-01-12 14:01:20 -05:00
Dianne Skoll
494664d1b6 Take out blank line from warning header lines. 2020-01-12 14:00:04 -05:00
Dianne Skoll
49686210ae Better reverse-engineering of ordinal. 2020-01-12 13:57:25 -05:00
Dianne Skoll
ddfa44188b Reset HighestTagSoFar when we rewrite the appendfile after deletion. 2020-01-12 13:52:17 -05:00
Dianne Skoll
73cf93d27b Renumber tags when we delete a tagged reminder. 2020-01-12 13:34:22 -05:00
Dianne Skoll
60d1a34bf0 Fix up AM/PM handling; delete old comment lines. 2020-01-12 13:28:45 -05:00
Dianne Skoll
6f80986801 New version of tkremind seems to be decent... 2020-01-12 13:14:32 -05:00
Dianne Skoll
2078f087b2 An OMITFUNC should set the nonconst_expr flag. 2020-01-12 13:06:55 -05:00
Dianne Skoll
68d110826e First version of TkRemind that can reverse-engineer reminder without needing comments to set up GUI. 2020-01-12 12:45:34 -05:00
Dianne Skoll
9fb04c54ae Start work on reverse-engineering reminder dialog from JSON instead of relying on comments. 2020-01-11 19:08:35 -05:00
Dianne Skoll
d82314594b Make rem2html understand JSON interchange format. 2020-01-10 15:06:59 -05:00
Dianne Skoll
ad169a5248 Eliminate compiler warnings. 2020-01-10 13:57:13 -05:00
Dianne Skoll
a9bab81226 Test that rem2ps can parse "remind -pp" output. 2020-01-10 13:48:58 -05:00
Dianne Skoll
fa63a9ba51 Add comments. 2020-01-10 13:46:20 -05:00
Dianne Skoll
1e7a630737 rem2ps can read the new-style JSON output of "remind -pp" 2020-01-10 13:41:27 -05:00
Dianne Skoll
de1afce8da Suppress unused param warnings. 2020-01-09 18:53:00 -05:00
Dianne Skoll
ac3cb19c26 Simplify code. 2020-01-09 18:42:14 -05:00
Dianne Skoll
af0479d11d Start preparing rem2ps for parsing JSON input. 2020-01-09 18:38:08 -05:00
Dianne Skoll
0d9c04707f Output nonconst_expr and if_depth indicators in JSON mode. 2020-01-08 08:42:23 -05:00
Dianne Skoll
c2218f133b Preserve RGB info for a COLOR reminder. 2020-01-07 13:27:22 -05:00
Dianne Skoll
1ad0645fab Only print rawbody if it differs from body. 2020-01-06 22:25:49 -05:00
Dianne Skoll
3c16f6839a Pass raw body through to back-end in JSON mode. 2020-01-06 22:19:22 -05:00
Dianne Skoll
e8bac1e469 More info over JSON via -pp commandline switch. 2020-01-05 17:15:37 -05:00
Dianne Skoll
b3b69596f4 Output SKIP value in JSON. 2020-01-05 12:18:10 -05:00
Dianne Skoll
6a7bcb0956 Print the "wd" entry as array of weekday names. 2020-01-05 12:15:20 -05:00
Dianne Skoll
f18a0704c1 More work on emitting JSON. 2020-01-05 12:10:05 -05:00
Dianne Skoll
d6f24b7c1e rem2ps will only support "remind -p" protocol and not "remind -pp" 2020-01-03 18:00:21 -05:00
Dianne Skoll
e2c9bbf94c Start working on JSON-based alternate "remind -p" protocol. 2020-01-03 17:24:01 -05:00
Dianne Skoll
f53aa4f656 Start working on Version 2 of Rem2PS protocol. 2020-01-03 16:51:47 -05:00
Dianne Skoll
a7ab9b8bf8 Update release date. :( 2020-01-03 13:14:53 -05:00
Dianne Skoll
4448271166 Update WHATSNEW. 2020-01-03 13:05:33 -05:00
Dianne Skoll
4861b535a2 Use nicer moon graphics. 2020-01-03 13:02:16 -05:00
Dianne Skoll
167f0100c7 Minor tweaks. 2020-01-03 12:43:22 -05:00
Dianne Skoll
b0367c7a5c Update README.UNIX. 2020-01-02 14:45:31 -05:00
Dianne Skoll
4ae8ad52f5 Update WHATSNEW. 2020-01-02 14:42:46 -05:00
Dianne Skoll
dbd64828ab Use nicer moon images. 2020-01-02 11:39:29 -05:00
Dianne Skoll
158ca882ba Fix typo 2020-01-01 18:32:24 -05:00
Dianne Skoll
623ed44608 Update man page. 2020-01-01 18:30:46 -05:00
Dianne Skoll
f13b867626 Update WHATSNEW 2020-01-01 18:04:20 -05:00
Dianne Skoll
ff85325886 Support DATETIME - TIME 2020-01-01 18:00:22 -05:00
Dianne Skoll
aa830116ea Update copyright dates, etc. 2020-01-01 10:13:50 -05:00
Dianne Skoll
1a4504ba28 Catch date overflow if we use a crazy-long DURATION. 2020-01-01 10:01:02 -05:00
Dianne Skoll
20365c4627 Document DURATION 00:00 2020-01-01 09:50:13 -05:00
Dianne Skoll
fae8f89ed6 Handle self-overlapping events correctly; avoid 0-duration events; document
self-overlapping behaviour.
2020-01-01 09:45:28 -05:00
Dianne Skoll
a0689999fe Adjust duration_days to not include zero-duration tails. 2020-01-01 09:31:55 -05:00
Dianne Skoll
a42a0ab032 Update WHATSNEW. 2019-12-31 23:32:18 -05:00
Dianne Skoll
b66eb5d3ec Suppress printing subdirectory entry for "make test" 2019-12-31 23:11:55 -05:00
Dianne Skoll
8b4bc0f56e Print warning if we truncate a function name. 2019-12-31 22:54:22 -05:00
Dianne Skoll
c9d984983f Add a warning if we truncate variable names. 2019-12-31 22:50:42 -05:00
Dianne Skoll
47125b051a Clarify that IFTRIG can't take SATISFY 2019-12-31 22:41:34 -05:00
Dianne Skoll
e5e6ff6031 Return "Can't compute trigger" if SATISFY uses up too many iterations. 2019-12-31 22:26:23 -05:00
Dianne Skoll
9f0aedb608 Don't suppress errors in trigger computation. 2019-12-31 22:13:53 -05:00
Dianne Skoll
08af33ece5 Don't allow DURATION without an AT. 2019-12-31 21:51:34 -05:00
Dianne Skoll
9b421d0b94 Fix typo 2019-12-31 21:44:49 -05:00
Dianne Skoll
7bd8d2dd25 Tweak formatting. 2019-12-31 21:40:32 -05:00
Dianne Skoll
a7c4879a0a Update man page and WHATSNEW. 2019-12-31 21:38:18 -05:00
Dianne Skoll
8b3585a6b8 Add test for trigeventstart() and trigeventduration() 2019-12-31 21:12:44 -05:00
Dianne Skoll
a223149aee Add trigeventstart() and trigeventduration() functions. 2019-12-31 21:09:21 -05:00
Dianne Skoll
9185341b0c Add a test. 2019-12-31 19:14:15 -05:00
Dianne Skoll
bf2d707e13 Skip duration_days at least in each SATISFY loop. 2019-12-31 18:51:22 -05:00
Dianne Skoll
f081e5c54d Update test. 2019-12-31 18:42:10 -05:00
Dianne Skoll
18a3db0f31 Fix interation between multi-day events and SATISFY. 2019-12-31 18:41:25 -05:00
Dianne Skoll
d2c115127d Add a FIXME. 2019-12-31 18:02:49 -05:00
Dianne Skoll
c12e7e1b8f Update tests with new version. 2019-12-31 17:47:40 -05:00
Dianne Skoll
d3495ab3aa Update version to 3.2.0. Events spanning >1 day are a major new feature. 2019-12-31 17:46:40 -05:00
Dianne Skoll
b93a7a6195 Update tests. 2019-12-31 17:43:46 -05:00
Dianne Skoll
e5519a8498 Handle events that span >1 day. 2019-12-31 17:39:26 -05:00
Dianne Skoll
eb2256f873 Use proper arrow icons instead of text <- and -> 2019-12-30 20:51:37 -05:00
Dianne Skoll
637b137b1c Use open |foo rather than exec to handle cmdline option parsing more uniformly. 2019-12-30 20:27:12 -05:00
Dianne Skoll
e2d14e73bf Update copyright date. 2019-12-30 11:18:01 -05:00
Dianne Skoll
fbbffb4672 Bump version to 3.1.18 and copyright year to 2020. 2019-12-30 11:15:00 -05:00
Dianne Skoll
422e098727 Don't use a static coerce_buf 2019-12-30 11:02:09 -05:00
Dianne Skoll
87347e30b2 Make string concatenation more efficient. 2019-12-30 10:59:32 -05:00
Dianne Skoll
3314ce9823 Update WHATSNEW 2019-12-30 10:42:17 -05:00
Dianne Skoll
402c1fe614 Proper fix. 2019-12-30 10:37:30 -05:00
Dianne Skoll
1d57856aa8 Avoid startup error if ShowTodaysReminders is true and ExtraRemindArgs is empty. 2019-12-30 10:34:37 -05:00
Dianne Skoll
c027c215d6 Update WHATSNEW 2019-12-29 21:03:27 -05:00
Dianne Skoll
fa0428b9fe Fix compile error for Romanian language; avoid compiler warning for non-English languages. 2019-12-29 19:08:48 -05:00
Dianne Skoll
b01c499ce5 Tweak man page. 2019-12-29 18:53:29 -05:00
Dianne Skoll
4e5033dd24 Implement adding DATETIME+TIME, TIME+DATETIME and TIME+TIME 2019-12-29 18:46:10 -05:00
Dianne Skoll
00863f3830 Add header file dependency. 2019-12-28 17:46:17 -05:00
Dianne Skoll
2d4b35e8b9 Add tests for introspection functions. 2019-12-28 17:28:31 -05:00
Dianne Skoll
6e4f2b9466 Implement remaining trigger introspection functions. 2019-12-28 17:09:05 -05:00
Dianne Skoll
9a6fc0253b Clear last triggers in all necessary spots. 2019-12-28 16:42:10 -05:00
Dianne Skoll
3180c781ed Start working on making bits of the trigger and time trigger introspectable. 2019-12-28 16:37:47 -05:00
Dianne Skoll
632152e8b6 Remember the last trigger and time trigger. 2019-12-28 16:24:16 -05:00
Dianne Skoll
1048f7e98d Add TAGS to omitted files. 2019-12-28 16:17:32 -05:00
Dianne Skoll
3de265216e Document $MaxStringLen 2019-11-21 11:41:25 -05:00
Dianne Skoll
2bdcadc7ab Minor cleanups. 2019-11-21 11:36:49 -05:00
Dianne Skoll
421ddfc68e Catch date overflow in slide() function. 2019-11-21 11:06:00 -05:00
Dianne Skoll
41594bc1ac Update release notes. 2019-11-15 11:14:23 -05:00
Dianne Skoll
e85199d464 Remove obsolete line. 2019-11-15 11:08:04 -05:00
Dianne Skoll
a6ee3bc704 Use git-archive to create tarball. 2019-11-15 11:06:19 -05:00
Dianne Skoll
2909106f30 Update copyright date. 2019-11-15 10:57:01 -05:00
Dianne Skoll
05b97aabb2 Sign releases. 2019-11-15 10:56:40 -05:00
Dianne Skoll
84af60d817 Delete COMMIT_EDITMSG when syncing to public git repo. 2019-11-14 17:04:43 -05:00
Dianne Skoll
72403a2512 Warn if "OMIT a THROUGH b" has a > b 2019-11-14 11:09:51 -05:00
Dianne Skoll
4ec619d646 Update copyright date. 2019-11-07 20:52:38 -05:00
Dianne Skoll
6178a627a0 Fix bug that prevented warning if we redefine a built-in function. 2019-11-07 20:50:35 -05:00
Dianne Skoll
3095fd7e4a Enable warning-free compilation even with -Wextra. 2019-11-04 16:35:14 -05:00
Dianne Skoll
74a6041760 Update version to 03.01.17. 2019-11-04 16:18:56 -05:00
Dianne Skoll
96127e37ff Update man page. 2019-11-04 16:16:15 -05:00
Dianne Skoll
df5484ea35 Add test for "SCANFROM -n" form. 2019-11-04 16:10:53 -05:00
Dianne Skoll
0ae3dae030 Allow shortand: SCANFROM -n meaning SCANFROM [today() - n] 2019-11-04 16:08:44 -05:00
Dianne Skoll
e5979139ac Fix typo. 2019-02-13 11:04:20 -05:00
Dianne Skoll
f81f6deb20 Apply patch from Dov Feldstern to fix Adar behaviour. 2018-12-11 10:05:11 -05:00
Dianne Skoll
f9951909d8 First part of patch to fix ADAR behaviour 2018-12-11 10:04:05 -05:00
Dianne Skoll
bbda972b05 Properly react to changes in extra remind args. 2018-12-07 14:54:02 -05:00
Dianne Skoll
4445e9c434 Add "Extra remind options" option. 2018-12-07 14:47:47 -05:00
Dianne Skoll
709adacac2 Add helper script to sync to dianne.skoll.ca git repo 2018-11-29 11:18:35 -05:00
Dianne Skoll
9841cdd355 When dumping queue contents, omit expired reminders. 2018-11-28 14:27:40 -05:00
Dianne Skoll
4cabe5fd71 Update docs/WHATSNEW with release notes. 2018-11-09 08:27:21 -05:00
Dianne Skoll
0db239f8a0 Bump version to 03.01.16. 2018-11-09 08:20:08 -05:00
Dianne Skoll
32fb1706c8 Fix a few more SystemTime calls. 2018-11-04 13:47:18 -05:00
Dianne Skoll
c9e6cd9796 Queue should use actual clock in computer. 2018-11-04 13:45:23 -05:00
Dianne Skoll
81677528a5 In -z0 mode, wake up exactly on the minute. 2018-11-04 13:39:00 -05:00
Dianne Skoll
7761baba10 ? 2018-11-04 13:29:59 -05:00
Dianne Skoll
52d252723f Depenguinization. 2018-11-04 10:56:47 -05:00
Dianne Skoll
d476709b59 Update DST rules. 2018-10-31 10:44:44 -04:00
Dianne Skoll
0910e3da74 Center popups over cal window. 2018-10-29 13:22:33 -04:00
Dianne Skoll
2cc7b7c817 Make queue grid resize gracefully. 2018-04-19 14:06:52 -04:00
Dianne Skoll
011a95ebbd Format the queue output better. 2018-04-19 14:01:09 -04:00
Dianne Skoll
bbdc086a1f Correct definitions for Yom Hazikaron and Yom Ha'atzmaut. 2018-04-19 14:00:46 -04:00
Dianne Skoll
7d6617d21e Finish adding queue feature. 2018-04-18 10:57:51 -04:00
Dianne Skoll
f684baeeb9 Add a QUEUE daemon command to dump the queue. 2018-04-18 10:43:49 -04:00
Dianne Skoll
308104853b Redraw window if file time is updated. 2018-04-13 08:46:26 -04:00
Dianne Skoll
6953bcac35 Monitor .reminders for mtime changes and restart daemon if it changes. 2018-04-12 11:44:04 -04:00
Dianne Skoll
69e9fa4721 Put hostname in tkremind window. Silence gcc warning. 2017-07-18 10:36:08 -04:00
Dianne Skoll
72d154c5e0 Patch from Stephen Morgan to calculate astronomical and nautical twilight in addition to civil twilight. 2017-01-19 10:11:54 -05:00
Dianne Skoll
84b0a96170 Accept datetimes in ISO-8601 format on input.
Add $DateTimeSep system variable to select T or @ as separator
on output.
2016-07-25 10:05:25 -04:00
Dianne Skoll
6d3b8f7a09 Handle the "SHADE nnn" special with just one number.
Pointed out by hymie@lactose.homelinux.net
2016-01-15 10:16:02 -05:00
Dianne Skoll
81749ac1c9 Update release notes. 2015-07-27 15:41:14 -04:00
Dianne Skoll
65989c29b7 Add test for bug found by Alexander Keller 2015-07-27 15:38:11 -04:00
Dianne Skoll
ec4e58f25c Proper fix for overflow. 2015-07-27 13:20:00 -04:00
Dianne Skoll
0c699c2a19 Fix potential buffer overflow. 2015-07-27 13:18:16 -04:00
Dianne Skoll
739a938d32 Don't permit repeated DELTA or REPEATs either. 2015-05-27 13:21:33 -04:00
Dianne Skoll
61ad405b4a Reject AT clause with more than one following TIME. 2015-05-27 13:19:25 -04:00
Dianne Skoll
700e649e76 Fix typo in year. Pointed out by hymie@lactose.homelinux.net 2015-04-24 15:33:35 -04:00
Dianne Skoll
7bfdb1f0eb Document the magic __EOF__ marker. 2015-04-24 14:42:48 -04:00
Dianne Skoll
0c0280b2a9 Add test for __EOF__ 2015-04-24 14:40:12 -04:00
Dianne Skoll
57a1871077 Fix test output. 2015-04-24 14:37:32 -04:00
Dianne Skoll
ee972ad29f Update version to 3.1.14 2015-04-24 14:37:06 -04:00
David F. Skoll
29c8475ea9 s/David/Dianne/ 2015-04-17 02:07:18 -04:00
David F. Skoll
6dd0f6ed63 Fix typo. 2014-11-06 14:32:30 -05:00
David F. Skoll
fc2d7ae446 Add support for __EOF__ to make Remind stop reading a file. 2014-05-22 14:19:06 -04:00
David F. Skoll
d232ac0334 Clear out MD5 context correctly. 2014-02-14 12:46:12 -05:00
David F. Skoll
6e8dd68c8a Use ADVANCE_MODE rather than CAL_MODE for "-n" cmdline option. 2013-04-30 15:58:02 -04:00
David F. Skoll
495cc1b38d Improve PNG images. 2013-03-22 16:21:52 -04:00
David F. Skoll
d90e74b1a3 Update release notes. 2013-03-22 15:48:04 -04:00
David F. Skoll
bbd8a4b729 Bump version to 3.1.13. 2013-03-22 15:44:03 -04:00
David F. Skoll
cae3e18717 Two cleanup patches from Simon Ruderich. 2013-03-18 14:07:09 -04:00
David F. Skoll
0e989a7422 Use atan2 instead of atan. 2013-03-10 18:00:36 -04:00
David F. Skoll
7b7ce5bb57 Remove dead code and dead variable. 2013-03-08 10:27:38 -05:00
David F. Skoll
df95cdaad0 Final sunrise/sunset tweakage. 2013-03-08 10:26:48 -05:00
David F. Skoll
3026b6e5c2 Tweak sun stuff per John McGowan ticket #27369. 2013-03-07 13:49:53 -05:00
David F. Skoll
b3306c5572 Revert change: TrigAttempts too hard to define. 2012-12-09 11:23:02 -05:00
David F. Skoll
9ef3be33e5 Add new $TrigAttempts special var. 2012-12-09 11:17:16 -05:00
David F. Skoll
292262c128 -z defaults to 1, not 5, so correct man page and help output.
Thanks to Simon Ruderich for pointing out the bug.
2012-11-01 13:07:42 -04:00
David F. Skoll
e54bfe9197 Minor patches from Simon Ruderich 2012-10-18 09:31:12 -04:00
David F. Skoll
c56cfe9e1d Fix test harness failure. 2012-05-08 16:54:54 -04:00
David F. Skoll
f6b6a3285c Apply patch from Jonathan Kamens to allow 0-point margins. 2012-04-26 08:57:37 -04:00
David F. Skoll
6b031b0fdf Change "Daylight Savings" to "Daylight Saving" 2012-03-23 15:45:49 -04:00
David F. Skoll
2dab7025ba Fix incorrect info in man page. 2012-03-14 11:47:43 -04:00
David F. Skoll
7403114897 Patch to allow compilation with gcc 2.95. 2012-02-13 10:23:53 -05:00
David F. Skoll
82cbeec560 Update tests to skip sun-tests by default. 2012-01-23 13:21:50 -05:00
David F. Skoll
df6b4ac566 Update release notes. 2012-01-23 13:08:22 -05:00
David F. Skoll
4ba21ab526 Fix test-all-languages.sh. 2012-01-23 12:01:11 -05:00
David F. Skoll
acac7a7b31 Add shell script to test all languages. Add %* substitutions to tstlang.rem 2012-01-23 11:58:07 -05:00
David F. Skoll
2290fd09f5 Add altmode to various languages. 2012-01-23 11:49:32 -05:00
David F. Skoll
f02b6a1773 "-x" flag to git-ls-files doesn't work, apparently. 2012-01-23 11:14:00 -05:00
David F. Skoll
efffe05d42 Merge branch 'master' of ssh://source.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2012-01-20 15:49:27 -05:00
David F. Skoll
950d67c522 Update Finnish translation for altmode. 2012-01-20 15:49:03 -05:00
David F. Skoll
a1aa61f54e Fix comment. 2012-01-12 13:12:59 -05:00
David F. Skoll
3c2bd66460 Clarify wording. 2012-01-12 13:05:46 -05:00
David F. Skoll
245cebee56 If multiple -a options are supplied, then *do* trigger timed reminders
that are in the future.
2012-01-12 13:04:53 -05:00
David F. Skoll
c45364fdb3 More WIP on PHP stuff. 2012-01-12 12:48:36 -05:00
David F. Skoll
e380308604 More sunstuff tweaking. 2011-12-28 13:14:24 -05:00
David F. Skoll
bd019524dd Update test output 2011-12-28 08:50:03 -05:00
David F. Skoll
895536d7d3 Use proper value of cos(6 degrees) for dusk/dawn 2011-12-28 08:49:37 -05:00
David F. Skoll
3a0e41afd1 Round off sun times to nearest minute. 2011-12-27 12:34:17 -05:00
David F. Skoll
23dd28471e Update sunrise/sunset calculations with different formula for mean anomaly. 2011-12-27 12:20:36 -05:00
David F. Skoll
761217d403 Add dawn/sunrise/sunset/dusk tests. 2011-12-26 17:44:34 -05:00
David F. Skoll
77ed694111 Use proper formula for dusk/dawn. 2011-12-26 14:41:21 -05:00
David F. Skoll
61bcce3104 Add tests for %*x and upper-case %*X substitutions. 2011-12-25 11:43:07 -05:00
David F. Skoll
bf41b12ccd Paranoia. 2011-12-24 11:04:21 -05:00
David F. Skoll
5eabd7d8d8 Fix dumb error. :) 2011-12-24 11:02:52 -05:00
David F. Skoll
0c66f5f3af Add "alternate" substitution mode: %*X is the same as %x but it leaves
out the preposition "at" or "on".
2011-12-24 10:58:37 -05:00
David F. Skoll
3190f784d9 Update copyright year. 2011-12-16 16:00:13 -05:00
David F. Skoll
394ff55879 Bump version number. 2011-12-16 15:58:30 -05:00
David F. Skoll
9b846835bc Bump version to 03.01.11 2011-12-16 15:56:34 -05:00
David F. Skoll
01776af167 Update WHATSNEW 2011-12-16 15:51:26 -05:00
David F. Skoll
0db10424ad Make sure COLOUR works just as well as COLOR. 2011-12-16 15:47:46 -05:00
David F. Skoll
bafd7ea073 Apply Debian fixes from Kurt B. Kaiser. 2011-12-11 17:43:26 -05:00
David F. Skoll
0ab27fcb4b Fix typo. 2011-12-05 16:47:21 -05:00
David F. Skoll
95d016712e Merge branch 'master' of ssh://source.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2011-12-05 16:43:19 -05:00
David F. Skoll
fcb55001bb Allow the color special to be spelled COLOR or COLOUR. 2011-12-05 16:42:57 -05:00
David F. Skoll
7bc6961101 Apply some minor cleanup patches from Debian 2011-07-28 14:31:18 -04:00
David F. Skoll
450e88fad8 Fix typo. 2011-03-16 15:49:03 -04:00
David F. Skoll
3222b4c311 More work on PHP front/back-end. 2011-03-16 13:00:35 -04:00
David F. Skoll
1e0cc3605d Add THROUGH to vim syntax file. 2011-03-16 13:00:28 -04:00
David F. Skoll
129b7bfeb7 Fix typos. 2011-01-21 17:01:57 -05:00
David F. Skoll
388811b684 Handle MOON specials. 2011-01-21 16:59:03 -05:00
David F. Skoll
f83257407b Yet more hacking. 2011-01-21 16:20:17 -05:00
David F. Skoll
e4ced77340 Key entries by day. 2011-01-20 16:50:24 -05:00
David F. Skoll
92e0bc316a Parse out day/mon/yr 2011-01-20 16:40:11 -05:00
David F. Skoll
a4a55f35b2 Start on PHP front-end to Remind. 2011-01-20 16:35:00 -05:00
David F. Skoll
ed1150c189 Clarify sign of longitude components. 2011-01-03 09:42:15 -05:00
David F. Skoll
08080f4e86 Use 6-degree definition (Civil Dawn) instead of older 14-degree below horizon. 2010-12-16 09:00:12 -05:00
David F. Skoll
de4ebb8be6 Update WHATSNEW. 2010-10-30 17:13:17 -04:00
David F. Skoll
11e2ce5093 Document multiple tag clauses. 2010-10-29 13:09:12 -04:00
David F. Skoll
2c560e6f2b Merge branches 'master' and 'master' of ssh://vanadium.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2010-10-24 14:15:01 -04:00
David F. Skoll
643f394e6a Bug fix: If there are no tags, emit a "*" when doing NOTE reminder ... 2010-10-12 15:39:08 -04:00
David F. Skoll
6d047c2856 Use a dynamic buffer to accumulate tags instead of a special-purpose data structure. 2010-09-29 14:07:14 -04:00
David F. Skoll
be86746685 Support multiple TAGs in a single REM. 2010-09-23 15:47:22 -04:00
David F. Skoll
da429b9629 Avoid leaving running processes in the background when doing "make test" 2010-09-16 12:46:06 -04:00
David F. Skoll
b21a206c26 Fix token comparisons to be case-insensitive. 2010-09-13 20:17:02 -04:00
David F. Skoll
85bde8ba3a Make PrintCentered handle multi-byte characters. 2010-09-13 10:11:28 -04:00
David F. Skoll
f84e658e6b Update remind.vim to latest. 2010-09-12 12:48:39 -04:00
David F. Skoll
8f0eba8bcd Fix corner (UTF-8 had a typo.) 2010-09-10 17:37:49 -04:00
David F. Skoll
2faaaf78a8 Add support for UTF-8 line-drawing characters. 2010-09-10 10:18:22 -04:00
David F. Skoll
7f659dace2 Add support for multibyte chars in -c output. But that breaks line-drawing. :( 2010-09-09 17:17:18 -04:00
David F. Skoll
54cdd566c7 Shrink executable on non-Apple/non-MS platforms. 2010-09-02 15:30:56 -04:00
David F. Skoll
e212df87f9 Bump version to 03.01.10. 2010-09-01 17:15:37 -04:00
David F. Skoll
4fb4db15e8 Stricter syntax check - reject extra cruft afer "OMIT DUMP" 2010-09-01 17:12:55 -04:00
David F. Skoll
9a15a25a7b Don't hard-code text box background. 2010-09-01 12:07:41 -04:00
David F. Skoll
c02cfb9b17 Add THROUGH keyword to editor syntax files. 2010-08-31 16:57:27 -04:00
David F. Skoll
3e726f21f7 Improve error message. 2010-08-31 14:02:17 -04:00
David F. Skoll
21d4faa26f Allow OMIT ... THROUGH ... to be re-parsed as a REM command. 2010-08-31 13:51:13 -04:00
David F. Skoll
1d13d0ee07 Update tests to handle OMIT ... THROUGH ... 2010-08-31 13:44:57 -04:00
David F. Skoll
329d13e480 Fix typo 2010-08-31 13:34:55 -04:00
David F. Skoll
2161c09b1d Update man page. 2010-08-31 13:33:51 -04:00
David F. Skoll
3f2e396c3c Change "omit debug" to "omit dump" 2010-08-31 12:37:10 -04:00
David F. Skoll
412e242109 Don't create any OMITs with THROUGH if there would be too many.
Bump max full omits to 500 and partial omits to 366.
2010-08-31 12:27:23 -04:00
David F. Skoll
e827516b72 Add "OMIT start THROUGH end" syntax. Also add "OMIT DEBUG"
Add syntactic sugar:

REM start THROUGH end   is converted to REM start *1 UNTIL end
2010-08-31 12:19:08 -04:00
David F. Skoll
7f953e98d7 Clarify manual: Line continuations are processed before comments. 2010-08-20 13:47:51 -04:00
David F. Skoll
821d3fe783 Conform to older C spec that prohibits declaration of variables in the middle of a block. 2010-06-21 21:32:21 -04:00
David F. Skoll
fdb4b302ac Update WHATSNEW with release date. 2010-06-20 16:38:44 -04:00
David F. Skoll
760d5d4a09 Fix trap to reset signal disposition to default. 2010-06-02 09:05:11 -04:00
David F. Skoll
d561f98c42 Fix syntax error. 2010-05-18 20:45:36 -04:00
David F. Skoll
ea74f276dc Don't rkrphgvba more than once. 2010-05-18 12:46:34 -04:00
David F. Skoll
42cf82a5d5 More Apple / Cygwin detection. 2010-05-17 09:32:50 -04:00
David F. Skoll
825a6700da Make "trap" command follow POSIX standard. 2010-05-17 06:59:41 -04:00
David F. Skoll
2f27645dac Handle SPECIAL COLOR correctly with -n commandline option. 2010-05-01 20:52:25 -04:00
David F. Skoll
1e5b44d063 Make handling of continued lines same as in 3.1.8. 2010-04-25 10:07:12 -04:00
David F. Skoll
099ad9945d Fix huge bug in handling of continued lines. 2010-04-25 10:03:13 -04:00
David F. Skoll
540ce3d946 Allow "timepart" to take a TIME or DATETIME. Allow "datepart" to take a
DATE or DATETIME.  Update docs.
2010-04-25 09:50:39 -04:00
David F. Skoll
ac2efcc993 Document timepart() and datepart(). 2010-04-25 09:40:01 -04:00
David F. Skoll
b4bb1d9e37 Update copyright date. 2010-04-25 09:34:49 -04:00
David F. Skoll
9ec8b30934 Update copyright date. 2010-04-22 11:45:19 -04:00
David F. Skoll
fb38e5b35b Update WHATSNEW. 2010-04-21 16:01:04 -04:00
David F. Skoll
5fa10e9d84 Document Purge Mode. 2010-04-21 14:55:28 -04:00
David F. Skoll
3bc1b5bd46 Clean up tests; add test for non-parseable line in purge mode. 2010-04-21 13:30:10 -04:00
David F. Skoll
b266b399ba Test for fix of parse error.
Try REALLY hard to detect constant expressions...
2010-04-21 13:23:26 -04:00
David F. Skoll
0e827a457d Fix YomHashoah date and bug in DoSatReminder. 2010-04-21 09:49:33 -04:00
David F. Skoll
d05d85b243 More tests. 2010-04-21 09:04:48 -04:00
David F. Skoll
a1faa8d804 Finish up Purge Mode:
o Make it recognize constant expressions (yay!)
o Make it not add a blank line to end of *.purged files.
o Make it nuke #!P comments in the source files.
2010-04-21 09:02:25 -04:00
David F. Skoll
70adbf90c2 Add tests for purge mode. 2010-04-20 15:20:49 -04:00
David F. Skoll
501c04f4b6 More work on purge mode. 2010-04-20 14:01:54 -04:00
David F. Skoll
d294e62be1 More work on purge mode. 2010-04-20 11:34:07 -04:00
David F. Skoll
31f90b6c53 Add purge mode. 2010-04-20 10:59:57 -04:00
David F. Skoll
184d29c592 More work on -j ("Purge Mode") option. 2010-04-19 15:57:35 -04:00
David F. Skoll
2d798bc4ec Add support for DURATION in TkRemind. Patch from Marek Marczykowski. 2010-04-19 14:13:48 -04:00
David F. Skoll
bd9a3761a6 Sort PSFILE and PS reminders with same priority (Ticket #17581) 2010-04-19 13:17:00 -04:00
David F. Skoll
b1063b0a9e More purge-mode work. 2010-04-09 11:01:45 -04:00
David F. Skoll
cb2fffab92 Don't expire lines containing expressions. 2010-04-07 15:32:20 -04:00
David F. Skoll
55cca49428 Start implementing a "-j" mode to purge old reminders. 2010-04-07 15:30:29 -04:00
David F. Skoll
5a0ab9ed8a Fix shade.rem to be independent of location and time zone of test machine. 2010-03-10 11:14:36 -05:00
David F. Skoll
1f2cfdfd84 Bump version to 03.01.09. 2010-03-09 10:05:56 -05:00
David F. Skoll
dfd688caa6 Update WHATSNEW date. 2010-03-09 09:55:00 -05:00
David F. Skoll
830e3e339c Make it only mildly annoying to compile on Windows and Mac OS X. 2010-03-06 17:39:39 -05:00
David F. Skoll
bc9f560950 Update WHATSNEW file. 2010-03-03 11:18:35 -05:00
David F. Skoll
f91b748f50 I don't like Microsoft or Apple. So the ./configure script will bail out on those platforms. 2010-03-02 19:15:40 -05:00
David F. Skoll
3adbd7468c Update "WINDOWS" file; rename it to MICROSOFT-AND-APPLE. 2010-03-02 19:06:06 -05:00
David F. Skoll
b66039ee24 Ignore msgprefix()/msgsuffix() on RUN-type reminders. 2010-02-26 09:48:18 -05:00
David F. Skoll
27371f6475 Document new $T, $U system variables. 2009-12-29 21:26:11 -05:00
David F. Skoll
19e7c34b47 Bump version to 03.01.08. 2009-12-29 10:52:06 -05:00
David F. Skoll
3375aff3a7 Add $U, $Um, $Ud, $Uy and $Uw special variables. Just like the $T.. versions,
but using today() instead of trigdate().
2009-12-29 08:47:07 -05:00
David F. Skoll
41e9cb5ca3 Clean up handling of SPECIAL_TYPE variales. Make
$T return 1990-01-01 if last trigger date was not valid.
2009-12-26 13:06:50 -05:00
David F. Skoll
6348860adf Update test for new debugging output. 2009-12-26 00:28:16 -05:00
David F. Skoll
4e9d401002 Add $T, $Td, $Tm, $Tw and $Ty system variables as shorthands for
trigdate(), day(tridate()), month(trigdate()), wkdayno(trigdate()) and
year(trigdate())
2009-12-26 00:26:14 -05:00
David F. Skoll
3db2fc7d0f Make "$t" a synonym for "trigdate()" 2009-12-22 18:25:01 -05:00
David F. Skoll
0101d76113 Better -df output. 2009-11-16 00:09:40 -05:00
David F. Skoll
6fabab6d4b Add remind-conf-mode 2009-11-03 13:32:10 -05:00
David F. Skoll
905f1b0aaf Add some scripts in contrib/ 2009-11-03 13:25:17 -05:00
David F. Skoll
6a5ab8e70c Update man page. 2009-11-01 09:54:28 -05:00
David F. Skoll
943b037589 Better iconphoto. 2009-10-30 22:08:26 -04:00
David F. Skoll
5624cd44de Set a nice iconphoto. 2009-10-30 13:52:19 -04:00
David F. Skoll
8529f8b843 Fix bugs in Makefile.in 2009-10-15 15:19:56 -04:00
David F. Skoll
08be7c43cf Don't make SHADE specials obliterate MOON specials. Fixes ticket 15068. 2009-10-05 14:33:51 -04:00
David F. Skoll
aae76207ec Fix bug in SCHED function calculation (RT #15644) 2009-09-06 18:36:34 -04:00
David F. Skoll
5434f8330e Sort specials. 2009-09-06 18:36:27 -04:00
David F. Skoll
e18b4ed119 Update copyright. 2009-05-31 13:06:05 -04:00
David F. Skoll
51f6ffc093 Document changes. 2009-05-31 13:05:05 -04:00
David F. Skoll
72de7c6b14 Make CallFunc and built-in functions re-entrant. 2009-05-26 22:35:57 -04:00
David F. Skoll
bd4785d631 Remove spurious trigger() function calls from examples.
Bump version to 3.1.7
2009-05-16 10:56:12 -04:00
David F. Skoll
cb08f12470 Add another test. 2009-05-16 10:47:54 -04:00
David F. Skoll
04146db69b More man page updates. 2009-05-16 10:47:10 -04:00
David F. Skoll
d3fe045a39 Make slide function diagnose "Can't OMIT every weekday" 2009-05-16 10:42:43 -04:00
David F. Skoll
2be1e16087 Add some tests. 2009-05-16 10:30:25 -04:00
David F. Skoll
051e44ae3e Update man page. 2009-05-16 10:22:43 -04:00
David F. Skoll
6d5ae7a258 Allow short-hand date specs after UNTIL and SCANFROM.
Start updating man page.
2009-05-16 10:07:57 -04:00
David F. Skoll
2e69e140eb Accept a T_Date or T_DateTime on cmdline to set now() and today(). 2009-05-12 22:46:01 -04:00
David F. Skoll
516c4e2c39 Allow literal dates and datetimes in REM and OMIT statements.
This lets us avoid cluttering up files with [trigger(expr)]; we can
use [expr] directly.
2009-05-09 16:41:15 -04:00
David F. Skoll
b58ed62000 Simplify. 2009-05-09 00:17:11 -04:00
David F. Skoll
c685818783 Use macro to refer to RetVal.v.val 2009-05-09 00:10:45 -04:00
David F. Skoll
3e20ce56c9 Add the slide(date, amt [,localomits]) built-in function. 2009-05-09 00:07:59 -04:00
David F. Skoll
dd8d67f659 Update man page. 2009-02-03 23:11:50 -05:00
David F. Skoll
5ef4061819 Let Remind accept a date of the form YYYY-MM-DD on cmdline. 2009-02-03 23:08:27 -05:00
David F. Skoll
a146a0c819 Update WHATSNEW; fix typo in man page. 2008-11-16 11:01:01 -05:00
David F. Skoll
0f5a93cdf1 Fix up man page. 2008-11-16 10:51:10 -05:00
David F. Skoll
7db51e913e Clarify WEEK example. 2008-11-15 09:24:09 -05:00
David F. Skoll
93ac1aebf7 Document WEEK special. Clean up rem2ps handling of WEEK. 2008-11-15 09:20:54 -05:00
David F. Skoll
56ebedb9de Proper implementation of WEEK special. 2008-11-14 17:02:51 -05:00
David F. Skoll
e87d33de50 Handle the WEEK special. 2008-11-14 16:56:08 -05:00
David F. Skoll
a5774fd793 Document weekno() function. 2008-11-14 16:16:13 -05:00
David F. Skoll
adb60f3400 Fix example in man page. 2008-11-14 16:07:25 -05:00
David F. Skoll
47a0f63caa Fix tests. 2008-10-05 14:29:31 -04:00
David F. Skoll
30a385a7bb Fix bug in IsTopLevel. 2008-10-05 14:29:03 -04:00
David F. Skoll
9f2ae1773c Document evaltrig. 2008-10-05 14:11:58 -04:00
David F. Skoll
f470297958 Make max. string length controllable with $MaxStringLen system variable. 2008-10-05 13:49:45 -04:00
David F. Skoll
93dfc7995c Fix man page. 2008-09-23 22:39:12 -04:00
David F. Skoll
c96869817f Rejigger infrastructure to detect recursive OMITFUNC calls in evaltrig() 2008-09-23 22:21:39 -04:00
David F. Skoll
1bffa0e00b Allow any of the args to date() function to be a date,
in which case we just extract the appropriate part.
2008-09-20 11:07:33 -04:00
David F. Skoll
36035dda01 Issue a warning if we detect a SCANFROM used in two-arg evaltrig(). 2008-09-20 00:14:13 -04:00
David F. Skoll
50a15cf089 Make evaltrig return a DATETIME if there's an AT clause. 2008-09-20 00:03:38 -04:00
David F. Skoll
b59d4ed4a4 Add "evaltrig" function. 2008-09-19 23:49:11 -04:00
David F. Skoll
4c53710279 Set maximum string length to 65535 to minimize chances of self-DOS. 2008-09-19 23:28:19 -04:00
David F. Skoll
2274e88485 Remove extraneous semicolon 2008-09-19 23:10:57 -04:00
David F. Skoll
984a4677f2 Clean up funcs.c; add weekno function for ISO week number. 2008-09-19 23:08:15 -04:00
David F. Skoll
5e3dc54725 Document sorting of timed vs. untimed reminders.
Add an $UntimedFirst system variable.
2008-09-18 17:30:31 -04:00
David F. Skoll
53a7bf9773 Make tests pass. 2008-09-18 17:20:09 -04:00
David F. Skoll
1dcc3897d6 Allow sorting of untimed before timed. 2008-09-18 17:17:38 -04:00
David F. Skoll
fbc0375739 Fix bug if MON DAY WKDAY crosses year boundary. 2008-09-16 22:10:09 -04:00
David F. Skoll
4a74c03fa4 Small man-page fix. 2008-08-31 15:51:25 -04:00
David F. Skoll
d8833e6ce2 Updated man page. 2008-08-31 15:44:57 -04:00
David F. Skoll
2b8b9a56aa Fix typo. 2008-08-31 10:32:25 -04:00
David F. Skoll
85a8ebb357 Slight efficiency improvement in OMIT testing. 2008-08-31 10:30:59 -04:00
David F. Skoll
a67d9e2524 Change behaviour: OMITFUNC ignores local/global OMIT context. Only sane
way to solve garbage-day problem; also allows for more flexibility.
2008-08-31 10:29:28 -04:00
David F. Skoll
6845e72fd5 Communicate errors back for bad OMITFUNCs. 2008-08-30 22:10:06 -04:00
David F. Skoll
0ab977fa05 Whitespace cleanup 2008-08-30 21:43:38 -04:00
David F. Skoll
ad64a12b2a Update man page. 2008-08-30 16:35:48 -04:00
David F. Skoll
cfde4b50bb Updated man page. 2008-08-29 21:28:25 -04:00
David F. Skoll
f302c8eb95 Document OMITFUNC and fix huge bug. :-) 2008-08-29 21:22:48 -04:00
David F. Skoll
7ecc355358 Add test for OMITFUNC. 2008-08-29 21:03:01 -04:00
David F. Skoll
a52216d7e7 Update test.cmp for version. 2008-08-29 20:56:22 -04:00
David F. Skoll
8d8d4b667d Implement OMITFUNC clause in REM command. 2008-08-29 20:48:58 -04:00
David F. Skoll
670369121e Remove -a flag from "ShowTodaysReminders" 2008-08-28 12:29:38 -04:00
David F. Skoll
4365e580ee If main reminder file is a directory and AppendFile does not exist,
create AppendFile.
2008-04-16 21:54:05 -04:00
David F. Skoll
a8a09a905e Update test.cmp for new version. 2008-04-16 21:45:58 -04:00
David F. Skoll
dbb7381eb1 Update version number in configure. 2008-04-16 21:44:44 -04:00
David F. Skoll
aa3531a6bf Merge branch 'master' of ssh://source.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2008-04-16 13:35:36 -04:00
David F. Skoll
2848203d75 Note new behaviour: set var [expr] no longer works. 2008-04-16 13:34:38 -04:00
David F. Skoll
f0aef0703c Update WHATSNEW file. 2008-04-15 18:26:25 -04:00
David F. Skoll
7356a511e0 Update release notes and man page. 2008-04-14 21:30:35 -04:00
David F. Skoll
5be26a3cff Add "c" flag to -c option that causes Remind to approximate
SPECIAL COLOR reminders with vt100 escape sequences.
2008-04-14 21:03:45 -04:00
David F. Skoll
36a80acb0c Make tkremind handle the case when ~/.reminders is a directory better.
It uses ~/.reminders/100-tkremind.rem as the append file.
2008-03-31 14:00:09 -04:00
David F. Skoll
37ab03b49d Make tkremind work better on small-screen devices like eeepc. 2008-03-30 12:11:07 -04:00
David F. Skoll
75209cb40e Update tkremind copyright date. 2008-03-27 22:13:24 -04:00
David F. Skoll
4b2d274748 Add "l" flag to -c to draw calendar
using VT100 line-drawing characters.
2008-03-27 22:04:06 -04:00
David F. Skoll
1423495b88 Document -tn option
Implement "-ca" which is analagous to "-pa" and "-sa".
2008-03-26 21:51:30 -04:00
David F. Skoll
42e4ec8890 Make DEBUG command handle "f" flag. 2008-03-25 17:21:07 -04:00
David F. Skoll
58fbd51ef4 Call globfree to free memory used by glob. 2008-03-24 23:12:27 -04:00
David F. Skoll
7552dbb812 Update copyright. Put -df in online usage blurb. 2008-03-24 21:36:29 -04:00
David F. Skoll
31e0ecb71d Fix tests for version change. 2008-03-24 20:42:19 -04:00
David F. Skoll
f6743a4f87 Bump version to 03.01.05. 2008-03-24 20:41:12 -04:00
David F. Skoll
5f574949e6 Nicer -df output. Document -df. 2008-03-24 20:39:47 -04:00
David F. Skoll
724bce4fb9 Add "-df" debugging flag to track file opens. 2008-03-24 20:22:00 -04:00
David F. Skoll
8d59f025af Patch from Ian! Allen. 2008-03-24 14:10:01 -04:00
David F. Skoll
aad44f4716 Spit out errors if we can't open a non-readable file in a dir/*.rem. 2008-03-24 14:02:39 -04:00
David F. Skoll
0a38d7d213 Output fileinfo lines in tests. 2008-03-24 13:56:51 -04:00
David F. Skoll
4fcd60fd95 Increase INCLUDE_DEPTH to account for (wasted) top-of-stack entry.
Document that filename argument for INCLUDE and command-line can be a directory.
2008-03-24 13:54:21 -04:00
David F. Skoll
38beeb8cb0 Add some tests for INCLUDE functionality. 2008-03-24 13:29:31 -04:00
David F. Skoll
26f0acab35 Opening of directories works properly. 2008-03-24 13:16:28 -04:00
David F. Skoll
3897973bc1 Improve error messages. 2008-03-24 13:11:21 -04:00
David F. Skoll
7b3da27461 Fix parse error bug in calendar mode. 2008-03-24 13:02:05 -04:00
David F. Skoll
a85ee5f31c INCLUDE /directory works. Still need more futzing to fix parse error. 2008-03-24 12:58:23 -04:00
David F. Skoll
b272863aa0 Prep for push. 2008-03-24 10:00:34 -04:00
David F. Skoll
8249964380 Start coding feature allowing "INCLUDE /directory" which basically
includes "/directory/*.rem" files in glob-order.
2008-03-22 23:28:51 -04:00
David F. Skoll
af81bbb299 Preserve "\n" in continued lines.
Set a flag if parser encounters [expr].
2008-03-15 14:06:12 -04:00
David F. Skoll
d818dd9c80 Fix bug in AM/PM option setting for existing reminders. 2008-03-09 11:23:27 -04:00
David F. Skoll
fe8e34dece Better error message if nonsensical -i option given. 2008-02-06 23:42:12 -05:00
David F. Skoll
ba928989f7 Make expression parser accept backslashes in strings so we can do:
SET a "Some \"embedded\" quotes"
2008-02-06 23:35:46 -05:00
David F. Skoll
742f973028 Allow command-line '-i' option to define a function as well as a var.
Example:  remind ... '-isquare(x)=x*x' ...

Also, allow the syntax:

      SET var = expr
      FSET func(args) = defn

Old syntax still works, of course:

      SET var expr
      FSET func(args) defn
2008-02-06 23:12:51 -05:00
David F. Skoll
043932fcbe Add a $DeltaOffset read-only system variable that is set by "-tNNN" option. 2008-02-06 22:24:45 -05:00
David F. Skoll
ad5e096caa Make '-t' take a numeric argument that sets the "DeltaOffset" to that
value.  We trigger any reminder that will trigger between today and
today+DeltaOffset days.  A bare '-t' sets InfiniteDelta as before.
2008-02-06 22:16:47 -05:00
David F. Skoll
06c8fc8f78 Oops... forgot a release note. 2008-02-03 17:14:31 -05:00
David F. Skoll
487338d10c Updated for 3.1.4 release. 2008-02-03 17:12:16 -05:00
David F. Skoll
3d1c0e5667 Fix awful bug in rem2html for a 28-day February that starts on Sunday... 2008-01-31 23:31:45 -05:00
David F. Skoll
ce3bb191c4 More code cleanups and const-correctness. 2008-01-30 21:37:19 -05:00
David F. Skoll
03e9dbf364 More const qualification. 2008-01-28 11:39:15 -05:00
David F. Skoll
518aab3d02 Don't trash argv[] so reread works properly. 2008-01-28 11:28:17 -05:00
David F. Skoll
f055664f77 More const-correctness. 2008-01-27 11:02:03 -05:00
David F. Skoll
ba3e01f2ce Add a bunch of const qualifiers. 2008-01-26 21:55:58 -05:00
David F. Skoll
b6883c8a45 Keep version number in ONE place (configure.in) instead of two. 2008-01-26 15:34:32 -05:00
David F. Skoll
9e49ee3acb Make tkremind obey -b1 option (24-hour mode.) 2008-01-26 12:01:43 -05:00
David F. Skoll
7481f68bb2 Make tkremind work better with Tk8.5. 2007-12-24 11:40:22 -05:00
David F. Skoll
99792eec03 Add a test. 2007-11-05 11:52:50 -05:00
David F. Skoll
91458c7845 Better patch for parsing bug. 2007-11-05 11:44:48 -05:00
David F. Skoll
cad5849dc0 Merge branch 'master' of ssh://magnesium.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2007-11-05 11:38:17 -05:00
David F. Skoll
a38e120e99 Fix weird parsing bug if you have a SKIP on an omitted day with a SATISFY. 2007-11-05 11:37:48 -05:00
David F. Skoll
0b31a78cf2 Patch to clean up HTML output (Jorey Bump) 2007-10-16 11:46:58 -04:00
David F. Skoll
861858c1a6 Bump version to 03.01.04. 2007-10-15 14:17:09 -04:00
David F. Skoll
d43a2277da Updated WHATSNEW. 2007-10-15 14:00:09 -04:00
David F. Skoll
f678dc96b8 Write man page for rem2html 2007-10-07 22:24:35 -04:00
David F. Skoll
c2e371904e Update distclean target. 2007-10-07 22:10:25 -04:00
David F. Skoll
2a1cbff22e Add www/Makfile to gitignore. 2007-10-07 22:09:47 -04:00
David F. Skoll
a2d9f277c4 Minor tweaks to Makefile.in 2007-10-07 22:09:37 -04:00
David F. Skoll
d939059417 Improve www/Makefile stuff. 2007-10-07 22:05:35 -04:00
David F. Skoll
740cd4cfed Update README. 2007-10-06 11:41:40 -04:00
David F. Skoll
91a5306a67 Fix typo. 2007-10-06 11:38:23 -04:00
David F. Skoll
b78ffcbffd Tidy up option processing. 2007-10-06 11:35:57 -04:00
David F. Skoll
4f72f557b7 Minor fix to --nostyle output. 2007-10-05 11:52:16 -04:00
David F. Skoll
e3b21d6d0d More tweaks. 2007-10-04 22:02:27 -04:00
David F. Skoll
af28c49d8d Fixed up the www stuff. 2007-10-04 22:01:09 -04:00
David F. Skoll
67f4635573 Fix DST rules. 2007-10-04 13:41:42 -04:00
David F. Skoll
5f8d10908d Minor cleanups. 2007-10-03 12:32:41 -04:00
David F. Skoll
7307421812 Add --nostyle option to rem2html so it can produce basic HTML that does
not rely on an external stylesheet.
2007-10-02 18:47:38 -04:00
David F. Skoll
5cd3b628c5 Minor tweaks. 2007-10-02 14:03:19 -04:00
David F. Skoll
29e483ab64 Updated Makefile and rem2html to use IMGBASE for stylesheet also. 2007-10-02 11:31:06 -04:00
David F. Skoll
66ddba45af Add support for HTMLCLASS special. Add CSS code for rem-today class to
highlight "today".
2007-10-02 11:21:40 -04:00
David F. Skoll
9325b3f035 Minor tweaks to CSS. 2007-10-01 18:03:21 -04:00
David F. Skoll
522c4c94e1 Add --imgbase option. 2007-10-01 17:59:33 -04:00
David F. Skoll
730505cff3 Less verbose. 2007-10-01 17:27:58 -04:00
David F. Skoll
019783e1fa Redo rem2html. Uses CSS instead of hard-coded stuff. 2007-10-01 17:21:59 -04:00
David F. Skoll
8612bb6480 Do not evaluate SATISFY expression if reminder has expired. 2007-09-26 08:41:34 -04:00
David F. Skoll
7f1e6d21d9 Update version number and copyright year. 2007-09-24 10:32:06 -04:00
David F. Skoll
e6c0371be1 Make calendar times show duration. 2007-09-16 17:44:33 -04:00
David F. Skoll
58feaa7e0c Update version in test.cmp 2007-09-12 10:08:04 -04:00
David F. Skoll
a828378466 Update version. 2007-09-12 09:55:40 -04:00
David F. Skoll
53316e8b06 Update WHATSNEW for 3.1.2 release. 2007-09-11 21:41:00 -04:00
David F. Skoll
6127e390a1 Make tkremind notify when firing up editor. 2007-09-10 16:56:10 -04:00
David F. Skoll
4caa77f6b1 Make PgUp and PgDn work like Left and Right, respectively. 2007-09-06 14:25:52 -04:00
David F. Skoll
70419e8757 Found dates for almost all releases. 2007-09-05 17:25:50 -04:00
David F. Skoll
21d8bd1406 Add dates (where known) to releases. 2007-09-05 17:07:48 -04:00
David F. Skoll
25abee3259 Ensure that tkremind draws moons before anything else. 2007-09-05 16:20:33 -04:00
David F. Skoll
2d490c2b7a Clarify WHATSNEW 2007-09-05 15:52:57 -04:00
David F. Skoll
902b7895b7 Merge branch 'master' of ssh://magnesium.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2007-09-05 07:04:36 -04:00
David F. Skoll
1c80bb649f Trigger queued reminders at least once even if we hibernate past trigger time. 2007-09-05 07:04:11 -04:00
David F. Skoll
4508215617 Merge branch 'master' of ssh://magnesium.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2007-09-04 21:58:37 -04:00
David F. Skoll
739b68347a Update WHATSNEW 2007-09-04 21:53:33 -04:00
David F. Skoll
d834760cda Merge branch 'master' of ssh://magnesium.roaringpenguin.com/home/dfs/personal-git-repos/Remind 2007-09-04 21:46:16 -04:00
David F. Skoll
1bc78650bf Exit in queue mode if date rolls over. 2007-09-04 21:44:59 -04:00
David F. Skoll
ec4e203099 Fix typo that caused SEGV. 2007-09-04 14:38:46 -04:00
David F. Skoll
d23528da82 Don't trigger reminders if they are more than 60 seconds in the past.
We want to avoid a huge flurry of triggering up emerging from suspend
or hibernation on a laptop.
2007-09-04 14:24:32 -04:00
David F. Skoll
7401a0ba23 In queue mode, wake up once a minute to recalibrate sleep time. Required
for laptops that hibernate or suspend.
2007-09-04 14:16:12 -04:00
David F. Skoll
b14b4f08b1 build.tk tries to reuse existing settings if an installed version of Remind
is found.
2007-09-03 21:37:58 -04:00
David F. Skoll
70ece81340 Flash buttons before invoking. 2007-09-03 10:23:15 -04:00
David F. Skoll
19ac350527 Silence gcc warning on Ubuntu Feisty. 2007-09-03 10:09:07 -04:00
David F. Skoll
a9b08d7db8 Updated docs. 2007-09-03 07:06:53 -04:00
David F. Skoll
df8fa05632 Note that psmoon and psshade are deprecated. 2007-09-03 06:48:38 -04:00
David F. Skoll
6556137aad Warn about deprecated psmoon and psshade functions. 2007-09-03 06:46:58 -04:00
David F. Skoll
aa1ab2bbb4 Don't sort SPECIALs ahead of normal reminders. Allow all SPECIALs to include
times; back-ends can use or ignore them as they see fit.
2007-09-03 06:28:34 -04:00
David F. Skoll
be38d86521 Make non-PSFile and non-PostScript SPECIALs preserve time
in -p field.
2007-09-02 23:02:25 -04:00
David F. Skoll
3931afb6b1 Remove all mention of remind-all. 2007-08-31 23:37:19 -04:00
David F. Skoll
7d2df86b75 Remove mention of remind-all 2007-08-31 23:36:06 -04:00
David F. Skoll
5a3bd5839b Tweak "make distro" 2007-08-31 23:29:39 -04:00
David F. Skoll
b91ce9a3f7 Incorporate rem's functionality directly into Remind. 2007-08-31 23:10:40 -04:00
David F. Skoll
ac889dd329 Corrections to Jewish Holidays from Art Werschulz. 2007-08-31 11:37:40 -04:00
David F. Skoll
420df9b6ed Bump version to 03.01.02. 2007-08-31 11:06:19 -04:00
David F. Skoll
f862b6811d Add test for REM AT ... SPECIAL COLOR ... 2007-08-31 11:02:26 -04:00
David F. Skoll
c072698927 Handle queued SPECIAL COLOR reminders properly. 2007-08-31 11:00:49 -04:00
David F. Skoll
d22895831b Fix enter/leave events. 2007-08-31 10:32:01 -04:00
David F. Skoll
3c41f4ade4 add rem2ps to gitignore. 2007-08-30 23:31:42 -04:00
David F. Skoll
335d5fb984 Don't include .gitignore when making distro. 2007-08-30 23:30:51 -04:00
David F. Skoll
66bd2b8fac Add a .gitignore file. 2007-08-30 23:29:20 -04:00
David F. Skoll
fed3cad3b8 Fix regression that broke non-COLOR specials. 2007-08-30 23:23:45 -04:00
David F. Skoll
b20578f24f Add and document keyboard shortcuts to tkremind. 2007-08-30 22:31:11 -04:00
David F. Skoll
7a86e7f777 Use spacing rather than "....." to separate reminders in TkRemind. 2007-08-30 22:19:50 -04:00
David F. Skoll
16c93fcad6 Add rem.1 man page to install target. 2007-08-30 21:58:28 -04:00
David F. Skoll
edd66d8d89 Added man page for rem script.
Added more tests.
2007-08-30 21:57:30 -04:00
David F. Skoll
3ba39b6efe Add "rem" Perl script. 2007-08-30 17:33:26 -04:00
David F. Skoll
c656a1a169 Make SPECIAL COLOR always output color triplet in calendar mode even with %"%" escapes. 2007-08-30 15:40:25 -04:00
David F. Skoll
19f03e419a Fix test.cmp for new version. 2007-08-22 20:32:49 -04:00
David F. Skoll
5a281d5999 Updated changelog. 2007-08-22 20:29:35 -04:00
David F. Skoll
d80d14f585 Better placement of moons 2007-08-22 16:34:35 -04:00
David F. Skoll
520b8511bd Make moon images transparent. 2007-08-22 16:31:04 -04:00
David F. Skoll
91627d4f22 Fix typo 2007-08-22 15:57:27 -04:00
David F. Skoll
a21147c7a5 Prune a whole bunch of obsolete files. 2007-08-22 15:54:41 -04:00
David F. Skoll
d22c1dee49 Fix README to reflect reality. 2007-08-22 15:50:58 -04:00
David F. Skoll
95b0fc7480 Update version to 03.01.01; document changes in WHATSNEW 2007-08-22 15:31:17 -04:00
David F. Skoll
b40d5d7984 Performance improvements. 2007-08-22 12:00:12 -04:00
David F. Skoll
2df93c9df3 Fixed wording of man page. 2007-08-22 11:29:35 -04:00
David F. Skoll
51cdea4b17 better definition of prev_monday 2007-08-21 22:03:31 -04:00
David F. Skoll
f229e64744 Fix typo 2007-08-21 18:58:00 -04:00
David F. Skoll
0f15955a41 Better definition of prev_monday in man page. 2007-08-21 18:54:53 -04:00
David F. Skoll
390e6c2eed Fixed typo 2007-08-21 18:49:49 -04:00
David F. Skoll
877eaccd6d Documented nonomitted() 2007-08-21 18:47:51 -04:00
David F. Skoll
6424e655a1 Allow cycle modulus to be zero. 2007-08-21 17:34:46 -04:00
David F. Skoll
176037082b Add cycle function to handle Elizabeth's school schedule. 2007-08-21 17:10:04 -04:00
David F. Skoll
a361c7e426 Note that we always use "/" in rem2ps input. 2007-08-17 09:07:32 -04:00
David F. Skoll
caba0c1695 Make "-n" mode use / (always) in dates to match Simple Calendar output. 2007-08-15 23:26:41 -04:00
David F. Skoll
71b3f9fefc Remove kall, rem from install target. 2007-08-15 23:20:57 -04:00
David F. Skoll
91f8507e51 Remove obsolete scripts. Apply some Debian-maintainer patches. 2007-08-15 23:18:48 -04:00
David F. Skoll
b68e81a126 Fix trailing "s" bug (Debian patch) 2007-08-15 23:06:21 -04:00
David F. Skoll
72658025f1 Prevent warning with fcc 2.95 2007-08-15 15:14:18 -04:00
David F. Skoll
93aea240d6 Updated docs. 2007-08-14 21:25:09 -04:00
David F. Skoll
7717b37c36 Updated for 3.1.0 release. 2007-08-14 21:21:52 -04:00
David F. Skoll
e1b2990fb0 Prevent possible memory leak. 2007-08-12 20:01:50 -04:00
David F. Skoll
e49194c6ee Clean up man page. 2007-08-12 19:48:52 -04:00
David F. Skoll
79ab150546 Modify "make dist" target to use git-ls-files instead of peekentry into CVS. 2007-08-12 19:15:57 -04:00
David F. Skoll
fc658d15d4 Fix typos. Document -y option. 2007-08-11 22:22:12 -04:00
David F. Skoll
76d130ef82 Add -y option to synthesize tags. 2007-08-11 22:03:48 -04:00
David F. Skoll
3e9a55fbdb Working version of e-mail if you don't close timed reminder popup. 2007-08-10 22:27:08 -04:00
David F. Skoll
b071397d46 Fix typo. 2007-08-10 22:08:02 -04:00
David F. Skoll
df0dd55635 Add code to make tkremind mail reminders if dialog not dismissed. Untested! 2007-08-10 14:15:12 -04:00
David F. Skoll
960d08fd24 Start adding feature that e-mails reminders if popup not dismissed. 2007-08-10 09:08:06 -04:00
David F. Skoll
38603916a2 Fix typo. 2007-08-08 12:07:05 -04:00
David F. Skoll
0ed1bb4017 Remove $Id$ tags. 2007-08-08 12:05:28 -04:00
David F. Skoll
b4ac0c9f6c Remove CVS $Id$ tag. 2007-08-08 11:11:18 -04:00
David F. Skoll
b136af88ad Remove $Id$ tag. 2007-08-07 10:02:18 -04:00
David F. Skoll
508b5f9aae ? 2007-08-07 10:01:22 -04:00
David F. Skoll
43dff67a60 Modify "make dist" target to use git-ls-files instead of peekentry into CVS. 2007-08-02 22:27:12 -04:00
David F. Skoll
41b850321f Fix warning about unused variables. 2007-08-02 22:17:27 -04:00
David F. Skoll
523237007b Remove CVS ident tags. 2007-08-02 22:15:58 -04:00
dfs
a3f6c5fd9c Fix range of years allowed by tkremind. 2007-07-29 03:17:58 +00:00
dfs
785cdc8726 Increase YR_RANGE from 88 to 4000. 2007-07-29 03:16:40 +00:00
dfs
cbf12b5601 Save screen real-estate. 2007-07-17 08:57:38 +00:00
dfs
1a6d59d9c0 Updated man page. 2007-07-17 01:30:10 +00:00
dfs
23ae054abb Add missing DestroyParser call. 2007-07-14 17:18:11 +00:00
dfs
b57852d3d8 Properly handle timed reminders in -sa mode. 2007-07-13 12:19:13 +00:00
dfs
c0e1be2f3a Fixed custom.h.in 2007-07-13 03:43:30 +00:00
dfs
a442a15a8d Fix typo. 2007-07-13 03:40:24 +00:00
dfs
f91bf634ad Add FROM keyword.
Make Calendar delta calculations use ShouldTriggerReminder for proper
delta calculation.
2007-07-13 03:36:15 +00:00
dfs
ce4311c3df Add support for FROM keyword (a slight variation on SCANFROM) 2007-07-12 23:36:03 +00:00
dfs
08e69cb541 Fix compile error. 2007-07-12 12:12:25 +00:00
dfs
f8e2eaed73 Suppress time on timed-reminders in "advanced" trigger in -sa mode. 2007-07-12 04:31:52 +00:00
dfs
e68a16e73d Update docs. 2007-07-12 04:27:44 +00:00
dfs
ca191fbd92 Remove ACKNOWLEDGEMENTS 2007-07-12 04:26:36 +00:00
dfs
10276826c0 Fix docs. 2007-07-12 04:25:38 +00:00
dfs
02c9129903 Added WHATSNEW 2007-07-12 03:46:29 +00:00
dfs
04e4c902bd Write wrappers for setenv/unsetenv for Solaris 9. 2007-07-12 03:29:14 +00:00
dfs
0663ae77de Fix more bugs in -sa mode. 2007-07-12 03:14:36 +00:00
dfs
0c0f5ea093 Fix bug in -sa option. 2007-07-12 03:09:44 +00:00
dfs
f450fd633e Check for setenv and unsetenv. 2007-07-09 01:55:45 +00:00
dfs
59cdd35f61 Adjust spacing for longer variable names. 2007-07-08 18:48:32 +00:00
dfs
eab67cbda4 Increase some limits. 2007-07-08 18:46:23 +00:00
dfs
b3c4a48641 In normal mode, convert SPECIAL COLOR to MSG. 2007-07-08 18:42:13 +00:00
dfs
07ac8ed341 Error-checking for out-of-range dates in tzconvert. 2007-07-08 18:32:07 +00:00
dfs
e32aa218fc Documented tzconvert. 2007-07-08 18:21:39 +00:00
dfs
09d11d36c3 Added tzconvert function. 2007-07-08 16:57:47 +00:00
dfs
629e287526 More man-page tweaks. 2007-07-05 02:05:41 +00:00
dfs
e2cd29c824 Documented built-in funcs that can take a DATETIME. 2007-07-05 02:02:01 +00:00
dfs
69e597dbe7 Kill off HAVE_PROTOS. 2007-07-03 03:42:46 +00:00
dfs
152e7ebac9 More man page updates. 2007-07-03 03:36:52 +00:00
dfs
8d4451ed85 Remove obsolete files. 2007-07-01 20:22:52 +00:00
dfs
5b8836d4b8 Make default datesep '-' in build.tk 2007-07-01 20:13:37 +00:00
dfs
be7086579e Make DateSep and TimeSep into system variables that can be changed
at runtime.
2007-07-01 20:12:15 +00:00
dfs
ab16c8f1fe More work on Remind. 2007-07-01 14:49:44 +00:00
dfs
6bb71ee5e3 In simple calendar and normal mode, treat SPECIAL COLOR the same as MSG 2007-06-29 02:11:02 +00:00
dfs
ebb4ebea97 Change trigdate, trigtime, trigdatetime to return 0 if trigger was not
valid.
2007-06-29 01:52:36 +00:00
dfs
bf97e62d56 Bump version to 3.1.0 2007-06-29 01:23:36 +00:00
dfs
47645cddb6 Added full support for DATETIME data type. 2007-06-29 01:17:39 +00:00
dfs
cf2af56a05 Allow DATETIME - DATETIME 2007-06-28 21:57:07 +00:00
dfs
50d1ae42c9 More work on a unified DATETIME type. 2007-06-28 03:20:37 +00:00
dfs
9501498a7e Add DATETIME type. 2007-06-28 03:04:44 +00:00
dfs
614ab08099 Apply sorting patch so SPECIAL HTMLs sort with MSG-type reminders
(from Ian! Allen)
2007-06-05 02:44:30 +00:00
dfs
64ee338433 Sort "today's" reminder popup. 2007-04-24 14:34:48 +00:00
dfs
43556238d0 Fix Yom Ha'atzmaut and Yom Hazikaron. 2007-04-24 14:34:41 +00:00
dfs
58d7ac0520 Make "distclean" remove test.out 2007-03-26 19:37:56 +00:00
dfs
0754678ce7 Update copyright year 2007-01-25 02:33:18 +00:00
dfs
2bea176816 Update usage output. 2007-01-25 02:32:25 +00:00
dfs
fa90333219 Add "a" modifier to -s and -p options (Frank Terbeck) 2007-01-25 02:28:53 +00:00
dfs
e007b3bc0f Change per Tony Morel. 2006-11-02 20:50:16 +00:00
dfs
978e83567b Incorporate patch at http://bugs.debian.org/cgi-bin/bugreport.cgi/03-broken-postscript.patch?bug=320415;msg=26;att=1 2005-12-31 23:05:24 +00:00
dfs
d01c1190cd Fix incorrect sizes for Ledger vs. Legal 2005-12-01 14:37:10 +00:00
dfs
0b1855df9b Updated WHATSNEW file. 2005-11-20 01:43:25 +00:00
dfs
951f2785cc Support arbitrarily-long DURATIONs 2005-11-20 01:26:59 +00:00
dfs
30090d3f8d Fix segmentation fault (Stan Tobias) 2005-11-20 00:40:51 +00:00
dfs
b6ad67891c Implement Paul Pelzl's patch for combining -n with -s/-p 2005-10-16 14:48:02 +00:00
dfs
b61c9db6e6 Noted removal of non-UNIX support. 2005-09-30 03:36:19 +00:00
dfs
29368ec2ee Documented $PrefixLineNo variable. 2005-09-30 03:33:52 +00:00
dfs
88ff86c910 Removed old non-ANSI, non-UNIX cruft. 2005-09-30 03:29:32 +00:00
dfs
0cc5ae521c Start getting rid of non-ANSI cruft. 2005-09-28 02:43:09 +00:00
dfs
da1b5ed9a0 Remove OS2_POPUP crap. 2005-09-28 02:39:11 +00:00
dfs
f786d05c04 More Makefile tweaks. 2005-07-02 04:10:15 +00:00
dfs
0bcbe9047e Make Makefile obey DESTDIR 2005-07-02 04:08:36 +00:00
dfs
585346f753 Prep for 3.0.24 release. 2005-04-15 16:30:11 +00:00
dfs
324aa01f80 Remove logo stuff from tkremind. 2005-04-14 17:34:34 +00:00
dfs
8d0adfa6b7 New logo in build.tk 2005-04-14 17:33:26 +00:00
dfs
bffae3724c Corrected typo in docs. 2005-04-14 12:30:58 +00:00
dfs
a60dc3d1c8 Set status to "Editor already active" if editor is open and a reminder
is right-clicked.
2005-04-12 13:50:29 +00:00
dfs
df9977d4da Force gzip. 2005-04-12 13:41:54 +00:00
dfs
c31678d28e Updated man page for tkremind. 2005-04-12 13:41:27 +00:00
dfs
40c1a5a3ee Add hooks so right-clicking on a reminder brings up file on that line. 2005-04-12 02:30:21 +00:00
dfs
846dbd9338 Fix it so "SPECIAL COLOR" reminders are sorted as if they were MSG-type
reminders in the calendar.
2005-04-12 01:49:45 +00:00
dfs
2bfed13ebc Updated copyright dates. 2005-04-12 01:27:52 +00:00
dfs
2a5c625a7f Updated WHATSNEW file. 2005-04-12 01:25:58 +00:00
dfs
7660e4a5f1 Updated COPYRIGHT 2005-04-12 01:25:52 +00:00
dfs
779672a5b5 Updated README files. 2005-04-12 01:18:22 +00:00
dfs
46e9ac86bc Skip comments in remind -p output. 2005-04-12 01:14:48 +00:00
dfs
8d6ca79934 Fix regression test error. 2005-04-12 00:59:41 +00:00
dfs
2212d1eebe Create bindir and mandir/man1 2005-04-12 00:57:56 +00:00
dfs
c78c284f19 Updated docs for -l option 2005-04-12 00:57:48 +00:00
dfs
b6b30637c6 Make rem2html ignore "#" lines. 2005-04-12 00:51:36 +00:00
dfs
b17198697c Make rem2ps ignore lines beginning with '#' 2005-04-12 00:49:07 +00:00
dfs
3ec57a608d Add -l option for printing out line numbers (Paul Pelzl) 2005-04-12 00:44:07 +00:00
dfs
49cd14846c Fix bug in parsing unterminated date literals. 2004-09-04 03:17:09 +00:00
dfs
1fd794a5bc Documented COLOR special and arbitrary media sizes. 2004-08-11 14:59:49 +00:00
dfs
5848991c27 Bump version to 03.00.23 2004-08-11 14:54:11 +00:00
dfs
d71f92d034 Fixed typos. 2004-08-11 02:22:35 +00:00
dfs
f9719ae7f5 Fixed typos. 2004-08-11 02:14:36 +00:00
dfs
4e0be6645a ? 2004-08-11 02:01:46 +00:00
dfs
da25a18610 Added support for SPECIAL COLOR. 2004-08-11 01:55:39 +00:00
dfs
7bc3aa52d4 Added support for SPECIAL COLOR and for arbitrary media sizes. 2004-08-11 01:55:32 +00:00
dfs
ca5bb13096 Added support for SPECIAL COLOR 2004-08-11 01:55:20 +00:00
dfs
da124475fa Allow specification of arbitrary media sizes in rem2ps. 2004-08-09 19:48:04 +00:00
dfs
ff04b2e481 Whitespace cleanup. 2001-11-06 15:51:37 +00:00
dfs
09d66135b2 Change phone number to work number. 2001-11-05 14:41:36 +00:00
dfs
65cb72f7e8 *** empty log message *** 2001-05-07 14:15:22 +00:00
dfs
8ae1f93899 Made canvas background white. 2001-05-07 14:14:21 +00:00
dfs
0017f81da5 Made timed reminders have finer (5-minute) granularity. 2001-05-07 14:13:15 +00:00
dfs
8c782c5b4e Updated docs. 2001-05-07 14:12:58 +00:00
dfs
ffd283d779 Updated docs. 2001-05-07 14:08:08 +00:00
dfs
b9227e11df Corrected Hebrew dates for Yom Hazikaron/Yom Ha'atzmaut when 5 Iyar
falls on a Saturday.
2001-05-07 14:06:17 +00:00
dfs
5a289add73 *** empty log message *** 2000-12-18 14:09:16 +00:00
dfs
614254a40d Added Icelandic language. 2000-12-18 14:05:29 +00:00
dfs
e31981c4c8 -- Bumped version to 3.0.22 2000-06-26 14:50:52 +00:00
dfs
eb67e7757b -- Doh. Config stuff. 2000-06-26 14:47:25 +00:00
dfs
ececf4a76e -- Added option to name cgi files *.cgi 2000-06-26 14:44:17 +00:00
dfs
0a437420d8 -- Fixed serious bug -- NumQueued was not being incremented. 2000-06-26 14:44:07 +00:00
dfs
b6ddc22c80 -- Added option to display all reminders on startup; added ability to delete
a reminder from the popup dialog.
2000-06-26 14:43:51 +00:00
dfs
83d88affb7 -- Updated documentation. 2000-06-26 14:43:34 +00:00
dfs
5ae835db6c -- Clarified build instructions. 2000-06-26 14:43:25 +00:00
dfs
47e16f5525 -- Updated docs. 2000-03-26 00:01:32 +00:00
dfs
a6a3dffbd6 -- Changed packing order so buttons don't disappear. 2000-03-25 23:59:30 +00:00
dfs
9d1fcb19bf -- Fixed bug in configure.in 2000-03-15 16:05:18 +00:00
dfs
7176277ddb -- Moved no-longer-supported files to OBSOLETE. 2000-03-15 16:03:36 +00:00
dfs
d9acf28ea5 -- Updated WHATSNEW doc. 2000-03-15 15:58:46 +00:00
dfs
00bbb8b159 -- Updated e-mail address. 2000-03-15 15:51:33 +00:00
dfs
dbe22e99ee -- Added -Wall -Wstrict-prototype to gcc invocation. 2000-03-15 15:42:37 +00:00
dfs
361aa04c6d -- Clarified build instructions. 2000-03-13 17:40:38 +00:00
dfs
7e82b93a84 *** empty log message *** 2000-03-12 12:52:02 +00:00
dfs
36731d2606 -- More copyright fixes. 2000-02-18 03:55:47 +00:00
dfs
2e3ca89e0b -- More copyright message fixes. 2000-02-18 03:53:45 +00:00
dfs
394c4d0791 -- Fixed typo. 2000-02-18 03:48:53 +00:00
dfs
2bc3d991c1 -- Updated contact info, copyright years, etc. 2000-02-18 03:45:11 +00:00
dfs
a479ea971d -- Added "dusk" and "dawn" functions, courtesy of Ron Aaron. 2000-02-18 03:08:18 +00:00
dfs
075a491847 -- Fixed typo in queue.c which caused compilation failure for compilers
without function prototypes.
2000-02-02 20:20:33 +00:00
dfs
fefaea005b -- Added syntax highlighting file for Vim. 2000-02-02 20:20:13 +00:00
dfs
c564fa6165 -- Updated WHATSNEW 2000-02-02 20:20:00 +00:00
dfs
0f4d6b5f8b -- Removed "id" field from queued reminder. 1999-10-18 20:38:48 +00:00
dfs
55059d60e7 -- Updated regression test. 1999-10-18 20:38:18 +00:00
dfs
d45b590e59 -- Got the www scripts working properly. 1999-10-18 20:08:54 +00:00
dfs
76938d27f9 -- Updated what's-new doc. 1999-10-18 20:08:46 +00:00
dfs
e89b5a2d91 -- Fixed makefile. 1999-10-18 19:58:46 +00:00
dfs
a9ffc57ce6 -- Modified Makefile for my system 1999-10-18 19:57:38 +00:00
dfs
97fdee4616 -- Converted .gif images to .png 1999-10-18 19:55:10 +00:00
dfs
f9884f3e9d -- Added cm2rem.tcl script 1999-10-18 19:54:56 +00:00
dfs
87b9dbf36b -- Documented changes. 1999-10-18 19:54:45 +00:00
dfs
415c49fdb9 -- First more-or-less working cm2rem.tcl script. 1999-08-30 16:27:58 +00:00
dfs
89cbe86ad9 -- Decreased size of .gif images. 1999-08-23 18:14:09 +00:00
dfs
db605a774c -- Started on cm2rem conversion script. 1999-08-23 18:13:56 +00:00
dfs
0e00cf4ee9 -- Updated WHATSNEW doc. 1999-08-23 18:13:42 +00:00
dfs
5bfac19a2e -- Changed version to 3.0.21
-- Made queue.c restore some globals (LastTriggerDate, etc.) before
   issuing a reminder.
-- Removed version number where superfluous.
-- Fixed typo in dynbuf.c
1999-04-21 01:47:59 +00:00
dfs
ea34bd0950 -- Changed version to 3.0.21 1999-04-21 01:47:08 +00:00
dfs
eea301cb53 -- Put Roaring Penguin notices in man pages. 1999-04-13 01:46:18 +00:00
dfs
bb62c3a9b4 -- Documented change to pure GPL. 1999-04-13 01:42:37 +00:00
dfs
879d31a555 -- Documented Roaring Penguin stuff. 1999-04-13 01:41:34 +00:00
dfs
104007b8cd -- Added Penguin logo to tkremind the first time you run it. :-) 1999-04-13 01:39:33 +00:00
dfs
116f8b805e -- Added Roaring Penguin logo to build script. :-) 1999-04-13 01:24:40 +00:00
dfs
b95b731817 -- Added Roaring Penguin copyright to tkremind and init.c 1999-04-12 19:45:27 +00:00
dfs
365d5285b3 -- Added Roaring Penguin copyright to tkremind 1999-04-12 19:44:36 +00:00
dfs
0bd4f230d2 *** empty log message *** 1999-04-05 17:42:35 +00:00
dfs
392b9e7a12 -- Updated acceptance test output for 3.0.20 1999-04-05 17:40:28 +00:00
dfs
f60fc18d1b -- Changed copyright notice to Roaring Penguin Software Inc. 1999-04-05 17:34:34 +00:00
dfs
524dcf86be -- Changed copyright notice to Roaring Penguin Software Inc.
-- Removed restriction on porting to Windows, but wrote why it's a bad idea.
1999-04-05 17:34:27 +00:00
dfs
a1d634dcb6 -- Updated COPYRIGHT. 1999-02-06 21:43:13 +00:00
dfs
d88bcf4a33 -- Updated documentation
-- Fixed typo in src/langs/danish.h
-- Added more print options to scripts/tkremind
1998-11-24 18:19:17 +00:00
dfs
a540d139af -- Updated version number. 1998-10-27 17:50:59 +00:00
dfs
06a4085aa6 -- Updated man page 1998-10-27 17:50:48 +00:00
dfs
225749e6aa -- Updated WHATSNEW 1998-10-27 17:50:40 +00:00
dfs
a169dc02fc -- Patch sent by Mikko Silvonen 1998-10-27 17:50:20 +00:00
dfs
8cc9b44975 -- Non-PostScript "specials" were being passed through to PostScript
output.  DOH!  Bug report and fix courtesy Derek J Decker.
1998-08-15 14:19:05 +00:00
dfs
5c478cd6c9 -- Made textmode calendar allowed to be as small as 71 columns. 1998-07-18 03:16:37 +00:00
dfs
a2ffdfcc4f -- Proper fix to the "..." problem -- now gets correctly added in all
calendar boxes, even with moons.
1998-07-07 02:55:58 +00:00
dfs
5ba43e981d -- Made TkRemind put "....." separator even if there's a moon phase in
the calendar box.
1998-06-07 20:31:08 +00:00
dfs
87c948bb03 -- Added Spanish to build.tk 1998-05-24 15:43:34 +00:00
dfs
e4c85b7a49 -- Added Spanish language file 1998-05-24 15:40:13 +00:00
dfs
04f6b3223b -- Made queue.c work on Solaris and SunOS 1998-05-10 02:46:43 +00:00
dfs
9b3d4281ad -- Updated WHATSNEW.30 1998-05-10 02:32:24 +00:00
dfs
e0dd960ba6 -- Updated LSM. 1998-05-10 02:32:15 +00:00
dfs
f51e4f0fda -- Updated docs. 1998-05-10 02:20:38 +00:00
dfs
4a04089285 -- Allowed sources/objects to be in different directories. 1998-05-10 02:19:20 +00:00
dfs
47cb7a4e01 -- Modified rem2html documentation. 1998-05-10 01:29:23 +00:00
dfs
904f6f55f5 -- Fixed install target in makefile.
-- Added __sun__ test to queue.c
1998-05-10 01:29:12 +00:00
dfs
d2e2bf982e -- Updated man page. 1998-05-10 01:28:53 +00:00
dfs
ab59a2e575 -- Clarified copyright.
-- Added make distclean target.
1998-05-06 01:51:11 +00:00
dfs
e12462630e -- Updated man pages. 1998-05-06 01:47:41 +00:00
dfs
65f62d6012 -- Updated documentation 1998-05-06 01:47:27 +00:00
dfs
0e6f7f5e35 -- Updated documentation and man pages
-- Fixed examples to use SPECIAL SHADE and SPECIAL MOON
1998-05-05 03:16:17 +00:00
dfs
a8e977f8b7 -- Fixed minor bug in regexp to pick out tags. 1998-05-01 02:19:52 +00:00
dfs
8dac9848ee -- Updated man page. 1998-04-29 02:50:24 +00:00
dfs
e0129313c4 -- Made the SHADE and MOON specials work in rem2html.
-- Added little moon icons.
1998-04-23 02:57:06 +00:00
dfs
85c5dc6d26 -- Fixed minor problem in calendar resizing. 1998-04-23 02:56:46 +00:00
dfs
84a9aa22b4 -- Made TkRemind not quit if Remind screws up 1998-04-19 03:52:46 +00:00
dfs
102cbcc181 -- Made REMIND accept group-writable files. 1998-04-19 03:39:43 +00:00
dfs
db37d11d52 -- Corrected swap of moon images 1998-04-19 03:39:31 +00:00
dfs
dad6343f1e -- Updated WHATSNEW file 1998-04-19 03:39:17 +00:00
dfs
eaecc4d3f4 -- Made TkRemind understand MOON and SHADE specials. 1998-04-19 03:27:03 +00:00
dfs
9c1b04b3fe -- Made rem2ps handle the SHADE and MOON specials. 1998-04-19 03:03:25 +00:00
dfs
f9e28c39f9 -- Added "start iconified" option; made TkRemind unset Ignore array
when date rolls over.
1998-03-31 02:39:20 +00:00
dfs
63983d4f49 -- Removed debugging stuff from TkRemind. 1998-03-30 05:10:34 +00:00
dfs
a39088084e -- Made queued reminders carry the tag around (for TkRemind) 1998-03-30 05:08:51 +00:00
dfs
5973cb7631 -- Major changes to TkRemind: Stores options in ~/.tkremindrc; lets
you beep terminal, run commands, deiconify calendar when background
   reminders pop up.
-- Lets you tell TkRemind not to re-issue tagged pop-up reminders.
1998-03-30 05:08:34 +00:00
dfs
9a9da33989 -- Made tkremind not destroy and recreate calendar window each time.
Speed improvement plus we don't need the silly geometry kludge.
1998-03-25 04:24:59 +00:00
dfs
8a5df61642 -- Fixed spurious entries in calendar mode 1998-03-25 02:47:19 +00:00
dfs
6ca72652a3 -- Stopped accumulation of spurious blank lines in interactive reminder
editing.
1998-03-21 03:57:08 +00:00
dfs
ce1a0c3605 -- Got interactive editing of reminders working. 1998-03-21 03:49:47 +00:00
dfs
920699e17b -- Beginning of infrastructure for editing reminders from TkRemind. 1998-03-13 02:52:20 +00:00
dfs
83f24cd94f -- Fixed bug: Times were not being placed in calendar mode. 1998-03-04 18:13:26 +00:00
dfs
c9aa3000d1 -- Made tkremind reinitialize on date rollover. 1998-03-04 18:13:13 +00:00
dfs
08d2a36f2f -- Made TkRemind properly handle problems with running Remind because
of security features (even as Daemon)
1998-03-02 20:01:29 +00:00
dfs
eebe3733fc -- Caught wm . WM_DELETE_WINDOW 1998-03-02 19:55:41 +00:00
dfs
67aab59d19 -- Added "-z0" option to Remind for "daemonized" control by Tk front-end. 1998-03-02 19:38:33 +00:00
dfs
c1e4e42763 -- New custom.h 1998-03-01 21:04:27 +00:00
dfs
f3b85cec38 -- Prettied up build.tk a bit. 1998-03-01 21:03:36 +00:00
dfs
dc346f126d -- Updated version numbers. 1998-03-01 20:44:19 +00:00
dfs
b565353372 -- Updated Romanian module 1998-03-01 20:44:10 +00:00
dfs
b1e70ef272 -- Fixed uninitialized variable error.
-- Fixed syntax error for non-English languages
-- Updated version
1998-03-01 20:43:53 +00:00
dfs
ae072a2fa3 -- Made tkremind fail gracefully if Remind security features kick in 1998-03-01 20:43:23 +00:00
dfs
39d8fe3523 -- Updated WHATSNEW files. 1998-03-01 20:43:04 +00:00
dfs
048638cdda -- Updated build.tk to use new character set options. 1998-03-01 20:42:54 +00:00
dfs
70ae23809f -- Used difftime if available. 1998-02-16 03:41:38 +00:00
dfs
260d66b20f -- Fixed CalcMinsFromUTC 1998-02-16 03:32:27 +00:00
dfs
4b38ffdf12 -- Fixed bug in CalcMinsFromUTC 1998-02-16 03:20:46 +00:00
dfs
7ff0315ae9 -- Update tar file size in lsm 1998-02-16 02:45:09 +00:00
dfs
ce5a828896 -- Bleh. 1998-02-16 02:35:18 +00:00
dfs
a6686ab4a2 -- Updated man page dates 1998-02-16 02:35:09 +00:00
dfs
55e07e7326 -- Added acknowledgement blurb to "build.tk" 1998-02-16 02:35:00 +00:00
dfs
3cd69d3cb4 -- Fixed HTML calendar script to use "SPECIAL HTML" 1998-02-16 02:21:45 +00:00
dfs
8531f8b5b4 -- Fixed typo 1998-02-14 04:04:38 +00:00
dfs
9a6eef11ea -- Updated copyright year 1998-02-14 04:04:31 +00:00
dfs
ede057e8d1 -- Updated copyright notices. 1998-02-14 03:56:27 +00:00
dfs
22d3a18116 -- Fixed custom.h and custom.h.in 1998-02-14 03:41:39 +00:00
dfs
d37d2c08d9 -- Defined _SVID_SOURCE 1998-02-14 03:40:10 +00:00
dfs
49a9dfb0d3 -- Sorted language names in build.tk 1998-02-14 03:39:40 +00:00
dfs
69d85c5228 -- Compiles with no warnings with -Wall flag 1998-02-14 03:31:58 +00:00
dfs
6d5ed33b54 -- Made remind print a warning if $RunOff is tested in verbose mode. 1998-02-12 03:48:28 +00:00
dfs
d380f4571b -- Updated WHATSNEW.30
-- Updated Remind.1 man page
-- Made rem2html escape special HTML characters
-- Made Remind parser more forgiving. (!)
1998-02-12 03:32:05 +00:00
dfs
418e9ff265 -- Updated WHATSNEW.30
-- Fixed some more bugs.
1998-02-10 04:11:34 +00:00
dfs
c31b2e1d27 -- Yet more bug fixes. 1998-02-10 03:33:48 +00:00
dfs
38280bed8a -- Pass some more basic tests.
-- Updated copyright year.
1998-02-10 03:15:46 +00:00
dfs
f4e09f9e96 -- Got dynamic-buffer version to pass acceptance test. 1998-02-09 00:25:45 +00:00
dfs
ce88211f50 -- Replaced static buffers with dynamic ones and broke everything. 1998-02-07 05:35:50 +00:00
dfs
f8d91f559a -- Removed unneeded L_DAYINIT macro. 1998-02-02 02:58:20 +00:00
dfs
b936e3994b -- Made remind -p always use '/' as date separator to simplify lives
of back-ends.
1998-02-02 02:58:08 +00:00
dfs
bf5a11e1a3 -- Documented remind -p format.
-- Documented some new features (SPECIAL).  Still need to do
   TAG and DURATION.
1998-02-02 02:57:46 +00:00
dfs
0fac20e467 -- Updated WHATSNEW file. 1998-02-02 02:57:20 +00:00
dfs
0a990f91ee -- Made output of "remind -p" include day names so back-ends can
adapt to non-English languages.
1998-01-24 03:20:01 +00:00
dfs
c0d14e6d62 -- Made "install" target strip binaries. 1998-01-20 03:14:20 +00:00
dfs
01455ed0c2 -- custom.h noise 1998-01-19 03:33:54 +00:00
dfs
727eebfabc -- Updated WHATSNEW.30 file. 1998-01-19 03:33:46 +00:00
dfs
8841d03fe5 -- Added ACKNOWLEDGEMENTS file. 1998-01-19 03:33:34 +00:00
dfs
4828cfdbf6 -- Fixed "install" target in top-level Makefile. 1998-01-19 03:27:36 +00:00
dfs
41310f5a05 -- Custom.h noise. 1998-01-19 03:24:20 +00:00
dfs
d3325809ab -- Improved build.tk a bit. 1998-01-19 03:24:03 +00:00
dfs
1a538a0112 -- Got working version of graphical configure/build utility! 1998-01-19 03:07:09 +00:00
dfs
b64ac87881 -- Fixed ISOLATIN1 and IBMEXTENDED tests. 1998-01-17 22:09:59 +00:00
dfs
2fe7595d76 -- Made Makefile install man pages in the correct location. 1998-01-17 22:09:44 +00:00
dfs
5a22d20ed4 -- Updated top-level makefile. 1998-01-17 05:00:38 +00:00
dfs
df0bcfc1d2 -- Added $Id$ string to Makefile. 1998-01-17 04:51:52 +00:00
dfs
22c169fea8 -- Added top-level Makefile. 1998-01-17 04:51:21 +00:00
dfs
87cfe53b52 -- Made UNIX acceptance test work. 1998-01-17 04:51:04 +00:00
dfs
2db390d2e2 -- Made check for TM_IN_SYS_TIME_H 1998-01-17 04:50:50 +00:00
dfs
f2128d4cb6 -- Clarified documentation. 1998-01-17 04:50:33 +00:00
dfs
02a7023040 -- Made a one-step "make install"
-- Clarified copyright.
1998-01-17 04:50:16 +00:00
dfs
931e7a7b26 -- Made source compatible with autoconf script. 1998-01-17 03:58:26 +00:00
dfs
05b3808e5c -- Added "unconfigure" script. 1998-01-17 03:58:12 +00:00
dfs
bc95350f1e -- Modified autoconf settings to create src/Makefile. 1998-01-15 03:28:31 +00:00
dfs
0ff20006c7 -- Rearranged directory structure; starting conversion to autoconf. 1998-01-15 02:49:26 +00:00
dfs
1ba2968df8 -- Updated finnish.h from Mikko Silvonen. 1998-01-12 02:19:21 +00:00
dfs
c4fd7e3176 -- Updated URL for Finnish holidays. 1998-01-01 02:01:26 +00:00
dfs
e1cf4d5e70 - Added TAG and DURATION clauses for communicating more information to
back-ends and eventually converting REMIND into a full-fledged
  scheduler.

- Completely reworked the PS/PSFILE mechanism to use the more
  general SPECIAL mechanism for customizing output in REMIND back-ends.

- Modified tkremind, rem2ps and www/rem2html to use new "SPECIAL"
  communication channel.
1997-09-21 23:23:34 +00:00
dfs
31bc3c8aa8 -- Added TAG, DURATION and SPECIAL keywords and associated handling. 1997-09-16 03:16:30 +00:00
dfs
dd917df96f -- Removed use of difftime() -- SunOS doesn't have it. 1997-09-07 19:19:11 +00:00
dfs
a15e9bc2b4 -- Removed unnecessary chown's from www Makefile -- the www scripts
have RUN commands only in "inline" scripts supplied from stdin.
1997-08-31 17:17:51 +00:00
dfs
254f340f4c -- Made WWW Makefile do a "chown" to accomodate Remind security features. 1997-08-31 17:09:45 +00:00
dfs
800438a1d1 -- Clarified rem2html documentation. 1997-08-31 17:03:45 +00:00
dfs
8eb2028cf2 -- Made REMIND disable "RUN" on files not owned by its effective UID.
-- Updated copyright year.
1997-08-31 17:03:25 +00:00
dfs
ef2aa97967 -- Documented security features in man page. 1997-08-01 02:28:31 +00:00
dfs
165db3d5b6 -- Made HTML Hebrew calendar "self-linking" with links to next and
previous months.
1997-07-31 03:10:17 +00:00
dfs
76e0c78d15 -- Added HTML hebrew calendar; fixed wording here and there. 1997-07-31 02:19:04 +00:00
dfs
2d5d6d1f56 -- Added romanian.h to MANIFEST. 1997-07-31 01:57:10 +00:00
dfs
6248fd1808 -- Added "\n" to message. 1997-07-31 01:52:46 +00:00
dfs
2c9465b4bb -- Fixed bug in CheckSafety. 1997-07-31 01:51:18 +00:00
dfs
7897067eda -- Added UNIX security checks. 1997-07-31 01:49:37 +00:00
dfs
3c53ab13c9 -- Increased some static buffer sizes.
-- Added security features to "-u" option -- it now implies -r.
-- Remind refuses to run if installed set-uid or set-gid.
1997-07-30 01:30:56 +00:00
dfs
f32e0027ad -- Increased some static buffer sizes.
-- Made Remind ignore trailing commas at end of tokens.
1997-07-13 16:18:48 +00:00
dfs
4c46eb5fee -- Clarified Remind licensing issues. 1997-07-06 14:36:01 +00:00
dfs
a1fc29e66d -- Fixed CalcMinsFromUTC to work with unsigned time_t
-- Added rem2html.
1997-07-06 14:34:37 +00:00
dfs
8e17c968e2 CalcMinsFromUTC was failing if time_t was unsigned. I really _should_
use difftime(), but not all systems have it.  Also, defs.rem was
rearranged so PostScript stuff works better, and new target "emxomf"
was added to makefile.ost which uses OMF linking and a
dynamically-linked C library.  All three of these fixes are courtesy
of Christopher J. Madsen <madsen@iglobal.net>.  Thanks, Christopher.
1997-03-31 22:13:08 +00:00
dfs
ef9f13e83d -- Changed version to 3.0.17
-- Added romanian.h to manifest
-- Made code compile properly on compilers that don't grok 'const'
-- Changed PostScript output to be more compatible with Adobe recommendations
-- Fixed comment characters in HTML stuff
1997-03-30 19:07:35 +00:00
dfs
b5cb430fe4 -- Fixed grammer in WHATSNEW.30
-- Fixed bug in queue.c -- if you used -g option, background reminders
   were not issued.
-- Fixed WWW README.
1997-02-11 01:44:29 +00:00
dfs
a12cd4234c -- Added calendar.html-DIST.
-- Fixed bugs in missing newlines after Content-Type: header in hebdate
   and hebps.
1997-01-19 03:59:55 +00:00
dfs
100f038ae1 Made makefile slightly prettier.
Cleaned up www/Makefile.
Adjusted LSM to note www scripts.
1997-01-16 04:31:07 +00:00
dfs
e1730460fe Changed copyright date to 1997.
Added documentation about WWW server stuff.
1997-01-16 04:14:18 +00:00
dfs
00c2383738 -- Added more details to Makefile and README. 1997-01-16 04:05:31 +00:00
dfs
0f167686d9 Initial checkin of www stuff 1997-01-16 04:00:26 +00:00
dfs
d0be59edff -- Changed version number.
-- Made sunrise() and sunset() distinguish between cases when sun never
   rises and sun never sets.
1996-12-18 00:20:43 +00:00
dfs
dfbbafe87b Added support for Romanian. 1996-12-10 02:36:32 +00:00
dfs
3183d6340e Added portbr.h to Manifest. 1996-10-27 21:49:54 +00:00
176 changed files with 41111 additions and 16837 deletions

4
.gitattributes vendored Normal file
View File

@@ -0,0 +1,4 @@
.gitignore export-ignore
.gitattributes export-ignore
remind.php export-ignore
sync-to-dianne-git export-ignore

16
.gitignore vendored Normal file
View File

@@ -0,0 +1,16 @@
*.bak
autom4te.cache
config.log
config.status
src/Makefile
www/Makefile
*.o
src/config.h
src/remind
src/*.tar.gz*
tests/test.out
.gitignore
*~
src/rem2ps
src/version.h
TAGS

View File

@@ -1,25 +1,15 @@
$Id: COPYRIGHT,v 1.4 1996-10-12 03:13:04 dfs Exp $
THE REMIND COPYRIGHT
1. REMIND refers to the entire set of files and documentation in the
REMIND package.
2. REMIND is Copyright 1992-1996 by David Skoll,
except where noted in individual files.
2. REMIND is Copyright 1992-2020 Dianne Skoll, except where noted in
individual files.
3. DISTRIBUTION AND USE
a) REMIND may not be used under Microsoft Windows (3.0, 3.1, 95
or NT) or any future version of Windows. Such use constitutes
a violation of copyright.
b) REMIND may not be used by Cadabra Design Libraries Inc. or its
directors, nor by any of Cadabra's subsidiaries or their directors.
Such use constitutes a violation of copyright.
c) Except for situations (a) and (b), REMIND may be used and
distributed according to the terms of the GNU General Public
License, Version 2, which follows:
REMIND may be used and distributed according to the terms of the
GNU General Public License, Version 2, which follows:
GNU GENERAL PUBLIC LICENSE
@@ -302,56 +292,9 @@ PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
ACKNOWLEDGEMENTS:
I would like to thank the following people:
Bill Aten <netagw!bill@uunet.UU.NET> for providing remind-all.sh
Bradley D. Keister <keister@poincare.phys.cmu.edu>, Rhys Weatherly
rhys@batserver.cs.uq.OZ.AU> and Anthony Cheng for initially providing
the Turbo C compiler support.
Dennis Cottel <dennis@peanuts.nosc.mil> for providing the patch to
produce calendars by weeks as well as by months.
Bill Silvert <bill%biomel@cs.dal.ca> and Dennis Cottel
<dennis@peanuts.nosc.mil> for suggesting many of the new features in
REMIND.
Dave Wolfe <dwolfe@pffft.sps.mot.com> and Raphael Manfredi
<ram@eiffel.com> for noticing bugs and sending me fixes.
Dave Rickel and George M. Sipe for sample reminders and holidays.
Michael Salmon for ISO encoding of PostScript output.
Darrel Hankerson for helping me provide some OS/2 support. Sorry
it's not complete, Darrel!
Phillipp Slusallek for suggesting the -k option.
Amos Shapir, David W. Tamkin and Frank Yellin for help with the Hebrew
calendar.
All of the language translators whose names are listed in lang.h
Timo Salmi, Keith Petersen, Bill Davidsen and Kent Landfield for
maintaining the uwasa and SIMTEL archives, and comp.binaries.ibm.pc
and comp.sources.misc in the face of a flurry of updates to REMIND.
All others who have corresponded with me to report bugs, express
appreciation or suggest features - too many people to list here.
Finally, all those who donated money to support the production of
REMIND. Your donations were gratefully appreciated.
--
David F. Skoll <dfs@doe.carleton.ca> <aa775@freenet.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Dianne Skoll <dianne@skoll.ca>
https://dianne.skoll.ca/projects/remind
Tel. (613) 225-8687

30
MICROSOFT-AND-APPLE Normal file
View File

@@ -0,0 +1,30 @@
MICROSOFT WINDOWS
=================
I used to prohibit porting Remind to Microsoft Windows. However, this
may cause problems with the GPL, so I have removed that restriction.
Although I cannot prevent you from porting Remind to Windows, I appeal
to you not to do it. I am trying to encourage the growth of free
software, not proprietary software.
If you port Remind to Windows, I will not provide support or answers to
questions -- you're on your own. On the other hand, I will feel no guilt
in taking enhancements and merging them into the UNIX stream.
APPLE
=====
I can't prevent you from using Remind on Apple's products, but I hope
you don't. Apple's corporate culture is the very antithesis of Free
Software. Rather than using Mac OS X, I encourage you to switch to
Linux or FreeBSD, two Free Software operating systems that are every
bit as capable as Mac OS X and which are unencumbered by Apple's
arbitrary restrictions.
And if you're looking to port Remind to other Apple products like the
iPhone or iPad, please don't. Those products enforce Apple's rigorous
controls much more stringently than Mac OS X on an Apple PC.
--
Dianne Skoll

234
Makefile
View File

@@ -1,215 +1,37 @@
# Makefile for REMIND
# $Id: Makefile,v 1.14 1996-10-27 21:28:03 dfs Exp $
# Top-level Makefile for Remind.
#-----------------------------------------------------------------------------
# THINGS FOR YOU TO EDIT START BELOW
#-----------------------------------------------------------------------------
all: src/Makefile
@echo ""
@echo "*******************"
@echo "* *"
@echo "* Building REMIND *"
@echo "* *"
@echo "*******************"
@echo ""
@cd src && $(MAKE) all LANGDEF=$(LANGDEF)
# Uncomment the next line if you are running on a SYSV system
SYSV= -DSYSV
# Uncomment the next line if you are running under UNIX (including SYSV!)
UNIX= -DUNIX
# Uncomment the next lines if you want to use gcc instead of default compiler
# NOTE: Tempting as it may be, if you use 'cc' for the C compiler, do not
# use 'ld' for the linker. It will probably work much better if you use
# LD= cc rather than LD= ld.
CC= gcc
LD= gcc
# Put any additional flags for the C compiler or linker here - if you
# are not using gcc, you probably want to remove '-ansi -pedantic -Wall'.
CFLAGS= -O -ansi -pedantic -Wall
CDEFS=
LDFLAGS=
#### INSTALLATION LOCATIONS ####
# Note that I use 'cp' rather than 'install' for improved portability.
#
# BINDIR: Where should the Remind executable be installed?
BINDIR= /usr/local/bin
# SCRIPTDIR: Where should the kall and rem shell scripts be installed?
SCRIPTDIR= /usr/local/bin
# MANDIR: Where should the man pages be installed?
MANDIR= /usr/local/man
# MANSECT: Which man section should the man pages go into?
MANSECT= 1
# EXEMODE: What file protection mode should be used for the executables?
EXEMODE= 755
# MANMODE: What file protection mode should be used for the man pages?
MANMODE= 644
# OWNER, GROUP: What owner and group to use for executables,
# scripts and man pages?
OWNER=bin
GROUP=bin
#-----------------------------------------------------------------------------
# YOU SHOULDN'T EDIT ANYTHING BELOW HERE. You may want to change some things
# in config.h; then, you should be able to type 'make'.
#-----------------------------------------------------------------------------
VERSION= 03.00.15
MATHLIB= -lm
HDRS= config.h err.h expr.h globals.h protos.h types.h version.h \
lang.h english.h german.h dutch.h finnish.h french.h norwgian.h \
danish.h polish.h
STDHDRS= config.h types.h protos.h globals.h err.h lang.h
LANGHDRS= english.h german.h dutch.h finnish.h french.h norwgian.h danish.h \
polish.h portbr.h italian.h
SRCS= calendar.c dorem.c dosubst.c expr.c files.c funcs.c globals.c hbcal.c \
init.c main.c moon.c omit.c sort.c queue.c token.c trigger.c userfns.c \
utils.c var.c
MANIFEST=COPYRIGHT Makefile Makefile_QDOS README.AMIGA README.BCC \
README.DOS README.OS2 README.UNIX README_QDOS WHATSNEW.30 \
amiga-SCOPTIONS amiga.c calendar.c config.h danish.h defs.rem dorem.c \
dosubst.c dutch.h english.h err.h expr.c expr.h files.c finnish.h \
french.h funcs.c german.h globals.c globals.h hbcal.c init.c italian.h kall \
kall.1 lang.h lnk.bcc lnk.msc lnk.tc main.c makefile.bcc makefile.msc \
makefile.os2 makefile.tc moon.c norwgian.h omit.c os2func.c polish.h \
protos.h queue.c rem rem.1 rem2ps.1 rem2ps.c rem2ps.h remind-all.csh \
remind-all.sh remind.1 remind.def smakefile sort.c test-rem \
test-rem.ami test-rem.bat test-rem.cmd test-rem.rexx test.cmp test.rem \
test1.cmp test2.cmp tkremind tkremind.1 token.c trigger.c tstlang.rem \
types.h userfns.c utils.c var.c version.h remind.LSM
OBJS= $(SRCS:.c=.o)
all: remind rem2ps
.c.o:
$(CC) $(UNIX) $(SYSV) -c $(CFLAGS) $(CDEFS) $*.c
rem2ps: rem2ps.o
$(LD) $(LDFLAGS) -o rem2ps rem2ps.o
remind: $(OBJS)
$(LD) $(LDFLAGS) -o remind $(OBJS) $(MATHLIB)
install:
@echo ""
@echo "*********************"
@echo "* *"
@echo "* Installing REMIND *"
@echo "* *"
@echo "*********************"
@echo ""
@cd src && $(MAKE) install
clean:
rm -f *.o *~ core *.bak
find . -name '*~' -exec rm {} \;
cd src && $(MAKE) clean
clobber:
rm -f *.o *~ remind rem2ps test.out core *.bak
test:
@cd src && $(MAKE) -s test
test: remind
sh test-rem
distclean: clean
rm -f config.cache config.log config.status src/Makefile src/config.h tests/test.out www/Makefile
rem2ps.o: rem2ps.c rem2ps.h lang.h config.h
calendar.o: calendar.c $(STDHDRS) expr.h
dorem.o: dorem.c $(STDHDRS) expr.h
dosubst.o: dosubst.c $(STDHDRS) $(LANGHDRS)
expr.o: expr.c $(STDHDRS) expr.h
files.o: files.c $(STDHDRS)
funcs.o: funcs.c $(STDHDRS) expr.h version.h
globals.o: globals.c config.h types.h globals.h err.h lang.h $(LANGHDRS)
hbcal.o: hbcal.c $(STDHDRS)
init.o: init.c $(STDHDRS) expr.h version.h lang.h $(LANGHDRS)
main.o: main.c $(STDHDRS) expr.h
moon.o: moon.c $(STDHDRS)
omit.o: omit.c $(STDHDRS)
sort.o: sort.c $(STDHDRS)
queue.o: queue.c $(STDHDRS)
token.o: token.c $(STDHDRS)
trigger.o: trigger.c $(STDHDRS) expr.h
userfns.o: userfns.c $(STDHDRS) expr.h
utils.o: utils.c $(STDHDRS)
var.o: var.c $(STDHDRS) expr.h
src/Makefile: src/Makefile.in
./configure
# Some of these targets are just for my convenience and
# probably won't be too useful to you! -- dfs
# DO NOT DELETE
tgz:
-rm -rf remind-$(VERSION)
-mkdir remind-$(VERSION)
cd remind-$(VERSION); for i in $(MANIFEST) ;do ln -s ../$$i .; done; cd ..
tar -c -h -v -f remind-3.0.15.tar remind-$(VERSION)
gzip -v -9 remind-3.0.15.tar
mv remind-3.0.15.tar.gz remind-3.0.15.tgz
rm -rf remind-$(VERSION)
shar:
shar -o./Shar -sdfs@doe.carleton.ca -a -c -n"Remind $(VERSION)" -m -l58 -o./Shar $(MANIFEST)
backup:
tar cvzf ../rbackup.tgz $(MANIFEST)
zip:
zip ../rbackup.zip $(MANIFEST)
todos:
rm -rf DOS
mkdir DOS
for i in $(MANIFEST) ; do todos < $$i > DOS/$$i; done
transmit:
sz -a -e $(MANIFEST)
install: install-bin install-scripts install-man
install-bin: remind rem2ps
cp remind $(BINDIR)/remind
-chmod $(EXEMODE) $(BINDIR)/remind
-chown $(OWNER) $(BINDIR)/remind
-chgrp $(GROUP) $(BINDIR)/remind
cp rem2ps $(BINDIR)/rem2ps
-chmod $(EXEMODE) $(BINDIR)/rem2ps
-chown $(OWNER) $(BINDIR)/rem2ps
-chgrp $(GROUP) $(BINDIR)/rem2ps
install-scripts:
cp kall $(SCRIPTDIR)/kall
-chmod $(EXEMODE) $(SCRIPTDIR)/kall
-chown $(OWNER) $(SCRIPTDIR)/kall
-chgrp $(GROUP) $(SCRIPTDIR)/kall
cp rem $(SCRIPTDIR)/rem
-chmod $(EXEMODE) $(SCRIPTDIR)/rem
-chown $(OWNER) $(SCRIPTDIR)/rem
-chgrp $(GROUP) $(SCRIPTDIR)/rem
cp tkremind $(SCRIPTDIR)/tkremind
-chmod $(EXEMODE) $(SCRIPTDIR)/tkremind
-chown $(OWNER) $(SCRIPTDIR)/tkremind
-chgrp $(GROUP) $(SCRIPTDIR)/tkremind
install-man:
cp remind.1 $(MANDIR)/man$(MANSECT)/remind.$(MANSECT)
-chmod $(MANMODE) $(MANDIR)/man$(MANSECT)/remind.$(MANSECT)
-chown $(OWNER) $(MANDIR)/man$(MANSECT)/remind.$(MANSECT)
-chgrp $(GROUP) $(MANDIR)/man$(MANSECT)/remind.$(MANSECT)
cp tkremind.1 $(MANDIR)/man$(MANSECT)/tkremind.$(MANSECT)
-chmod $(MANMODE) $(MANDIR)/man$(MANSECT)/tkremind.$(MANSECT)
-chown $(OWNER) $(MANDIR)/man$(MANSECT)/tkremind.$(MANSECT)
-chgrp $(GROUP) $(MANDIR)/man$(MANSECT)/tkremind.$(MANSECT)
cp rem.1 $(MANDIR)/man$(MANSECT)/rem.$(MANSECT)
-chmod $(MANMODE) $(MANDIR)/man$(MANSECT)/rem.$(MANSECT)
-chown $(OWNER) $(MANDIR)/man$(MANSECT)/rem.$(MANSECT)
-chgrp $(GROUP) $(MANDIR)/man$(MANSECT)/rem.$(MANSECT)
cp kall.1 $(MANDIR)/man$(MANSECT)/kall.$(MANSECT)
-chmod $(MANMODE) $(MANDIR)/man$(MANSECT)/kall.$(MANSECT)
-chown $(OWNER) $(MANDIR)/man$(MANSECT)/kall.$(MANSECT)
-chgrp $(GROUP) $(MANDIR)/man$(MANSECT)/kall.$(MANSECT)
cp rem2ps.1 $(MANDIR)/man$(MANSECT)/rem2ps.$(MANSECT)
-chmod $(MANMODE) $(MANDIR)/man$(MANSECT)/rem2ps.$(MANSECT)
-chown $(OWNER) $(MANDIR)/man$(MANSECT)/rem2ps.$(MANSECT)
-chgrp $(GROUP) $(MANDIR)/man$(MANSECT)/rem2ps.$(MANSECT)
release:
-mkdir RELEASE
-rm -f RELEASE/*
mkpatch ../prev . patch.15 Shar "Remind-3.0/Patch-15/part"
mv Shar* RELEASE
rm -f patch.15*
for i in *.1; do nroff -man $$i | sed -e 's/_//g' > `basename $$i .1`.man; done
mv *.man RELEASE
for i in *.1; do groff -man -Tps $$i > `basename $$i .1`.ps; done
mv *.ps RELEASE

View File

@@ -1,86 +0,0 @@
#$Id: Makefile_QDOS,v 1.3 1996-09-28 18:17:06 dfs Exp $
# Makefile for REMIND for QDOS / SMSQ
#-----------------------------------------------------------------------------
# THINGS FOR YOU TO EDIT START BELOW
#-----------------------------------------------------------------------------
# Uncomment the next lines if you want to use gcc instead of default compiler
# NOTE: Tempting as it may be, if you use 'cc' for the C compiler, do not
# use 'ld' for the linker. It will probably work much better if you use
# LD= cc rather than LD= ld.
# QDOS remark: I made it work the following way, and I found it to be working.
CC= cc
LD= ld
# Put any additional flags for the C compiler or linker here - if you
# are not using gcc, you probably want to remove '-ansi'.
# QDOS remark: no -ansi option and no gcc on QDOS / SMSQ
CFLAGS= -V -O -DQDOS
CDEFS=
LDFLAGS= -bufp200K
#-----------------------------------------------------------------------------
# YOU SHOULDN'T EDIT ANYTHING BELOW HERE. You may want to change some things
# in config_h; then, you should be able to type 'make'.
#-----------------------------------------------------------------------------
VERSION= 03.00.15
MATHLIB= -lm
HDRS= config_h err_h expr_h globals_h protos_h types_h version_h \
lang_h english_h german_h dutch_h finnish_h french_h norwgian_h \
danish_h polish_h
STDHDRS= config_h types_h protos_h globals_h err_h lang_h
LANGHDRS= english_h german_h dutch_h finnish_h french_h norwgian_h danish_h \
polish_h
SRCS= calendar_c dorem_c dosubst_c expr_c files_c funcs_c globals_c hbcal_c \
init_c main_c moon_c omit_c sort_c queue_c token_c trigger_c userfns_c \
utils_c var_c
OBJS= calendar_o dorem_o dosubst_o expr_o files_o funcs_o globals_o hbcal_o \
init_o main_o moon_o omit_o sort_o queue_o token_o trigger_o userfns_o \
utils_o var_o
all: remind rem2ps
# _c_o:
# $(CC) $(UNIX) $(SYSV) -c $(CFLAGS) $(CDEFS) $*_c
rem2ps: rem2ps_o
# $(CC) $(CFLAGS) rem2ps_c
$(LD) $(LDFLAGS) -orem2ps rem2ps_o
remind: $(OBJS)
# $(CC) $(CFLAGS) $(SRCS)
$(LD) $(LDFLAGS) -oremind $(OBJS) $(MATHLIB)
rem2ps_o: rem2ps_c rem2ps_h lang_h config_h
calendar_o: calendar_c $(STDHDRS) expr_h
dorem_o: dorem_c $(STDHDRS) expr_h
dosubst_o: dosubst_c $(STDHDRS) $(LANGHDRS)
expr_o: expr_c $(STDHDRS) expr_h
files_o: files_c $(STDHDRS)
funcs_o: funcs_c $(STDHDRS) expr_h version_h
globals_o: globals_c config_h types_h globals_h err_h lang_h $(LANGHDRS)
hbcal_o: hbcal_c $(STDHDRS)
init_o: init_c $(STDHDRS) expr_h version_h lang_h $(LANGHDRS)
main_o: main_c $(STDHDRS) expr_h
moon_o: moon_c $(STDHDRS)
omit_o: omit_c $(STDHDRS)
sort_o: sort_c $(STDHDRS)
queue_o: queue_c $(STDHDRS)
token_o: token_c $(STDHDRS)
trigger_o: trigger_c $(STDHDRS) expr_h
userfns_o: userfns_c $(STDHDRS) expr_h
utils_o: utils_c $(STDHDRS)
var_o: var_c $(STDHDRS) expr_h
clean:
rm -f *_o *_bak
clobber:
rm -f *_o remind rem2ps test_out *_bak

38
README Normal file
View File

@@ -0,0 +1,38 @@
REMIND
Remind is a full-featured calendar/alarm program. Copying policy is
in the file "COPYRIGHT" in this directory.
Installation notes for various operating systems are in "docs". See
the appropriate README file for installation on your system.
Manual pages are in "man".
-----------------------------------------------------------------------------
Quick UNIX installation instructions for the very impatient:
If you have Tcl/Tk (wish 4.1 or higher) installed and are running X Windows:
--------------------------------------------------------------
1) Type: wish ./build.tk from this directory. Fill in the various
options and hit "Build Remind"
2) Type: "make install" -- you may need to be root to do this.
If you do NOT have Tcl/Tk or are NOT running X Windows:
-------------------------------------------------------
1) Edit the file "src/custom.h" according to your preferences.
2) Edit the file "src/lang.h" to choose a language.
3) Type: "./configure" (You can supply options; type "./configure --help"
for details.)
4) Type: "make"
5) Type: "make install" -- you may need to be root to do this.
Contact info: mailto:dianne@skoll.ca
Home page: https://dianne.skoll.ca/projects/remind/

View File

@@ -1,57 +0,0 @@
$Id: README.AMIGA,v 1.1 1996-03-31 04:01:52 dfs Exp $
REMIND version 3.0 for AmigaDOS
REMIND is a sophisticated alarm/calendar program. Details are given
in the man page, "remind.1".
1 - Read the file COPYRIGHT.
2 - Examine the file config.h and adjust parameters as needed
3 - If you are using SAS/C to compile Remind, type:
copy amiga-SCOPTIONS SCOPTIONS
smake -f smakefile
This will create remind, which is ready to be executed.
The file "defs.rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french.h" for an example.
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english.h" and "german.h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx.h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- You should define L_LANGNAME to be the full English name of your language,
with the first letter capitalized and the rest lower-case.
[Please note: I CANNOT SUPPORT THE AMIGA VERSION!]
--
David F. Skoll <dfs@doe.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Tel. (613) 225-8687

View File

@@ -1,65 +0,0 @@
$Id: README.BCC,v 1.1 1996-03-27 03:25:48 dfs Exp $
REMIND version 3.0 for Borland C++
1 - Read the file COPYRIGHT. (This may be called COPYRIGH on your
MS-DOS system.)
2 - You must use the Borland C++ OS/2 or MSDOS/Windows compiler.
3 - Examine the file config.h and adjust parameters as needed
4 - Examine the file makefile.bcc and adjust parameters as needed.
5 - Type:
make -f makefile.bcc
This will make 'remind.exe' and 'rem2ps.exe' in the ..\os2-ex or ..\msdos-ex
directories.
The file "defs.rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays.
NOTE that I do not have access to an OS/2 system, so support for this
system may not be as good as I'd like.
OS/2 support is courtesy of Russ Herman <rwh@gov.on.ca>, Norman Walsh
<norm@ora.com>, and Darrel Hankerson <hankedr@mail.auburn.edu>.
However, if you have problems, please contact me.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french.h" for an
example of the latter.
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english.h" and "german.h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx.h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- You should define L_LANGNAME to be the full English name of your language,
with the first letter capitalized and the rest lower-case.
--
David F. Skoll <dfs@doe.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Tel. (613) 225-8687

View File

@@ -1,62 +0,0 @@
$Id: README.DOS,v 1.2 1996-10-12 02:59:06 dfs Exp $
REMIND version 3.0 for MS-DOS
IMPORTANT NOTE: I'm no longer officially supporting Remind under
DOS. It may very well work, but if it doesn't... you're on your own.
REMIND is a sophisticated alarm/calendar program. Details are given
in the man page, "remind.1".
1 - Read the file COPYRIGHT. (This may be called COPYRIGH on your
MS-DOS system.)
2 - Examine the file config.h and adjust parameters as needed
3 - If you are using Turbo C to compile Remind, type:
make -fmakefile.tc
If you are using Microsoft C to compile Remind, type:
make makefile.msc
This will create REMIND.EXE, which is ready to be executed.
The file "defs.rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french.h" for an example.
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english.h" and "german.h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx.h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- You should define L_LANGNAME to be the full English name of your language,
with the first letter capitalized and the rest lower-case.
--
David F. Skoll <dfs@doe.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Tel. (613) 225-8687

View File

@@ -1,137 +0,0 @@
$Id: README.OS2,v 1.1 1996-03-27 03:25:49 dfs Exp $
REMIND version 3.0 for OS/2
This file contains instructions for compiling Remind under OS/2 with
Eberhard Mattes' emx/gcc compiler and with the Microsoft C compiler.
There are a number of targets in Makefile.os2, including OS/2-only
versions and bound versions (programs which run under OS/2 and DOS).
Note that there is also support for OS/2 using the Borland C
compiler--see the file README.BCC for details.
REMIND is a sophisticated alarm/calendar program. Details are given
in the man page, "remind.1".
1 - Read the file COPYRIGHT. (This may be called COPYRIGH on your
MS-DOS system.)
2 - To compile Remind for OS/2, you must use the Microsoft C compiler
or emx/gcc. You must also have a decent version of 'make', such
as dmake or GNU make.
3 - Examine the file config.h and adjust parameters as needed
4 - Examine the file Makefile.os2 and adjust parameters as needed.
5 - Type:
make -f Makefile.os2
to see a list of targets. For example,
make -f Makefile.os2 emx
will build a 32-bit emx version which runs under OS/2 2.x and DOS.
The file "defs.rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays.
NOTE that I do not have access to an OS/2 system, so support for this
system may not be as good as I'd like.
OS/2 support is courtesy of Russ Herman <rwh@gov.on.ca>, Norman Walsh
<norm@ora.com>, and Darrel Hankerson <hankedr@mail.auburn.edu>.
However, if you have problems, please contact me.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french.h" for an
example of the latter.
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english.h" and "german.h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx.h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- You should define L_LANGNAME to be the full English name of your language,
with the first letter capitalized and the rest lower-case.
RELEASE NOTES -- miscellaneous info that couldn't go anywhere else!
1. POPUP REMINDERS
If you define the symbol OS2_POPUP in the OS/2 Makefile, you get
"full-screen popups" (as implemented by Russ Herman) for all MSG-
and MSF-type reminders. You may or may not like this feature.
One way of implementing popup reminders is to get the program
"pmpopup.exe" from ftp-os2.cdrom.com, and using Remind with the
'-k' option as follows from C:\STARTUP.CMD:
start /pm /inv /n remind "-kstart pmpopup %%s" remfile
Alternatively, if you have the Vrexx package, you can use this
procedure suggested by Norman Walsh:
Start remind like this in C:\STARTUP.CMD:
start /pm /inv /n \bin\remind -faz "-kstart popupmsg %%s" .reminders
The popups are done by POPUPMSG.CMD which looks like this:
-------------- Cut Here ---------- Cut Here ---------- Cut Here --------
/* PopUpMsg */
'@echo off'
parse arg theargs
if theargs = "" then
theargs = "Empty message"
call RxFuncAdd 'VInit', 'VREXX', 'VINIT'
initcode = VInit()
if initcode = 'ERROR' then signal CLEANUP
signal on failure name CLEANUP
signal on halt name CLEANUP
signal on syntax name CLEANUP
/* example VMsgBox call */
msg.0 = 1
msg.1 = theargs
call VDialogPos 50, 50
call VMsgBox 'Popup Message', msg, 1
/* end of CMD file */
CLEANUP:
call VExit
exit
-------------- Cut Here ---------- Cut Here ---------- Cut Here --------
--
David F. Skoll <dfs@doe.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Tel. (613) 225-8687

View File

@@ -1,147 +0,0 @@
$Id: README.UNIX,v 1.2 1996-10-12 02:59:06 dfs Exp $
REMIND version 3.0 for UNIX
REMIND is a sophisticated alarm/calendar program. Details are given
in the man page, "remind.1".
1 - Read the file COPYRIGHT.
2- Before compiling the software, check to see if it includes patches.
These are files called patch.xx. If there are patches, apply them all
by typing:
cat patch.* | patch
3 - Examine the Makefile and change any parameters which need to be
changed for your system. As it stands, the Makefile is set up for a
Linux system.
4 - Examine the file config.h and adjust parameters as needed
5 - Examine lang.h and choose the language you want Remind to use.
(You can do this on the "make" command-line -- see "OTHER
LANGUAE SUPPORT.)
6 - Type 'make'
7 - Type 'sh test-rem' or 'make test' to run the acceptance test. Note
that the test script works only for the English version of Remind.
8 - Type 'make install' to install Remind, kall, rem and the man
pages.
Two shell scripts, "remind-all.csh" and "remind-all.sh" are provided.
These allow automatic mailing of reminders to all users who create a
$HOME/.reminders file. These two scripts are equivalent; one is a
"sh" script and the other is a "csh" script. Pick the one you want to
use, and follow the instructions in the opening comments of the
script.
*** NOTE *** Please be aware that "remind-all.csh" and "remind-all.sh"
have been changed since version 03.00.05 of Remind. If you install
the new remind executable, make sure you switch over to the new
"remind-all" scripts.
A shell script called "rem" is provided for those who like to have
'remind' assume a default reminders file. A man page for this script
is provided. You should examine the script to ensure that the defaults
are correct.
Many people have asked me why I supply the "rem" script instead of
having Remind assume a default file. The answer is: That's how I like
it! My personal preference is for a program which normally takes
parameters to display usage information when invoked with no
parameters. I like that behaviour so I can quickly get an idea of
what a program does without poring through the man page. And I think
I'll keep Remind that way. Sorry to all who dislike it. :-)
A shell script called "kall" is provided so you can kill your background
remind processes when you log out. See the man page. Note that kall
depends on the output of "ps", and may not be portable.
The file "defs.rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french.h" for an
example of the latter.
To compile Remind for a non-english language, look at the constants
defined in "lang.h". Then, to compile Remind for Italian (as an
example), type:
make "CDEFS=-DLANG=ITALIAN"
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english.h" and "german.h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx.h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- Your language file should define L_LANGNAME to be the full English
name of your language, with the first letter capitalized and the rest
lower-case.
RELEASE NOTES -- miscellaneous info that couldn't go anywhere else!
1. POPUP REMINDERS
If you're running under X-Windows and you have the TCL tools,
you can create simple pop-up reminders by creating the following
TCL script called 'popup'. It pops a message on to the screen and
waits for you to press the 'OK' button. If you don't press the OK button
within 15 seconds, it exits anyway. To use it, you can use the '-k' option
for Remind as follows:
remind "-kpopup '%s'&" .reminders
Or use the following in your Remind script:
REM AT 17:00 RUN popup 'Time to go home.' &
This TCL script is a slightly modified version of one submitted by
Norman Walsh. TCL is available via FTP at ftp.uu.net in /languages/tcl.
-------------- Cut Here ---------- Cut Here ---------- Cut Here -------------
#!/usr/local/bin/wish -f
wm withdraw .
if { [ llength $argv ] == 1 } {
eval set msg $argv
} else {
eval set msg [ list $argv ]
}
after 15000 { destroy . ; exit }
tk_dialog .d { Message } $msg warning 0 { OK }
destroy .
exit
-------------- Cut Here ---------- Cut Here ---------- Cut Here -------------
--
David F. Skoll <dfs@doe.carleton.ca>
986 Eiffel Avenue
Ottawa, Ontario K2C 0J2
CANADA
Tel. (613) 225-8687

View File

@@ -1,95 +0,0 @@
$Id: README_QDOS,v 1.3 1996-09-28 18:17:07 dfs Exp $
REMIND version 3.0.15 for QDOS / SMSQ
REMIND is a sophisticated alarm/calendar program. Details are given
in the documentation file, "remind_doc" (QUILL format).
[Note from David Skoll -- I was not sent the file `remind_doc', so
you're on your own here. You'll have to use the UNIX man pages.]
1 - Read the file COPYRIGHT.
2 - Do NOT redistribute Remind WITHOUT the sources!
3 - Examine the Makefile and change any parameters which need to be
changed for your system. (The makefile for QDOS / SMSQ is
makefile_QDOS).
4 - Examine the file config_h and adjust parameters as needed
5 - Examine lang_h and choose the language you want Remind to use.
There has no effort been put in making the language modules working
on the QL. You'll have to adjust the files for yourself to get
them working (umlauts etc).
6 - Execute "make;'-fMakefile_QDOS'". Be sure, that your DATA_DEFAULT
directory is the directory where the remind source files are
placed.
7 - There is an acceptance test for other systems. If you want to
test remind on your QDOS / SMSQ system execute the following
commands from your command line:
SETENV "TEST_GETENV=foo bar baz"
ex datad$&'remind';'-e -dxte test_rem 16 feb 1991 > test_out'
ex diff;'test_out test_cmp >test_diff'
Then check the output of diff. You will find lots of differences.
If there are other than differences in the filename
(supplied test-result: ./test.rem, QDOS result: test_rem) and
in the ostype (supplied: UNIX, QDOS: QDOS / SMSQ) Remind does
not work correctly.
The file "defs_rem" has some sample Remind definitions and commands,
as well as U.S. and Jewish holidays. You should delete the definitions
for ANSI colours as the QL does not support the ANSI standard.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"lang_h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "french_h" for an
example of the latter.
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "english_h" and "german_h" if you want to add
support for your favourite language. If you do add another language
to Remind, please let me know! Here are the basic guidelines:
- Your language file should be called "lxxx_h", where lxxx is the first 8
characters of the ENGLISH name of your language.
- Your language file should define L_LANGNAME to be the full English
name of your language, with the first letter capitalized and the rest
lower-case.
RELEASE NOTES -- miscellaneous info that couldn't go anywhere else!
The QDOS / SMSQ version does not support the enhanced features of
the UNIX and/or OS/2 versions.
I had some problems with the sunrise() and sunset() functions,
but didn't examine it.
I've ported Remind on a SMSQ/SGC system. It should work on other
systems without problems. The compiler used was C68 v4.14c.
Remind should work with each QL or compatible with 512K or more RAM.
It'll however NOT work on a standard QL due to it's code size.
Any problems with the QDOS / SMSQ versions should be sent to:
Robert H. Klein
Bluecherstrasse 24
D-56349 Kaub
Germany

View File

@@ -1,702 +0,0 @@
CHANGES TO REMIND
* Version 3.0 Patch 15
+ IMPORTANT NOTES
- The tar file now unpacks into a Remind subdirectory rather than into
the current working directory.
- I no longer support Remind under DOS. I don't think I've done anything
to stop it from working under DOS, but will no longer compile and test
it under DOS, and can't help you if you get stuck. Sorry -- I no longer
have a DOS machine.
+ MINOR ENHANCEMENTS
- Changed psshade() to accept 1 or 3 arguments for colored shading in
PostScript calendar mode.
- Added a Print dialog to tkremind.
- Added support for Brazilian Portuguese courtesy of Marco Paganini
- Added support for Italian courtesy of Valerio Aimale
+ BUG FIXES
- Fixed confusing error in rem2ps help messages.
- Fixed bug in TkRemind which caused a crash if the "-m" option was used
for a month beginning on Sunday. Doh!!!
* Version 3.0 Patch 14
+ CHANGE IN COPYING POLICY
- Remind is now distributed under an _AMENDED_ version of the Gnu
General Public License. These amendments are listed in the
file COPYRIGHT. The amendments were made for personal reasons;
please don't ask me to explain them. They probably don't affect
you, anyway.
+ MAJOR ENHANCEMENTS
- Added an X-Windows front-end to Remind. To use it, you must be
running under X-Windows on UNIX, and have the "wish" tcl/tk
interpreter, version 7.4 of tcl and 4.0 of tk. The front-end is
called "tkremind".
+ MINOR ENHANCEMENTS
- Added the WARN keyword for precise advance notice. You can now
have advance warning 5, 3, 1 and 0 days in advance (for example.)
The WARN keyword operates similarly to the SCHED keyword in that it
calls a user-defined function to obtain the advance warning sequence.
- Added support for QDOS/SMSQ on the Sinclair QL microcomputer,
courtesy of Robert H. Klein <kleir000@goofy.zdv.Uni-Mainz.de>
NOTE THAT I CANNOT TEST NOR SUPPORT THIS VERSION!
- Added support for AmigaDOS / SAS/C, courtesy of Martin Hohl
<martinh@caverna.tynet.sub.org>. As before, I CANNOT TEST NOR
SUPPORT THIS VERSION, but will rely on feedback from others.
+ BUG FIXES
- Removed the "-n" option from Rem2PS. Instead, if you want the
PostScript calendar to start on a Monday, supply the "-m" option
to Remind. It was repugnant to have two options to two programs
to accomplish one thing.
- The "hebdate" built-in function worked incorrectly with 5 arguments.
The bug was pointed out by Hershel Safer <h.safer@ieee.org>
- This would hang up REMIND: REM Mon 31 Feb MSG Foo
and this would fail quietly: REM Mon 31 Feb 1996 MSG Foo
Both have been fixed and now report bad date specifications.
- Remind now compiles without complaint under gcc -ansi -Wall -pedantic
(on my Linux system, anyway!)
+ IMPORTANT NOTE
- I had problems building the DOS version with Turbo C. I have access
only to ancient versions of Turbo C and Microsoft C. Remind built
fine with Microsoft C, but the TC version hung up. I am not too
interested in maintaining the DOS version, so when the MSC compiler
no longer works, I will drop DOS support. Please not that I will
_not_ support MS Windows, and in fact do not allow Remind to run
under Windows (see COPYRIGHT).
* Version 3.0 Patch 13
+ MINOR ENHANCEMENTS
- Added extra parameters to the "psmoon" built-in function so you
can annotate the PostScript moon icons.
- Added a command-line "time" argument to Remind for testing Remind
scripts with specific system times. Also added the realnow() function
which has the same relationship to now() as realtoday() has to today().
(See the man page!)
- Modified Rem2PS so it prints progress messages to stderr if
'-v' command-line argument is used.
- In the top of the 'finnish.h' file, added a note about
Mikko Silvonen's file of Finnish holidays.
+ BUG FIXES
- Fixed a bug in rem2ps which sometimes caused incorrect PostScript if
the -e and -m options were used. Thanks to Michael Neuhauser for
reporting the bug and providing a fix.
- Made the '-k' option escape shell characters in the message to make it
safer.
- Fixed a segmentation violation which resulted if not all
PUSH-OMIT-CONTEXTs were balanced by POP-OMIT-CONTEXTs.
- Removed the prototype for DestroyValue, which is now a macro. I'm
amazed that very few compilers complained about this one!
- Updated the copyright notices everywhere.
* Version 3.0 Patch 12
+ MINOR ENHANCEMENTS
- Added support for the Danish language, courtesy of Mogens Lynnerup.
- Added support for the Polish language, courtesy of Jerzy Sobczyk.
- Made the Makefile more portable, thanks to Jim Budler.
- Removed some compiler warnings under Linux, thanks to Francois Pinard.
- Tidied the man page a bit; added a small bibliography.
+ BUG FIXES
- Fixed a problem with the '-k' option which resulted in a newline being
placed after the message text. This was giving sh(1) heartburn...
* Version 3.0 Patch 11
+ MINOR ENHANCEMENTS
- Added release notes to README.UNIX and README.OS2 describing one
way to make pop-up alarms under X-Windows and Presentation Manager.
- Added the $DefaultPrio system variable
- Improved OS/2 support, thanks to Darrel Hankerson, Russ Herman
and Norman Walsh.
- Made the pushing and popping of operators and operands during
expression evaluation in-line code instead of function calls. Did the
same for DestroyValue. I'm not sure if this was a good idea -- on the
Sparc using gcc, this slowed things down... go figure.
+ BUG FIXES
- Fixed a potential memory leak in the char() function.
- Made the TRIGGER() built-in function return its answer in English even
for the foreign-language versions -- this was required for compilers which
are not 8-bit clean, and for languages with accented letters.
- Made expression evaluation slightly faster by eliminating some unnecessary
copying of string values.
- Corrected some non-portable definitions of the macro UPPER(c)
- Fixed typos in french.h
* Version 3.0 Patch 10
+ MAJOR ENHANCEMENT
- OS/2 support is now much better, thanks to Russ Herman. The Borland
C compiler under OS/2 and MS-DOS is supported.
+ MINOR ENHANCEMENTS
- Added the SCHED keyword for precise control of scheduling of timed
reminders -- it's really quite nifty!
- Modified the trigger() function to take up to three arguments -- in
addition to a date, you can specify a time and a flag specifying that
the trigger should be converted from UTC to local time.
- Added $SortByDate, $SortByTime and $SortByPrio system variables.
- Added test suites for MS-DOS and OS/2, courtesy of Russ Herman.
- In PostScript output, the month and year are output in the %%Page: comments.
Makes it nicer to view multi-month calendars with previewers (eg,
GhostView.)
- Added the PRIORITY keyword for more control of sort order of reminders.
Based on a suggestion by George M. Sipe.
- Added the msgprefix() and msgsuffix() evaluations around MSG-type
reminders for doing fancy things with reminders of different priorities.
Also added calprefix() and calsuffix() for doing the same thing in
calendar mode.
- Enabled the -g option during calendar mode as well as regular mode.
+ BUG FIXES
- Fixed minor bugs in the LocalToUTC and UTCToLocal functions.
- "remind -c -de file" used to cause a segmentation violation. Whoops...
- Some files which should have included <string.h> didn't include it - these
are now fixed.
- Fixed the moondate() and moontime() functions, which used to be incorrect
after November 1994.
- Fixed the Finnish language support which was missing a few newlines.
* Version 3.0 Patch 9
+ NOTES
- Remind is now too big to compile under the "small" model in
MS-DOS. You must recompile everything under the "medium" model.
+ MAJOR ENHANCEMENTS
- Functions moonphase(), moondate() and moontime() were added for dealing
with phases of the moon. The code was snarfed from "moontool" by
John Walker - see the file "moon.c" for detailed acknowledgement. Also
added psmoon() for putting little moon symbols on the PostScript calendar.
+ MINOR ENHANCEMENTS
- Added some more examples to defs.rem - notably, support for ANSI
terminal color-changing escape sequences, thanks to Gail Gurman.
- Modified both Remind and Rem2PS so that calendars can start on Sunday or
Monday, depending on your preference. Unfortunately, the command-line
options are different -- for Remind, it's '-m' and for Rem2PS it's '-n'
because '-m' was already in use. Based on a suggestion by John Plate
and a patch sent by Mikko Silvonen.
- The Finnish language support is better - now, all usage and error
messages are in Finnish. In addition, the Finnish language module
supports the IBM extended character set as well as ISOLATIN1.
Thanks to Mikko Silvonen.
- Modified Rem2PS to allow more control over the placement of the small
calendars, thanks to a suggestion by Frank Vance. Also added option
to control the calendar title (e.g., "September 1993") independently
of day-of-week headings.
- Added the psshade() function to make it easier to shade PostScript
calendars.
- Allowed a repeat parameter '*num' to be supplied on command line so
a 'preview' of many days' worth of reminders can be obtained easily.
- Added the $Location system variable.
- Allowed an expression to be supplied to EXIT to return an exit
status.
- Added the FLUSH command.
+ BUG FIXES
- Fixed the MSF-type reminder to fill paragraphs more intelligently.
It puts double spaces after '!', '.' and '?', and can handle quotes,
brackets, etc. after periods, etc. These characters can be specified
with the $EndSent and $EndSentIg system variables. Also modified it
so that newlines in the body start new paragraphs, rather than being
swallowed as white-space.
* Version 3.0 Patch 8
+ MAJOR ENHANCEMENTS
- Changed the code to more fully support foreign languages - error
messages and usage instructions can now be changed. All changes can
be localized in the appropriate language.h files.
- Added support for the French language, courtesy of Laurent Duperval.
Note that the French support is more complete than for other languages -
French usage instructions and error messages are supported.
- Added support for the Norwegian language, courtesy of Trygve Randen.
+ MINOR ENHANCEMENTS
- Added code for the functions timelocal() and timegm(), courtesy of
Lucio de Re. This is for those very few machines whose libraries
include neither those functions nor mktime().
- Added the filedate() function.
- Allowed the filename to be specified as "-" to cause Remind to take
its input from the standard input stream.
- Added the "MSF" keyword to cause reminders to be formatted automatically.
This keyword paragraph-fills reminder text following user specifications.
Based on a suggestion by Ken McGlothlen.
- Added the "-e" option to Rem2PS, allowing the PostScript calendar
to fill the entire page. Thanks to Arthur G. Yaffe.
+ BUG FIXES
- Corrected the Hebrew holidays Tzom Gedalia, Tzom Tevet, Ta'anit
Esther, Tzom Tamuz and Tisha B'Av so they won't occur on Saturday.
Corrections made following the algorithm in "Calendrical Calculations"
by Nachum Dershowitz and Edward M. Reingold.
- Changed the dutch.h language file as suggested by Erik-Jan Vens. Made
month and day names lower-case; corrected the spelling of oktober.
- Changed HashVal in var.c to use unsigned arithmetic - it's conceivable
that a machine with signed chars could cause problems otherwise.
- Changed the LONG_* macros in config.h to LON_* to avoid conflicts
with names defined by ANSI C. Thanks to David W. Sanderson.
- Allowed the built-in function char() to accept numbers in the
range [-128, 255] (but not 0) so that char(asc(s)) works even
on machines with signed char types.
* Version 3.0 Patch 7
+ MAJOR ENHANCEMENTS
- Added "system variables" to allow the user more control over
Remind operation, and to allow queries about the command-line
options from within a reminder script. They allow for specification
of longitude and latitude for use by sunrise/sunset calculations.
- Added sunrise(), sunset(), isdst() and minsfromutc() functions -
these are needed to support sunrise and sunset calculations.
+ MINOR ENHANCEMENTS
- Allowed the MSG, RUN, CAL, PS and PSF keywords to be used in the
same reminder as the SATISFY keyword. This makes many complex
reminders more compact.
- Added the filedir() function to enable Remind's include to emulate
CPP's #include more closely.
- Allowed non-root users to use the "-u" option. It only affects
the "SHELL", "HOME", "USER" and "LOGNAME" environment variables -
it doesn't change the effective uid and gid when run by non-root.
- Added built-in function "easterdate" to calculate date of Easter
Sunday - function courtesy of Michael Salmon.
- Improved the Jewish holiday reminders in "defs.rem" to give advance
notice of holidays.
- Allowed the "simple calendar" option (-s) to specify a number of
weeks as well as a number of months, in the same fashion as the
-c option. Thanks to Dave Rickel.
+ BUG FIXES
- Corrected the behaviour of "hebdate" for jahrzeits; added an additional
parameter to specify the behaviour of dates in Adar during leap years.
- Changed kall so that "kall sh" doesn't commit suicide - patch courtesy
of Michael Salmon.
* Version 3.0 Patch 6
+ MINOR ENHANCEMENTS
- Added the PS- and PSFILE-type reminders - these allow you to include
arbitrary PostScript code in your PostScript calendars. Useful for
shading, drawing graphics on calendars, etc. Use with care, though!
- Added the "-ivar=val" option to initialize variables from the command
line. Changed the remind-all.* shell scripts to predefine the variable
"remind_all".
+ BUG FIXES
- Fixed a bug in the hebmon(), hebday() and hebyear() functions - there
was an off-by-one error. Sorry!
- Fixed a bug in the hebdate() function which resulted in infinite loops
for dates after about 2075
- Fixed a bug in the -u option which sometimes caused a core dump
(embarrassed grin!) The fix is due to Tina Hoeltig. Thanks, Tina!
* Version 3.0 Patch 5
+ MAJOR ENHANCEMENTS:
- Added support for the Hebrew calendar - can now specify Jewish holidays
easily. Thanks to Amos Shapir for explaining the Hebrew calendar, and
to Danny Sadinoff, from whose HEBCAL program I got some inspiration.
Also thanks to David W. Tamkin and Frank Yellin for explaining the rules
for jahrzeits.
+ MINOR ENHANCEMENTS:
- Allowed the default page size used by Rem2PS to be selected in config.h
- Edited the defs.rem file to contain Jewish holidays. Cleaned up some
of the examples and improved the layout - thanks to George M. Sipe.
- Modified the IIF function to be more general
- Updated finnish.h to support the ISO 8859-1 character set, courtesy
of Mikko Silvonen.
- Changed the date conversion routines to greatly speed up conversion from
Julian to yyyy/mm/dd form.
+ BUG FIXES:
- Fixed a bug in which Remind complained incorrectly about a missing quote
in the command SET foo ""
- Fixed bugs in dosubst.c which caused the %o, %1 and %@ substitutions
to be incorrect
- Fixed a bug in the man page - thanks to Ed Oskiewicz.
* Version 3.0 Patch 4
- Added the -g option - this sorts reminders by date/time before
issuing them. (You can see I'm running out of letters to
name options!) This feature was suggested by George M. Sipe,
Paul D. Smith, and Francois Pinard.
- Added the "args()" and "dosubst()" built-in functions - see the
man page for details.
- Added more support for the ISO 8859-1 character set, and
modified the german.h file to take advantage of this, thanks
to Robert Joop.
- Allowed any character to be used as date and time separator
characters (not just "/-:.")
- Added support for the Dutch and Finnish languages, thanks to
Willem Kasdorp and Mikko Silvonen. (Anyone care to contribute
French? Italian? Spanish?)
- Made Remind issue a warning if you try to redefine a built-in
function. This warning is disabled in 'Hush' mode.
- Added the SCANFROM clause to the REM command. This allows reasonably
safe moveable OMITs such as the Labour Day example in the manual.
- Added more examples to the defs.rem file, and cleaned up some old
examples. Note that there are now safe moveable holidays for most
U.S. holidays provided in the defs.rem file.
- Added the '-k' option, which allows MSG-type reminders to be passed
to any system command. (Idea and patch courtesy of Philipp Slusallek.)
- Allowed selection of ':' or '.' as time separator characters at
compile-time.
- Edited the COPYRIGHT file to clarify the rules. Please read them.
- Removed hard-coding of "am" and "pm" and placed them in language-specific
header files as #defines L_AM and L_PM
- Fixed a bug in the FindToken() routine which had, through sheer luck,
never been activated until the SCANFROM clause was added!
- Fixed the UNTIL clause to check for a valid expiry date.
- Removed identifiers in the C source beginning with "_" to conform
to ANSI practice.
- Fixed a bug in the -u option which resulted in environment variables
SHELL and USER not being set correctly. Also made -u set the LOGNAME
environment variable.
- Fixed a couple of typos in the man page; added LDFLAGS to the
Makefile. (Thanks to Dave Wolfe.)
- Put my new mailing address in the README files.
* Version 3.0 Patch 3
- Corrected bugs in Remind and Rem2PS. No new features added. You
should NOT use patch level 2 - either stick to 3.0.1 or upgrade to
3.0.3.
* Version 3.0 Patch 2
- Added the -u option to Remind so that root can run it as any user.
This simplifies the remind-all scripts, and makes them more efficient.
If you are worried that this option is a security hole, you can
disable it in config.h
- Changed the RUN command so that RUN OFF can be used anywhere, even
though RUN ON only works in the top-level file. This eases the
management of global files which may want to switch RUN OFF.
- Added ISO encoding (ISO 8859-1) to the PostScript output, courtesy of
Michael Salmon. This can be selected with the '-i' option in rem2ps.
- Added support for the '-' date separator as well as the '/' separator.
- Added support for languages other than English. Note that this support
is not complete - error messages are still in English. The idea and
German translation came from Wolfgang Thronicke.
- Changed the -w option to include the "padding" and "spacing" options.
NOTE INCOMPATIBILITY: In the previous patch level, creating a weekly
calendar using the -c+n option left no blank lines between the day
number and the first reminder entry. This has been changed so that one
blank line is left. To revert to the old behaviour, use the "-w,,0"
option.
- Added the -o option to Rem2ps. This allows you to specify the margins
when producing a PostScript calendar.
- Updated the copyright notices in all the files. :-)
- Added 'make clobber' and 'make test' targets to the Unix makefile.
- Corrected typos in WHATSNEW.30 and remind.1 man page. Thanks to
Dave Wolfe <dwolfe@pffft.sps.mot.com>
- Changed Remind so that supplying the -a option causes timed reminders
not to be placed into the calendar in calendar mode.
* Version 3.0 Patch 1
- Wrote the Rem2ps program to produce PostScript calendars
- Added an 'install' target to the Makefile
- Fixed a bug which allowed the shell() function to execute in timed
reminders which were queued with RUN disabled.
- Added support for OS/2, courtesy of DARREL HANKERSON
<HANK@DUCVAX.AUBURN.EDU>
- In expressions, can now specify literal dates as 'yyyy/mm/dd' rather than
using the date() function.
- Fixed all the source files to include "config.h" first.
- Changed the way triggers are calculated so that trigger dates are
always valid if year, month and day are specified, and there is no
UNTIL clause. See MAN page section "DETAILS ABOUT TRIGVALID()."
- Defined _POSIX_SOURCE so Remind will compile on SGI workstations (and
be more portable... I hope.)
- Fixed some rather brain-dead definitions of UPPER and LOWER, as pointed
out by <rsalz@osf.org>
- Added more details to the Man page concerning how triggers are computed,
and added warnings about computing OMIT dates.
- Added the file defs.rem which contains examples of useful definitions and
triggers.
- Changed the script test-rem to be a sh script instead of csh for improved
portability.
- Fixed up the README.* files to reflect the changes.
- Re-formatted the WHATSNEW.30 file.
* Version 3.0
- Total rewrite from previous versions
- Added variables, expressions, flow-control statements, daemon mode
- Added "expression pasting"
- Added CAL-type reminders
- Added the SATISFY clause
- Improved debugging of reminder scripts
- Took out the "purge" option - it is in general too dificult to tell when
a reminder has expired for good, so now it's up to you to do this
by hand.
- Fixed a lurking bug in trigger date calculation which, amazingly, had not
been caught in the couple of years that Remind has been out!
* Version 2.3 Patch 5
- Added the "c+n" option for printing a calendar by
weeks instead of months, courtesy Dennis Cottel (dennis@peanuts.nosc.mil).
* Version 2.3 Patch 4
- Made the init.c file nicer. Made the Makefile
prettier. Added "make test", "make tar" and "make shar" Makefile targets.
* Version 2.3 Patch 3
- Added a command-line option for Remind to process
queued reminders in the foreground. This makes automatic termination
of Remind processes from within X-Windows and Sunview easier.
* Version 2.3 Patch 2
- Fixed up a problem with timed reminders which resulted
in cursor not starting from left side of screen on some systems.
- Fixed the SIGINT handler for SYSV systems - this was interrupting the
sleep(2) system call.
- Closed stdin and stdout if remind was part of a pipe - this prevents other
sections of the pipe from hanging as remind puts itself in the background.
- Added the "-h" (Hush mode) option
- Added the "%#" and "%@" modifiers for the current time.
- Made the Makefile more portable
* Version 2.3 Patch 1
- Added the "-t" command-line option to get Remind
to trigger all non-expired reminders.
- Added Turbo C support courtesy of Rhys Weatherly
- Added the "RUN ON" and "RUN OFF" commands for a secure interface with
the Elm mail system.
- Added the "rem" shell script for running Remind with a default script.
- Added manual pages for "kall" and "rem".
* Version 2.3
- Added the UNTIL keyword for forcing reminders to expire.
- Added the "++" form of 'back' and the "--" form of 'delta' for
ignoring OMIT information.
- Added the CLEAR-OMIT-CONTEXT, PUSH-OMIT-CONTEXT and POP-OMIT-CONTEXT
keywords for isolating personal or peculiar reminders from the global
OMIT context.
- Speeded up the parsing of tokens.
- Changed the source to recognize and exploit ANSI-C compilers which
accept function prototypes.
- Added the "-n" option to output the next occurrence of each reminder
in SimpleCalendar format
- Modified the calendar and SimpleCalendar formats so that the % escape
substitutions ARE performed.
* Version 2.2 - Patch 5
- Added the BEFORE, AFTER and SKIP tokens to make the
handling of holidays more sensible. Also corrected a few more bugs.
* Version 2.2 - Patch 3
- Added the MSG or RUN tokens in an OMIT command; also
allowed RUN-type reminders to be explicitly included in the calendar by
using the %" escape sequence.
* Version 2.2
- Added the AT keyword, the timed reminders daemon, and the
calendar facility.
* Version 2.1
- Added the "repeat" token for repeating reminders with a period
other than 7 days. Also fixed some bugs from version 2.0
* Version 2.0
- first public release. Included advanced date specifications,
character substitution, and the RUN keyword.
* Version 1.0
- never publicly released.

View File

@@ -1,7 +0,0 @@
IGNORE=154
IGNORE=161
IGNORE=100
IGNORE=85
LINKOPT SC
LINKOPT SD
LINKOPT NOICONS

63
amiga.c
View File

@@ -1,63 +0,0 @@
/***************************************************************/
/* */
/* AMIGA.C */
/* */
/* Support functions for AmigaDOS */
/* */
/* This file is Copyright (C) 1995 by Martin Hohl */
/* */
/* This file is part of REMIND. */
/* Remind is Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: amiga.c,v 1.1 1996-03-31 04:01:53 dfs Exp $";
#include <stdlib.h>
#include <string.h>
#include <exec/types.h>
#include <dos/dos.h>
#include <dos/dosextens.h>
#include <proto/dos.h>
#include "version.h" /* Hopefully this will define VERSION as a string */
#ifdef __SASC_60
/* AmigaDOS 2.04 compatible version string for "version" utility */
const static char ver_string[] = "$VER: remind "VERSION" "__AMIGADATE__;
#endif
void sleep(int dt)
{
register long Ticks;
if (dt != 0) {
Ticks = 50L * dt;
Delay(Ticks);
}
}
void execvp(char *name, char **argvec)
{
char *cmdline;
int i,l;
l = strlen(name)+2;
i=1;
while (argvec[i] != 0L) {
l += strlen(argvec[i])+1;
i++;
};
cmdline = malloc(l+1);
if (cmdline == 0L) return;
strcpy(cmdline,name);
i=1;
while (argvec[i] != 0L) {
strcat(cmdline," ");
strcat(cmdline,argvec[i]);
i++;
};
system(cmdline);
free(cmdline);
}

862
build.tk Normal file
View File

@@ -0,0 +1,862 @@
#!/bin/sh
# -*-Mode: TCL;-*-
#--------------------------------------------------------------
# BUILD.TK
#
# A cheesy graphical front-end for building and installing REMIND.
#
# This file is part of REMIND.
# Copyright (C) 1992-2018 Dianne Skoll
#
#--------------------------------------------------------------
# the next line restarts using wish \
exec wish "$0" "$@"
#***********************************************************************
# %PROCEDURE: SetConfigDefaults
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Sets up default values for various parameters.
#***********************************************************************
proc SetConfigDefaults {} {
global Config
set Config(LAT_DEG) 45
set Config(LAT_MIN) 24
set Config(LON_DEG) 75
set Config(LON_MIN) 39
set Config(LOCATION) "Ottawa"
set Config(DEFAULT_PAGE) "Letter"
set Config(DATESEP) "-"
set Config(TIMESEP) ":"
set Config(ISOLATIN1) 0
set Config(IBMEXTENDED) 0
set Config(ISOLATIN2) 0
set Config(IBM852) 0
set Config(NORTHERN_HEMISPHERE) 1
set Config(WESTERN_HEMISPHERE) 1
set Config(LANGUAGE) "English"
set Config(INST_DIR) "/usr/local/bin"
set Config(MAN_DIR) "/usr/local/man"
}
#***********************************************************************
# %PROCEDURE: Bail
# %ARGUMENTS:
# msg -- a message
# %RETURNS:
# Does not return
# %DESCRIPTION:
# Pops up an error dialog; then calls exit.
#***********************************************************************
proc Bail { msg } {
tk_dialog .err "Remind Configuration Error" $msg error 0 "Bummer"
exit 1
}
#***********************************************************************
# %PROCEDURE: CheckSanity
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Checks sanity of install dir -- checks for critical files,
# warns user if something looks wrong.
#***********************************************************************
proc CheckSanity {} {
if {![file executable ./configure]} {
wm withdraw .
Bail "I can't seem to execute the file ./configure -- make sure you have all required files and are running this from the top-level Remind directory"
}
if {![file readable ./src/custom.h.in]} {
wm withdraw .
Bail "I can't seem to find the file src/custom.h.in -- make sure you have all required files and are running this from the top-level Remind directory"
}
}
#***********************************************************************
# %PROCEDURE: CreateMainDialog
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Creates and displays the main configuration dialog
#***********************************************************************
proc CreateMainDialog {} {
global Instdir Loc Options
wm title . "Remind Configuration"
wm iconname . "Remind Config"
SetConfigFromRemind
tabnotebook_create .tn
set Instdir [tabnotebook_page .tn "Installation Directories"]
CreateInstallDirDialog $Instdir
set Loc [tabnotebook_page .tn "Location"]
CreateLocationDialog $Loc
set Options [tabnotebook_page .tn "Options"]
CreateOptionsDialog $Options
pack .tn -side top -expand 1 -fill both
frame .buttons
button .build -text "Build Remind" -command BuildRemind
button .cancel -text "Cancel" -command exit
pack .build .cancel -in .buttons -side left -expand 1 -fill both
pack .buttons -side top -expand 0 -fill x
}
#***********************************************************************
# %PROCEDURE: CreateInstallDirDialog
# %ARGUMENTS:
# w -- frame containing widgets
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Creates the "installation directories" dialog.
#***********************************************************************
proc CreateInstallDirDialog { w } {
global Config
label $w.binlabel -text "Location for programs: "
entry $w.bin -width 30
$w.bin insert end $Config(INST_DIR)
label $w.manlabel -text "Location for man pages: "
entry $w.man -width 30
$w.man insert end $Config(MAN_DIR)
text $w.blurb -width 1 -height 5 -wrap word -relief flat -takefocus 0
$w.blurb insert end "\n(Tabbed-notebook Tcl code taken from \"Effective Tcl/Tk Programming\" by Mark Harrison and Michael McLennan, Addison-Wesley Professional Computing Series.)"
$w.blurb configure -state disabled
# Disable all text-window behaviour
bindtags $w.blurb {NoSuchTag}
grid $w.binlabel -row 0 -column 0 -sticky e
grid $w.bin -row 0 -column 1 -sticky nsew
grid $w.manlabel -row 1 -column 0 -sticky e
grid $w.man -row 1 -column 1 -sticky nsew
grid $w.blurb - -sticky nsew
}
#***********************************************************************
# %PROCEDURE: CreateLocationDialog
# %ARGUMENTS:
# w -- frame containing dialog
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Creates the location dialog
#***********************************************************************
proc CreateLocationDialog { w } {
global Config
scale $w.latdeg -label "Latitude (degrees)" -orient horizontal \
-from 0 -to 89 -length 300 -variable Config(LAT_DEG)
scale $w.latmin -label "Latitude (minutes)" -orient horizontal \
-from 0 -to 59 -length 300 -variable Config(LAT_MIN)
scale $w.londeg -label "Longitude (degrees)" -orient horizontal \
-from 0 -to 179 -length 300 -variable Config(LON_DEG)
scale $w.lonmin -label "Longtude (minutes)" -orient horizontal \
-from 0 -to 59 -length 300 -variable Config(LON_MIN)
radiobutton $w.north -text "Northern Hemisphere" \
-variable Config(NORTHERN_HEMISPHERE) -value 1
radiobutton $w.south -text "Southern Hemisphere" \
-variable Config(NORTHERN_HEMISPHERE) -value 0
radiobutton $w.west -text "Western Hemisphere" \
-variable Config(WESTERN_HEMISPHERE) -value 1
radiobutton $w.east -text "Eastern Hemisphere" \
-variable Config(WESTERN_HEMISPHERE) -value 0
label $w.loclab -text "City or Town: "
entry $w.location -width 20
$w.location insert end $Config(LOCATION)
grid $w.latdeg -
grid $w.latmin -
grid $w.londeg -
grid $w.lonmin -
grid $w.north $w.west
grid $w.south $w.east
grid $w.loclab -sticky e
grid $w.location -sticky nsew -row 6 -column 1
}
#***********************************************************************
# %PROCEDURE: CreateOptionsDialog
# %ARGUMENTS:
# w -- frame containing dialog
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Creates the options dialog
#***********************************************************************
proc CreateOptionsDialog { w } {
global Config
label $w.pagelabel -text "Default page size: "
menubutton $w.page -text $Config(DEFAULT_PAGE) \
-indicatoron 1 -relief raised \
-menu $w.page.menu
menu $w.page.menu -tearoff 0
$w.page.menu add command -label "Letter" \
-command "$w.page configure -text Letter"
$w.page.menu add command -label "A4" -command "$w.page configure -text A4"
grid configure $w.pagelabel -row 0 -column 0 -sticky e
grid configure $w.page -row 0 -column 1 -sticky nsew
label $w.datelabel -text "Default date separator: "
menubutton $w.date -text $Config(DATESEP) -indicatoron 1 -relief raised \
-menu $w.date.menu
menu $w.date.menu -tearoff 0
$w.date.menu add command -label "/" -command "$w.date configure -text /"
$w.date.menu add command -label "-" -command "$w.date configure -text -"
grid configure $w.datelabel -row 1 -column 0 -sticky e
grid configure $w.date -row 1 -column 1 -sticky nsew
label $w.timelabel -text "Default time separator: "
menubutton $w.time -text $Config(TIMESEP) -indicatoron 1 -relief raised \
-menu $w.time.menu
menu $w.time.menu -tearoff 0
$w.time.menu add command -label ":" -command "$w.time configure -text :"
$w.time.menu add command -label "." -command "$w.time configure -text ."
grid configure $w.timelabel -row 2 -column 0 -sticky e
grid configure $w.time -row 2 -column 1 -sticky nsew
label $w.charlabel -text "Character set: "
menubutton $w.char -text "ISO 8859-1" -indicatoron 1 -relief raised \
-menu $w.char.menu
menu $w.char.menu -tearoff 0
$w.char.menu add command -label "ISO 8859-1" -command "$w.char configure -text {ISO 8859-1}"
$w.char.menu add command -label "ISO 8859-2" -command "$w.char configure -text {ISO 8859-2}"
$w.char.menu add command -label "IBM Extended" -command "$w.char configure -text {IBM Extended}"
$w.char.menu add command -label "IBM CPI-852" -command "$w.char configure -text {ISO 8859-2}"
$w.char.menu add command -label "Plain ASCII" -command "$w.char configure -text {Plain ASCII}"
grid configure $w.charlabel -row 3 -column 0 -sticky e
grid configure $w.char -row 3 -column 1 -sticky nsew
label $w.langlabel -text "Language: "
menubutton $w.lang -text $Config(LANGUAGE) -indicatoron 1 -relief raised \
-menu $w.lang.menu
menu $w.lang.menu -tearoff 0
foreach lang {
"Brazilian Portuguese"
"Danish"
"Dutch"
"English"
"Finnish"
"French"
"German"
"Italian"
"Norwegian"
"Polish"
"Romanian"
"Spanish"
"Icelandic"
} {
$w.lang.menu add command -label $lang -command [list $w.lang configure -text $lang]
}
grid configure $w.langlabel -row 4 -column 0 -sticky e
grid configure $w.lang -row 4 -column 1 -sticky nsew
}
#***********************************************************************
# %PROCEDURE: BuildRemind
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Builds Remind by:
# -- creating custom.h from custom.h.in
# -- running ./configure
# -- running make
#***********************************************************************
proc BuildRemind {} {
pack forget .tn
pack forget .buttons
wm title . "Remind Configuration Status"
text .msgs -width 130 -height 35 -wrap char -yscrollcommand ".sb set"
scrollbar .sb -orient vertical -command ".msgs yview"
.msgs tag configure green -foreground #005500
.msgs tag configure red -foreground #990000
pack .msgs -side left -expand 1 -fill both
pack .sb -side left -expand 0 -fill y
update
.msgs insert end "\n>>> Creating src/custom.h...\n\n" green
CreateCustomH
.msgs insert end ">>> Calling `./configure'...\n\n" green
CallConfigure
.msgs insert end ">>> Calling `make'...\n\n" green
CallMake
.msgs insert end "\n----------------------------------------------\n\n"
.msgs insert end "Remind" red
.msgs insert end " has been built. To install it, type:\n\n"
.msgs insert end "make install\n\n" green
.msgs insert end "from the top-level "
.msgs insert end "Remind" red
.msgs insert end " directory. (You may need to be root.)\n\n"
.msgs insert end "After it's installed, create an empty file called:\n"
.msgs insert end " \$HOME/.reminders\n" green
.msgs insert end "and type "
.msgs insert end "tkremind" green
.msgs insert end " for a nice easy introduction to "
.msgs insert end "Remind.\n\n" red
.msgs insert end "Press me to exit --> "
button .msgs.ok -text "OK" -command "exit"
.msgs window create end -window .msgs.ok
.msgs see end
}
#***********************************************************************
# %PROCEDURE: RunCommand
# %ARGUMENTS:
# cmd -- shell command to run
# %RETURNS:
# Return code of command
# %DESCRIPTION:
# Runs a command putting output into ".msgs"
#***********************************************************************
proc RunCommand { cmd } {
global CmdDone
set CmdDone 0
.msgs insert end "$cmd\n" red
set problem [catch {set CmdFile [open "|$cmd" "r"]} err]
if {$problem} {
Bail "Error running command `$cmd': $err"
}
fconfigure $CmdFile -blocking 0
fileevent $CmdFile readable "CommandReadable $CmdFile"
vwait CmdDone
set problem [catch {close $CmdFile} err]
if {$problem} {
Bail "Error running command `$cmd': $err"
}
}
#***********************************************************************
# %PROCEDURE: CommandReadable
# %ARGUMENTS:
# f -- file to read from
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Reads characters from command pipelin and appends them to .msg.
#***********************************************************************
proc CommandReadable { f } {
global CmdDone
set stuff [read $f]
.msgs insert end $stuff
.msgs see end
if {[eof $f]} {
set CmdDone 1
}
}
#***********************************************************************
# %PROCEDURE: CallConfigure
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Executes "./configure" with appropriate arguments
# %PRECONDITIONS:
# Any preconditions
# %POSTCONDITIONS:
# Any postconditions
# %SIDE EFFECTS:
# Any side effects
#***********************************************************************
proc CallConfigure {} {
global Instdir
set bin [$Instdir.bin get]
set man [$Instdir.man get]
RunCommand "./configure --bindir=$bin --mandir=$man"
}
#***********************************************************************
# %PROCEDURE: CreateCustomH
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Creates "src/custom.h" from "src/custom.h.in"
#***********************************************************************
proc CreateCustomH {} {
global Loc Options Config
set problem [catch {set in [open "src/custom.h.in" "r"]} err]
if {$problem} {
Bail "Can't read src/custom.h.in: $err"
}
set problem [catch {set out [open "src/custom.h" "w"]} err]
if {$problem} {
Bail "Can't write src/custom.h: $err"
}
# Retrieve values
# The latitude/longitude ones are tied to the scales; we can't
# modify them willy-nilly
set LAT_DEG $Config(LAT_DEG)
set LAT_MIN $Config(LAT_MIN)
set LON_DEG $Config(LON_DEG)
set LON_MIN $Config(LON_MIN)
if {!$Config(NORTHERN_HEMISPHERE)} {
set LAT_DEG "-$LAT_DEG"
set LAT_MIN "-$LAT_MIN"
}
if {!$Config(WESTERN_HEMISPHERE)} {
set LON_DEG "-$LON_DEG"
set LON_MIN "-$LON_MIN"
}
set Config(LOCATION) [$Loc.location get]
switch -- [$Options.page cget -text] {
"A4" {
set Config(DEFAULT_PAGE) "{\"A4\", 595, 842}"
}
default {
set Config(DEFAULT_PAGE) "{\"Letter\", 612, 792}"
}
}
set Config(DATESEP) [$Options.date cget -text]
set Config(TIMESEP) [$Options.time cget -text]
switch -- [$Options.char cget -text] {
"ISO 8859-1" {
set Config(ISOLATIN1) 1
}
"ISO 8859-2" {
set Config(ISOLATIN2) 1
}
"IBM CPI-852" {
set Config(IBM852) 1
}
"IBM Extended" {
set Config(IBMEXTENDED) 1
}
}
while {[gets $in line] != -1} {
switch -glob -- $line {
"#define LAT_DEG *" {
puts $out "#define LAT_DEG $LAT_DEG"
.msgs insert end "#define LAT_DEG $LAT_DEG\n"
}
"#define LAT_MIN *" {
puts $out "#define LAT_MIN $LAT_MIN"
.msgs insert end "#define LAT_MIN $LAT_MIN\n"
}
"#define LON_DEG *" {
puts $out "#define LON_DEG $LON_DEG"
.msgs insert end "#define LON_DEG $LON_DEG\n"
}
"#define LON_MIN *" {
puts $out "#define LON_MIN $LON_MIN"
.msgs insert end "#define LON_MIN $LON_MIN\n"
}
"#define LOCATION *" {
puts $out "#define LOCATION \"$Config(LOCATION)\""
.msgs insert end "#define LOCATION \"$Config(LOCATION)\"\n"
}
"#define DEFAULT_PAGE *" {
puts $out "#define DEFAULT_PAGE $Config(DEFAULT_PAGE)"
.msgs insert end "#define DEFAULT_PAGE $Config(DEFAULT_PAGE)\n"
}
"#define DATESEP *" {
puts $out "#define DATESEP '$Config(DATESEP)'"
.msgs insert end "#define DATESEP '$Config(DATESEP)'\n"
}
"#define TIMESEP *" {
puts $out "#define TIMESEP '$Config(TIMESEP)'"
.msgs insert end "#define TIMESEP '$Config(TIMESEP)'\n"
}
"#define ISOLATIN1 *" {
puts $out "#define ISOLATIN1 $Config(ISOLATIN1)"
.msgs insert end "#define ISOLATIN1 $Config(ISOLATIN1)\n"
}
"#define ISOLATIN2 *" {
puts $out "#define ISOLATIN2 $Config(ISOLATIN2)"
.msgs insert end "#define ISOLATIN2 $Config(ISOLATIN2)\n"
}
"#define IBM852 *" {
puts $out "#define IBM852 $Config(IBM852)"
.msgs insert end "#define IBM852 $Config(IBM852)\n"
}
"#define IBMEXTENDED *" {
puts $out "#define IBMEXTENDED $Config(IBMEXTENDED)"
.msgs insert end "#define IBMEXTENDED $Config(IBMEXTENDED)\n"
}
default {
puts $out $line
}
}
}
close $in
close $out
}
#***********************************************************************
# %PROCEDURE: CallMake
# %ARGUMENTS:
# None
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Runs "make" with appropriate language definitions
#***********************************************************************
proc CallMake {} {
global Options
set lang [$Options.lang cget -text]
switch -- $lang {
"German" { set lang GERMAN }
"Dutch" { set lang DUTCH }
"Finnish" { set lang FINNISH }
"French" { set lang FRENCH }
"Norwegian" { set lang NORWEGIAN }
"Danish" { set lang DANISH }
"Polish" { set lang POLISH }
"Brazilian Portuguese" { set lang BRAZPORT }
"Italian" { set lang ITALIAN }
"Romanian" { set lang ROMANIAN }
"Spanish" { set lang SPANISH }
"Icelandic" { set lang ICELANDIC }
default { set lang ENGLISH }
}
RunCommand "make \"LANGDEF=-DLANG=$lang\""
}
# Tabbed notebook code from "Effective Tcl/Tk Programming"
# ----------------------------------------------------------------------
# EXAMPLE: tabnotebook that can dial up pages
# ----------------------------------------------------------------------
# Effective Tcl/Tk Programming
# Mark Harrison, DSC Communications Corp.
# Michael McLennan, Bell Labs Innovations for Lucent Technologies
# Addison-Wesley Professional Computing Series
# ======================================================================
# Copyright (c) 1996-1997 Lucent Technologies Inc. and Mark Harrison
# ======================================================================
option add *Tabnotebook.tabs.background #666666 widgetDefault
option add *Tabnotebook.margin 6 widgetDefault
option add *Tabnotebook.tabColor #a6a6a6 widgetDefault
option add *Tabnotebook.activeTabColor #d9d9d9 widgetDefault
option add *Tabnotebook.tabFont \
-*-helvetica-bold-r-normal--*-120-* widgetDefault
proc tabnotebook_create {win} {
global tnInfo
frame $win -class Tabnotebook
canvas $win.tabs -highlightthickness 0
pack $win.tabs -fill x
notebook_create $win.notebook
pack $win.notebook -expand yes -fill both
set tnInfo($win-tabs) ""
set tnInfo($win-current) ""
set tnInfo($win-pending) ""
return $win
}
proc tabnotebook_page {win name} {
global tnInfo
set page [notebook_page $win.notebook $name]
lappend tnInfo($win-tabs) $name
if {$tnInfo($win-pending) == ""} {
set id [after idle [list tabnotebook_refresh $win]]
set tnInfo($win-pending) $id
}
return $page
}
proc tabnotebook_refresh {win} {
global tnInfo
$win.tabs delete all
set margin [option get $win margin Margin]
set color [option get $win tabColor Color]
set font [option get $win tabFont Font]
set x 2
set maxh 0
foreach name $tnInfo($win-tabs) {
set id [$win.tabs create text \
[expr $x+$margin+2] [expr -0.5*$margin] \
-anchor sw -text $name -font $font \
-tags [list $name]]
set bbox [$win.tabs bbox $id]
set wd [expr [lindex $bbox 2]-[lindex $bbox 0]]
set ht [expr [lindex $bbox 3]-[lindex $bbox 1]]
if {$ht > $maxh} {
set maxh $ht
}
$win.tabs create polygon 0 0 $x 0 \
[expr $x+$margin] [expr -$ht-$margin] \
[expr $x+$margin+$wd] [expr -$ht-$margin] \
[expr $x+$wd+2*$margin] 0 \
2000 0 2000 10 0 10 \
-outline black -fill $color \
-tags [list $name tab tab-$name]
$win.tabs raise $id
$win.tabs bind $name <ButtonPress-1> \
[list tabnotebook_display $win $name]
set x [expr $x+$wd+2*$margin]
}
set height [expr $maxh+2*$margin]
$win.tabs move all 0 $height
$win.tabs configure -width $x -height [expr $height+4]
if {$tnInfo($win-current) != ""} {
tabnotebook_display $win $tnInfo($win-current)
} else {
tabnotebook_display $win [lindex $tnInfo($win-tabs) 0]
}
set tnInfo($win-pending) ""
}
proc tabnotebook_display {win name} {
global tnInfo
notebook_display $win.notebook $name
set normal [option get $win tabColor Color]
$win.tabs itemconfigure tab -fill $normal
set active [option get $win activeTabColor Color]
$win.tabs itemconfigure tab-$name -fill $active
$win.tabs raise $name
set tnInfo($win-current) $name
}
# ----------------------------------------------------------------------
# EXAMPLE: simple notebook that can dial up pages
# ----------------------------------------------------------------------
# Effective Tcl/Tk Programming
# Mark Harrison, DSC Communications Corp.
# Michael McLennan, Bell Labs Innovations for Lucent Technologies
# Addison-Wesley Professional Computing Series
# ======================================================================
# Copyright (c) 1996-1997 Lucent Technologies Inc. and Mark Harrison
# ======================================================================
option add *Notebook.borderWidth 2 widgetDefault
option add *Notebook.relief sunken widgetDefault
proc notebook_create {win} {
global nbInfo
frame $win -class Notebook
pack propagate $win 0
set nbInfo($win-count) 0
set nbInfo($win-pages) ""
set nbInfo($win-current) ""
return $win
}
proc notebook_page {win name} {
global nbInfo
set page "$win.page[incr nbInfo($win-count)]"
lappend nbInfo($win-pages) $page
set nbInfo($win-page-$name) $page
frame $page
if {$nbInfo($win-count) == 1} {
after idle [list notebook_display $win $name]
}
return $page
}
proc notebook_display {win name} {
global nbInfo
set page ""
if {[info exists nbInfo($win-page-$name)]} {
set page $nbInfo($win-page-$name)
} elseif {[winfo exists $win.page$name]} {
set page $win.page$name
}
if {$page == ""} {
error "bad notebook page \"$name\""
}
notebook_fix_size $win
if {$nbInfo($win-current) != ""} {
pack forget $nbInfo($win-current)
}
pack $page -expand yes -fill both
set nbInfo($win-current) $page
}
proc notebook_fix_size {win} {
global nbInfo
update idletasks
set maxw 0
set maxh 0
foreach page $nbInfo($win-pages) {
set w [winfo reqwidth $page]
if {$w > $maxw} {
set maxw $w
}
set h [winfo reqheight $page]
if {$h > $maxh} {
set maxh $h
}
}
set bd [$win cget -borderwidth]
set maxw [expr $maxw+2*$bd]
set maxh [expr $maxh+2*$bd]
$win configure -width $maxw -height $maxh
}
#***********************************************************************
# %PROCEDURE: FindRemind
# %ARGUMENTS:
# None
# %RETURNS:
# Full path to an existing "remind" if one is found. Otherwise,
# empty string.
#***********************************************************************
proc FindRemind {} {
global env
set path [concat [split $env(PATH) ":"] "/bin" "/usr/bin" "/usr/local/bin"]
foreach thing $path {
if [file executable [file join $thing "remind"]] {
return [file join $thing "remind"]
}
}
return {}
}
#***********************************************************************
# %PROCEDURE: SetConfigFromRemind
# %ARGUMENTS:
# None
# %RETURNS:
# Sets config settings based on existing remind (if one found) or else
# sensible defaults.
#***********************************************************************
proc SetConfigFromRemind {} {
global Config
SetConfigDefaults
set rem [FindRemind]
if {"$rem" == ""} {
return
}
set dir [file dirname $rem]
set Config(INST_DIR) $dir
if {"$dir" == "/usr/local/bin"} {
set Config(MAN_DIR) "/usr/local/man"
} elseif {$dir == "/usr/bin"} {
set Config(MAN_DIR) "/usr/share/man"
}
# Check for existing man page
if {[file readable "/usr/share/man/man1/remind.1"]} {
set Config(MAN_DIR) "/usr/share/man"
} elseif {[file readable "/usr/man/man1/remind.1"]} {
set Config(MAN_DIR) "/usr/man"
} elseif {[file readable "/usr/local/man/man1/remind.1"]} {
set Config(MAN_DIR) "/usr/local/man"
}
# Query Remind for the rest
QueryRemind $rem LAT_DEG {$LatDeg}
QueryRemind $rem LAT_MIN {$LatMin}
QueryRemind $rem LON_DEG {$LongDeg}
QueryRemind $rem LON_MIN {$LongMin}
QueryRemind $rem LOCATION {$Location}
QueryRemind $rem DATESEP {$DateSep}
QueryRemind $rem TIMESEP {$TimeSep}
QueryRemind $rem LANGUAGE {language()}
set $Config(LAT_MIN) [expr abs($Config(LAT_MIN))]
if {$Config(LAT_DEG) >= 0} {
set Config(NORTHERN_HEMISPHERE) 1
} else {
set Config(NORTHERN_HEMISPHERE) 0
set Config(LAT_DEG) [expr abs($Config(LAT_DEG))]
}
set $Config(LON_MIN) [expr abs($Config(LON_MIN))]
if {$Config(LON_DEG) >= 0} {
set Config(WESTERN_HEMISPHERE) 1
} else {
set Config(WESTERN_HEMISPHERE) 0
set Config(LON_DEG) [expr abs($Config(LON_DEG))]
}
# Get default page from rem2ps
set rem2ps [file join $dir "rem2ps"]
catch {
exec $rem2ps -m help
} err
set errlist [split $err "\n"]
set err [lindex $errlist end]
if {[string match "Default media type is*" $err]} {
set Config(DEFAULT_PAGE) [lindex $err end]
}
}
proc QueryRemind { rem symbol rem_msg } {
global Config
catch {
set fp [open "| $rem -" "r+"]
puts $fp "banner %\nMSG \[$rem_msg\]%\nFLUSH\n"
flush $fp
gets $fp line
catch { close $fp }
}
if {"$line" == ""} {
return
}
set Config($symbol) $line
}
CheckSanity
CreateMainDialog

View File

@@ -1,925 +0,0 @@
/***************************************************************/
/* */
/* CALENDAR.C */
/* */
/* The code for generating a calendar. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: calendar.c,v 1.2 1996-03-31 04:01:54 dfs Exp $";
#include "config.h"
#include <stdio.h>
#include <string.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#include <ctype.h>
#include "types.h"
#include "protos.h"
#include "expr.h"
#include "globals.h"
#include "err.h"
/* Data structures used by the calendar */
typedef struct cal_entry {
struct cal_entry *next;
char *text;
char *pos;
int time;
int priority;
} CalEntry;
/* Global variables */
static CalEntry *CalColumn[7];
static CalEntry *CalPs[7];
static int ColSpaces;
PRIVATE void SortCol ARGS((CalEntry **col));
PRIVATE void DoCalendarOneWeek ARGS ((void));
PRIVATE void DoCalendarOneMonth ARGS ((void));
PRIVATE int WriteCalendarRow ARGS ((void));
PRIVATE void PrintLeft ARGS ((char *s, int width, char pad));
PRIVATE void PrintCentered ARGS ((char *s, int width, char pad));
PRIVATE int WriteOneCalLine ARGS ((void));
PRIVATE int WriteOneColLine ARGS ((int col));
PRIVATE void GenerateCalEntries ARGS ((int col));
PRIVATE void WriteCalHeader ARGS ((void));
PRIVATE void WriteCalTrailer ARGS ((void));
PRIVATE int DoCalRem ARGS ((ParsePtr p, int col));
PRIVATE void WriteSimpleEntries ARGS ((int col, int jul));
PRIVATE void WriteSolidCalLine ARGS ((void));
PRIVATE void WriteIntermediateCalLine ARGS ((void));
PRIVATE void WriteCalDays ARGS ((void));
/***************************************************************/
/* */
/* ProduceCalendar */
/* */
/* Main loop for generating a calendar. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC void ProduceCalendar(void)
#else
void ProduceCalendar()
#endif
{
int y, m, d;
ShouldCache = 1;
ColSpaces = (CalWidth - 9) / 7;
CalWidth = 7*ColSpaces + 8;
if (CalMonths) {
FromJulian(JulianToday, &y, &m, &d);
JulianToday = Julian(y, m, 1);
while (CalMonths--)
DoCalendarOneMonth();
return;
} else {
if (MondayFirst) JulianToday -= (JulianToday%7);
else JulianToday -= ((JulianToday+1)%7);
if (!DoSimpleCalendar) {
WriteIntermediateCalLine();
WriteCalDays();
WriteIntermediateCalLine();
}
while (CalWeeks--)
DoCalendarOneWeek();
return;
}
}
/***************************************************************/
/* */
/* DoCalendarOneWeek */
/* */
/* Write a calendar for a single week */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void DoCalendarOneWeek(void)
#else
static void DoCalendarOneWeek()
#endif
{
int y, m, d, done, i, l, wd;
char buf[81];
int LinesWritten = 0;
int OrigJul = JulianToday;
/* Fill in the column entries */
for (i=0; i<7; i++) {
GenerateCalEntries(i);
JulianToday++;
}
/* Output the entries */
/* If it's "Simple Calendar" format, do it simply... */
if (DoSimpleCalendar) {
if (MondayFirst) wd = JulianToday % 7;
else wd = (JulianToday + 1) % 7;
for (i=0; i<7; i++) {
WriteSimpleEntries(i, OrigJul+i-wd);
}
return;
}
/* Here come the first few lines... */
PutChar('|');
for (i=0; i<7; i++) {
FromJulian(OrigJul+i, &y, &m, &d);
sprintf(buf, "%d %c%c%c ", d, MonthName[m][0], MonthName[m][1],
MonthName[m][2]);
if (OrigJul+i == RealToday)
PrintLeft(buf, ColSpaces, '*');
else
PrintLeft(buf, ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
for (l=0; l<CalPad; l++) {
PutChar('|');
for (i=0; i<7; i++) {
PrintLeft("", ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
}
/* Write the body lines */
done = 0;
while (!done) {
done = WriteOneCalLine();
LinesWritten++;
}
/* Write any blank lines required */
while (LinesWritten++ < CalLines) {
PutChar('|');
for (i=0; i<7; i++) {
PrintLeft("", ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
}
/* Write the final line */
WriteIntermediateCalLine();
}
/***************************************************************/
/* */
/* DoCalendarOneMonth */
/* */
/* Produce a calendar for the current month. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void DoCalendarOneMonth(void)
#else
static void DoCalendarOneMonth()
#endif
{
int y, m, d, mm, yy;
if (!DoSimpleCalendar) WriteCalHeader();
if (PsCal) {
FromJulian(JulianToday, &y, &m, &d);
printf("%s\n", PSBEGIN);
printf("%s %d %d %d %d\n",
MonthName[m], y, DaysInMonth(m, y), (JulianToday+1) % 7,
MondayFirst);
mm = m-1;
if (mm<0) {
mm = 11; yy = y-1;
} else yy=y;
printf("%s %d\n", MonthName[mm], DaysInMonth(mm,yy));
mm = m+1;
if (mm>11) {
mm = 0; yy = y+1;
} else yy=y;
printf("%s %d\n", MonthName[mm], DaysInMonth(mm,yy));
}
while (WriteCalendarRow()) continue;
if (PsCal) printf("%s\n", PSEND);
if (!DoSimpleCalendar) WriteCalTrailer();
}
/***************************************************************/
/* */
/* WriteCalendarRow */
/* */
/* Write one row of the calendar */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int WriteCalendarRow(void)
#else
static int WriteCalendarRow()
#endif
{
int y, m, d, wd, i, l;
int done;
char buf[81];
int OrigJul = JulianToday;
int LinesWritten = 0;
/* Get the date of the first day */
FromJulian(JulianToday, &y, &m, &d);
if (!MondayFirst) wd = (JulianToday + 1) % 7;
else wd = JulianToday % 7;
/* Fill in the column entries */
for (i=wd; i<7; i++) {
if (d+i-wd > DaysInMonth(m, y)) break;
GenerateCalEntries(i);
JulianToday++;
}
/* Output the entries */
/* If it's "Simple Calendar" format, do it simply... */
if (DoSimpleCalendar) {
for (i=wd; i<7 && d+i-wd<=DaysInMonth(m, y); i++) {
WriteSimpleEntries(i, OrigJul+i-wd);
}
return (d+7-wd <= DaysInMonth(m, y));
}
/* Here come the first few lines... */
PutChar('|');
for (i=0; i<7; i++) {
if (i < wd || d+i-wd>DaysInMonth(m, y))
PrintLeft("", ColSpaces, ' ');
else {
sprintf(buf, "%d", d+i-wd);
PrintLeft(buf, ColSpaces, ' ');
}
PutChar('|');
}
PutChar('\n');
for (l=0; l<CalPad; l++) {
PutChar('|');
for (i=0; i<7; i++) {
PrintLeft("", ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
}
/* Write the body lines */
done = 0;
while (!done) {
done = WriteOneCalLine();
LinesWritten++;
}
/* Write any blank lines required */
while (LinesWritten++ < CalLines) {
PutChar('|');
for (i=0; i<7; i++) {
PrintLeft("", ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
}
WriteIntermediateCalLine();
/* Return non-zero if we have not yet finished */
return (d+7-wd <= DaysInMonth(m, y));
}
/***************************************************************/
/* */
/* PrintLeft */
/* */
/* Left-justify a piece of text. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void PrintLeft(char *s, int width, char pad)
#else
static void PrintLeft(s, width, pad)
char *s;
int width;
char pad;
#endif
{
int len = strlen(s);
printf("%s", s);
while (len++ < width) PutChar(pad);
}
/***************************************************************/
/* */
/* PrintCentered */
/* */
/* Center a piec of text */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void PrintCentered(char *s, int width, char pad)
#else
static void PrintCentered(s, width, pad)
char *s;
int width;
char pad;
#endif
{
int len = strlen(s);
int d = (width - len) / 2;
int i;
for (i=0; i<d; i++) PutChar(pad);
for (i=0; i<width; i++) {
if (*s) PutChar(*s++); else break;
}
for (i=d+len; i<width; i++) PutChar(pad);
}
/***************************************************************/
/* */
/* WriteOneCalLine */
/* */
/* Write a single line. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int WriteOneCalLine(void)
#else
static int WriteOneCalLine()
#endif
{
int done = 1, i;
PutChar('|');
for (i=0; i<7; i++) {
if (CalColumn[i]) {
if (WriteOneColLine(i)) done = 0;
} else {
PrintCentered("", ColSpaces, ' ');
}
PutChar('|');
}
PutChar('\n');
return done;
}
/***************************************************************/
/* */
/* WriteOneColLine */
/* */
/* Write a single line for a specified column. Return 1 if */
/* the column still has entries; 0 otherwise. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int WriteOneColLine(int col)
#else
static int WriteOneColLine(col)
int col;
#endif
{
CalEntry *e = CalColumn[col];
char *s;
char *space;
int numwritten = 0;
/* Print as many characters as possible within the column */
space = NULL;
s = e->pos;
/* If we're at the end, and there's another entry, do a blank line and move
to next entry. */
if (!*s && e->next) {
PrintLeft("", ColSpaces, ' ');
CalColumn[col] = e->next;
free(e->text);
free(e);
return 1;
}
/* Find the last space char within the column. */
while (s - e->pos <= ColSpaces) {
if (!*s) {space = s; break;}
if (*s == ' ') space = s;
s++;
}
/* If we couldn't find a space char, print what we have. */
if (!space) {
for (s = e->pos; s - e->pos < ColSpaces; s++) {
if (!*s) break;
numwritten++;
PutChar(*s);
}
e->pos = s;
} else {
/* We found a space - print everything before it. */
for (s = e->pos; s<space; s++) {
if (!*s) break;
numwritten++;
PutChar(*s);
}
}
/* Flesh out the rest of the column */
while(numwritten++ < ColSpaces) PutChar(' ');
/* Skip any spaces before next word */
while (*s == ' ') s++;
/* If done, free memory if no next entry. */
if (!*s && !e->next) {
CalColumn[col] = e->next;
free(e->text);
free(e);
} else {
e->pos = s;
}
if (CalColumn[col]) return 1; else return 0;
}
/***************************************************************/
/* */
/* GenerateCalEntries */
/* */
/* Generate the calendar entries for the ith column */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void GenerateCalEntries(int col)
#else
static void GenerateCalEntries(col)
int col;
#endif
{
int r;
Token tok;
char *s;
Parser p;
/* Do some initialization first... */
ClearGlobalOmits();
DestroyOmitContexts();
DestroyVars(0);
NumTriggered = 0;
r=OpenFile(InitialFile);
if (r) {
fprintf(ErrFp, "%s %s: %s\n", ErrMsg[E_ERR_READING], InitialFile, ErrMsg[r]);
exit(1);
}
while(1) {
r = ReadLine();
if (r == E_EOF) return;
if (r) {
Eprint("%s: %s", ErrMsg[E_ERR_READING], ErrMsg[r]);
exit(1);
}
s = FindInitialToken(&tok, CurLine);
/* Should we ignore it? */
if (NumIfs &&
tok.type != T_If &&
tok.type != T_Else &&
tok.type != T_EndIf &&
tok.type != T_IfTrig &&
ShouldIgnoreLine())
{
/* DO NOTHING */
}
else {
/* Create a parser to parse the line */
CreateParser(s, &p);
switch(tok.type) {
case T_Empty:
case T_Comment:
break;
case T_ErrMsg: r=DoErrMsg(&p); break;
case T_Rem: r=DoCalRem(&p, col); break;
case T_If: r=DoIf(&p); break;
case T_IfTrig: r=DoIfTrig(&p); break;
case T_Else: r=DoElse(&p); break;
case T_EndIf: r=DoEndif(&p); break;
case T_Include: r=DoInclude(&p); break;
case T_Exit: DoExit(&p); break;
case T_Set: r=DoSet(&p); break;
case T_Fset: r=DoFset(&p); break;
case T_UnSet: r=DoUnset(&p); break;
case T_Clr: r=DoClear(&p); break;
case T_Flush: r=DoFlush(&p); break;
case T_Debug: break; /* IGNORE DEBUG CMD */
case T_Dumpvars: break; /* IGNORE DUMPVARS CMD */
case T_Banner: break; /* IGNORE BANNER CMD */
case T_Omit: r=DoOmit(&p);
if (r == E_PARSE_AS_REM) {
DestroyParser(&p);
CreateParser(s, &p);
r=DoCalRem(&p, col);
}
break;
case T_Pop: r=PopOmitContext(&p); break;
case T_Push: r=PushOmitContext(&p); break;
case T_Preserve: r=DoPreserve(&p); break;
case T_RemType: if (tok.val == RUN_TYPE) {
r=DoRun(&p);
break;
} else {
CreateParser(CurLine, &p);
r=DoCalRem(&p, col);
break;
}
/* If we don't recognize the command, do a REM by default */
/* Note: Since the parser hasn't been used yet, we don't */
/* need to destroy it here. */
default: CreateParser(CurLine, &p);
r=DoCalRem(&p, col);
break;
}
if (r && (!Hush || r != E_RUN_DISABLED)) Eprint("%s", ErrMsg[r]);
/* Destroy the parser - free up resources it may be tying up */
DestroyParser(&p);
}
}
}
/***************************************************************/
/* */
/* WriteCalHeader */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void WriteCalHeader(void)
#else
static void WriteCalHeader()
#endif
{
char buf[80];
int y, m, d;
FromJulian(JulianToday, &y, &m, &d);
sprintf(buf, "%s %d", MonthName[m], y);
WriteSolidCalLine();
PutChar('|');
PrintCentered(buf, CalWidth-2, ' ');
PutChar('|');
PutChar('\n');
WriteIntermediateCalLine();
WriteCalDays();
WriteIntermediateCalLine();
}
/***************************************************************/
/* */
/* WriteCalTrailer */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void WriteCalTrailer(void)
#else
static void WriteCalTrailer()
#endif
{
PutChar('\f');
}
/***************************************************************/
/* */
/* DoCalRem */
/* */
/* Do the REM command in the context of a calendar. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int DoCalRem(ParsePtr p, int col)
#else
static int DoCalRem(p, col)
ParsePtr p;
int col;
#endif
{
Trigger trig;
TimeTrig tim;
Value v;
int r;
int jul;
CalEntry *CurCol = CalColumn[col];
CalEntry *CurPs = CalPs[col];
CalEntry *e;
char *s, *s2;
static char buf[TOKSIZE];
static char obuf[LINELEN];
Token tok;
/* Parse the trigger date and time */
if ( (r=ParseRem(p, &trig, &tim)) ) return r;
/* Don't include timed reminders in calendar if -a option supplied. */
#ifdef HAVE_QUEUED
if (DontIssueAts && tim.ttime != NO_TIME) return OK;
#endif
if (trig.typ == NO_TYPE) return E_EOLN;
if (trig.typ == SAT_TYPE) {
r=DoSatRemind(&trig, &tim, p);
if (r) return r;
r=ParseToken(p, buf);
if (r) return r;
FindToken(buf, &tok);
if (tok.type == T_Empty || tok.type == T_Comment) return OK;
if (tok.type != T_RemType || tok.val == SAT_TYPE) return E_PARSE_ERR;
trig.typ = tok.val;
jul = LastTriggerDate;
if (!LastTrigValid) return OK;
} else {
/* Calculate the trigger date */
jul = ComputeTrigger(trig.scanfrom, &trig, &r);
if (r) return r;
}
if (!PsCal && (trig.typ == PS_TYPE || trig.typ == PSF_TYPE)) return OK;
/* Remove any "at" times from PS or PSFILE reminders */
if (trig.typ == PS_TYPE || trig.typ == PSF_TYPE) tim.ttime = NO_TIME;
/* If trigger date == today, add it to the current entry */
if (jul == JulianToday) {
NumTriggered++;
s = obuf;
*s = 0;
if (DoSimpleCalendar || tim.ttime != NO_TIME)
s += strlen(SimpleTime(tim.ttime, s));
if (trig.typ != PS_TYPE && trig.typ != PSF_TYPE &&
UserFuncExists("calprefix")==1) {
sprintf(buf, "calprefix(%d)", trig.priority);
s2 = buf;
r = EvalExpr(&s2, &v);
if (!r) {
if (!DoCoerce(STR_TYPE, &v)) {
strcat(s, v.v.str);
s += strlen(s);
}
DestroyValue(v);
}
}
if ( (r=DoSubst(p, s, &trig, &tim, jul, CAL_MODE)) ) return r;
if (!*s) return OK;
if (trig.typ != PS_TYPE && trig.typ != PSF_TYPE &&
UserFuncExists("calsuffix")==1) {
sprintf(buf, "calsuffix(%d)", trig.priority);
s2 = buf;
r = EvalExpr(&s2, &v);
if (!r) {
if (!DoCoerce(STR_TYPE, &v)) {
strcat(s, v.v.str);
s += strlen(s);
}
DestroyValue(v);
}
}
s = obuf;
if (!DoSimpleCalendar) while (isspace(*s)) s++;
e = NEW(CalEntry);
if (!e) return E_NO_MEM;
e->text = StrDup(s);
if (!e->text) {
free(e);
return E_NO_MEM;
}
e->priority = trig.priority;
if (trig.typ == PS_TYPE || trig.typ == PSF_TYPE) {
e->pos = (trig.typ == PS_TYPE) ? "P" : "F";
e->time = NO_TIME;
e->next = CurPs;
CalPs[col] = e;
SortCol(&CalPs[col]);
} else {
e->pos = e->text;
e->time = tim.ttime;
e->next = CurCol;
CalColumn[col] = e;
SortCol(&CalColumn[col]);
}
}
return OK;
}
/***************************************************************/
/* */
/* WriteSimpleEntries */
/* */
/* Write entries in 'simple calendar' format. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void WriteSimpleEntries(int col, int jul)
#else
static void WriteSimpleEntries(col, jul)
int col, jul;
#endif
{
CalEntry *e = CalPs[col];
CalEntry *n;
int y, m, d;
/* Do all the PostScript entries first, if any */
FromJulian(jul, &y, &m, &d);
while(e) {
printf("%c%c%c%c%c%02d%c%02d ", *(e->pos), *(e->pos),
*(e->pos), *(e->pos), DATESEP,
m+1, DATESEP, d);
printf("%s\n", e->text);
free(e->text);
n = e->next;
free(e);
e = n;
}
CalPs[col] = NULL;
e = CalColumn[col];
while(e) {
printf("%04d%c%02d%c%02d ", y, DATESEP, m+1, DATESEP, d);
printf("%s\n", e->text);
free(e->text);
n = e->next;
free(e);
e = n;
}
CalColumn[col] = NULL;
}
/***************************************************************/
/* */
/* Various functions for writing different types of lines. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void WriteSolidCalLine(void)
#else
static void WriteSolidCalLine()
#endif
{
PutChar('+');
PrintCentered("", CalWidth-2, '-');
PutChar('+');
PutChar('\n');
}
#ifdef HAVE_PROTOS
PRIVATE void WriteIntermediateCalLine(void)
#else
static void WriteIntermediateCalLine()
#endif
{
int i;
PutChar('+');
for (i=0; i<7; i++) {
PrintCentered("", ColSpaces, '-');
PutChar('+');
}
PutChar('\n');
}
#ifdef HAVE_PROTOS
PRIVATE void WriteCalDays(void)
#else
static void WriteCalDays()
#endif
{
int i;
PutChar('|');
for (i=0; i<7; i++) {
if (!MondayFirst)
PrintCentered(DayName[(i+6)%7], ColSpaces, ' ');
else
PrintCentered(DayName[i%7], ColSpaces, ' ');
PutChar('|');
}
PutChar('\n');
}
/***************************************************************/
/* */
/* SimpleTime */
/* */
/* Format the time according to simple time format. */
/* If out is NULL, result placed in internal static buffer. */
/* A trailing space is always added. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC char *SimpleTime(int tim, char *out)
#else
char *SimpleTime(tim, out)
int tim;
char *out;
#endif
{
static buf[9];
int h, min, hh;
if (!out) out = (char *) buf;
*out = 0;
switch(ScFormat) {
case SC_AMPM:
if (tim == NO_TIME) sprintf(out, " ");
else {
h = tim / 60;
min = tim % 60;
if (h == 0) hh=12;
else if (h > 12) hh=h-12;
else hh=h;
sprintf(out, "%2d%c%02d%s ", hh, TIMESEP, min, (h>=12) ? L_PM : L_AM);
}
break;
case SC_MIL:
if (tim == NO_TIME) sprintf(out, " ");
else {
h = tim / 60;
min = tim % 60;
sprintf(out, "%02d%c%02d ", h, TIMESEP, min);
}
break;
}
return out;
}
/***************************************************************/
/* */
/* SortCol */
/* */
/* Sort the calendar entries in a column by time and priority */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void SortCol(CalEntry **col)
#else
static void SortCol(col)
CalEntry **col;
#endif
{
CalEntry *cur, *prev, *next;
cur = *col;
prev = NULL;
/* Note that we use <= comparison rather than > comparison to preserve the
file order of reminders which have the same time and priority */
while (cur->next &&
CompareRems(0, cur->time, cur->priority,
0, cur->next->time, cur->next->priority,
SortByDate, SortByTime, SortByPrio) <= 0) {
next = cur->next;
/* Swap cur and next */
if (!prev) {
*col = next;
cur->next = next->next;
next->next = cur;
prev = next;
} else {
prev->next = next;
cur->next = next->next;
next->next = cur;
prev = next;
}
}
}

5277
configure vendored Executable file

File diff suppressed because it is too large Load Diff

80
configure.in Normal file
View File

@@ -0,0 +1,80 @@
dnl Process this file with autoconf to produce a configure script.
AC_INIT(src/queue.c)
cat <<'EOF'
**********************
* *
* Configuring REMIND *
* *
**********************
EOF
AC_CONFIG_HEADER(src/config.h)
if test "`uname -s`" = "Darwin" ; then
trap 'echo Be patient...' INT TERM
cat <<'EOF'
Please don't use Apple products. This script will continue in 30 seconds
if you insist on compiling Remind on Mac OS X.
EOF
for i in 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 ; do
sleep 1
done
trap - INT
trap - TERM
fi
if uname -s | grep -i -q 'cygwin' ; then
trap 'echo Be patient...' INT TERM
cat <<'EOF'
Please don't use Microsoft products. This script will continue in 30
seconds if you insist on compiling Remind on Cygwin.
EOF
for i in 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 ; do
sleep 1
done
trap - INT
trap - TERM
fi
dnl Checks for programs.
AC_PROG_CC
AC_PROG_INSTALL
AC_PROG_LN_S
AC_PROG_MAKE_SET
dnl Checks for libraries.
dnl Replace `main' with a function in -lm:
AC_CHECK_LIB(m, sqrt)
dnl Integer sizes
AC_CHECK_SIZEOF(unsigned short)
AC_CHECK_SIZEOF(unsigned int)
AC_CHECK_SIZEOF(unsigned long)
dnl Checks for header files.
AC_CHECK_HEADERS(sys/file.h glob.h wctype.h locale.h)
dnl Checks for typedefs, structures, and compiler characteristics.
AC_STRUCT_TM
dnl Checks for library functions.
AC_FUNC_UTIME_NULL
AC_HEADER_TIME
if test "$GCC" = yes; then
CFLAGS="$CFLAGS -Wall -Wextra -Wstrict-prototypes"
fi
AC_CHECK_FUNCS(setenv unsetenv glob mbstowcs setlocale)
VERSION=03.03.04
AC_SUBST(VERSION)
AC_OUTPUT(src/Makefile www/Makefile src/version.h)

9
contrib/README Normal file
View File

@@ -0,0 +1,9 @@
This directory contains contributed scripts. They are provided
"as-is" with no warranty. Please do not contact Dianne Skoll for help
with these scripts; instead, contact the script authors.
You should check the upstream sources; there may be newer versions
of these scripts available.
--
Dianne Skoll

279
contrib/ical2rem.pl Executable file
View File

@@ -0,0 +1,279 @@
#!/usr/bin/perl -w
#
# ical2rem.pl -
# Reads iCal files and outputs remind-compatible files. Tested ONLY with
# calendar files created by Mozilla Calendar/Sunbird. Use at your own risk.
# Copyright (c) 2005, 2007, Justin B. Alcorn
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#
#
# version 0.5.2 2007-03-23
# - BUG: leadtime for recurring events had a max of 4 instead of DEFAULT_LEAD_TIME
# - remove project-lead-time, since Category was a non-standard attribute
# - NOTE: There is a bug in iCal::Parser v1.14 that causes multiple calendars to
# fail if a calendar with recurring events is followed by a calendar with no
# recurring events. This has been reported to the iCal::Parser author.
# version 0.5.1 2007-03-21
# - BUG: Handle multiple calendars on STDIN
# - add --heading option for priority on section headers
# version 0.5 2007-03-21
# - Add more help options
# - --project-lead-time option
# - Supress printing of heading if there are no todos to print
# version 0.4
# - Version 0.4 changes all written or inspired by, and thanks to Mark Stosberg
# - Change to GetOptions
# - Change to pipe
# - Add --label, --help options
# - Add Help Text
# - Change to subroutines
# - Efficiency and Cleanup
# version 0.3
# - Convert to GPL (Thanks to Mark Stosberg)
# - Add usage
# version 0.2
# - add command line switches
# - add debug code
# - add SCHED _sfun keyword
# - fix typos
# version 0.1 - ALPHA CODE.
=head1 SYNOPSIS
cat /path/to/file*.ics | ical2rem.pl > ~/.ical2rem
All options have reasonable defaults:
--label Calendar name (Default: Calendar)
--lead-time Advance days to start reminders (Default: 3)
--todos, --no-todos Process Todos? (Default: Yes)
--heading Define a priority for static entries
--help Usage
--man Complete man page
Expects an ICAL stream on STDIN. Converts it to the format
used by the C<remind> script and prints it to STDOUT.
=head2 --label
ical2rem.pl --label "Bob's Calendar"
The syntax generated includes a label for the calendar parsed.
By default this is "Calendar". You can customize this with
the "--label" option.
=head2 --lead-time
ical2rem.pl --lead-time 3
How may days in advance to start getting reminders about the events. Defaults to 3.
=head2 --no-todos
ical2rem.pl --no-todos
If you don't care about the ToDos the calendar, this will surpress
printing of the ToDo heading, as well as skipping ToDo processing.
=head2 --heading
ical2rem.pl --heading "PRIORITY 9999"
Set an option on static messages output. Using priorities can made the static messages look different from
the calendar entries. See the file defs.rem from the remind distribution for more information.
=cut
use strict;
use iCal::Parser;
use DateTime;
use Getopt::Long 2.24 qw':config auto_help';
use Pod::Usage;
use Data::Dumper;
use vars '$VERSION';
$VERSION = "0.5.2";
# Declare how many days in advance to remind
my $DEFAULT_LEAD_TIME = 3;
my $PROCESS_TODOS = 1;
my $HEADING = "";
my $help;
my $man;
my $label = 'Calendar';
GetOptions (
"label=s" => \$label,
"lead-time=i" => \$DEFAULT_LEAD_TIME,
"todos!" => \$PROCESS_TODOS,
"heading=s" => \$HEADING,
"help|?" => \$help,
"man" => \$man
);
pod2usage(1) if $help;
pod2usage(-verbose => 2) if $man;
my $month = ['None','Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec'];
my @calendars;
my $in;
while (<>) {
$in .= $_;
if (/END:VCALENDAR/) {
push(@calendars,$in);
$in = "";
}
}
my $parser = iCal::Parser->new();
my $hash = $parser->parse_strings(@calendars);
##############################################################
#
# Subroutines
#
#############################################################
#
# _process_todos()
# expects 'todos' hashref from iCal::Parser is input
# returns String to output
sub _process_todos {
my $todos = shift;
my ($todo, @newtodos, $leadtime);
my $output = "";
$output .= 'REM '.$HEADING.' MSG '.$label.' ToDos:%"%"%'."\n";
# For sorting, make sure everything's got something
# To sort on.
my $now = DateTime->now;
for $todo (@{$todos}) {
# remove completed items
if ($todo->{'STATUS'} && $todo->{'STATUS'} eq 'COMPLETED') {
next;
} elsif ($todo->{'DUE'}) {
# All we need is a due date, everything else is sugar
$todo->{'SORT'} = $todo->{'DUE'}->clone;
} elsif ($todo->{'DTSTART'}) {
# for sorting, sort on start date if there's no due date
$todo->{'SORT'} = $todo->{'DTSTART'}->clone;
} else {
# if there's no due or start date, just make it now.
$todo->{'SORT'} = $now;
}
push(@newtodos,$todo);
}
if (! (scalar @newtodos)) {
return "";
}
# Now sort on the new Due dates and print them out.
for $todo (sort { DateTime->compare($a->{'SORT'}, $b->{'SORT'}) } @newtodos) {
my $due = $todo->{'SORT'}->clone();
my $priority = "";
if (defined($todo->{'PRIORITY'})) {
if ($todo->{'PRIORITY'} == 1) {
$priority = "PRIORITY 1000";
} elsif ($todo->{'PRIORITY'} == 3) {
$priority = "PRIORITY 7500";
}
}
if (defined($todo->{'DTSTART'}) && defined($todo->{'DUE'})) {
# Lead time is duration of task + lead time
my $diff = ($todo->{'DUE'}->delta_days($todo->{'DTSTART'})->days())+$DEFAULT_LEAD_TIME;
$leadtime = "+".$diff;
} else {
$leadtime = "+".$DEFAULT_LEAD_TIME;
}
$output .= "REM ".$due->month_abbr." ".$due->day." ".$due->year." $leadtime $priority MSG \%a $todo->{'SUMMARY'}\%\"\%\"\%\n";
}
$output .= 'REM '.$HEADING.' MSG %"%"%'."\n";
return $output;
}
#######################################################################
#
# Main Program
#
######################################################################
print _process_todos($hash->{'todos'}) if $PROCESS_TODOS;
my ($leadtime, $yearkey, $monkey, $daykey,$uid,%eventsbyuid);
print 'REM '.$HEADING.' MSG '.$label.' Events:%"%"%'."\n";
my $events = $hash->{'events'};
foreach $yearkey (sort keys %{$events} ) {
my $yearevents = $events->{$yearkey};
foreach $monkey (sort {$a <=> $b} keys %{$yearevents}){
my $monevents = $yearevents->{$monkey};
foreach $daykey (sort {$a <=> $b} keys %{$monevents} ) {
my $dayevents = $monevents->{$daykey};
foreach $uid (sort {
DateTime->compare($dayevents->{$a}->{'DTSTART'}, $dayevents->{$b}->{'DTSTART'})
} keys %{$dayevents}) {
my $event = $dayevents->{$uid};
if ($eventsbyuid{$uid}) {
my $curreventday = $event->{'DTSTART'}->clone;
$curreventday->truncate( to => 'day' );
$eventsbyuid{$uid}{$curreventday->epoch()} =1;
for (my $i = 0;$i < $DEFAULT_LEAD_TIME && !defined($event->{'LEADTIME'});$i++) {
if ($eventsbyuid{$uid}{$curreventday->subtract( days => $i+1 )->epoch() }) {
$event->{'LEADTIME'} = $i;
}
}
} else {
$eventsbyuid{$uid} = $event;
my $curreventday = $event->{'DTSTART'}->clone;
$curreventday->truncate( to => 'day' );
$eventsbyuid{$uid}{$curreventday->epoch()} =1;
}
}
}
}
}
foreach $yearkey (sort keys %{$events} ) {
my $yearevents = $events->{$yearkey};
foreach $monkey (sort {$a <=> $b} keys %{$yearevents}){
my $monevents = $yearevents->{$monkey};
foreach $daykey (sort {$a <=> $b} keys %{$monevents} ) {
my $dayevents = $monevents->{$daykey};
foreach $uid (sort {
DateTime->compare($dayevents->{$a}->{'DTSTART'}, $dayevents->{$b}->{'DTSTART'})
} keys %{$dayevents}) {
my $event = $dayevents->{$uid};
if (exists($event->{'LEADTIME'})) {
$leadtime = "+".$event->{'LEADTIME'};
} else {
$leadtime = "+".$DEFAULT_LEAD_TIME;
}
my $start = $event->{'DTSTART'};
print "REM ".$start->month_abbr." ".$start->day." ".$start->year." $leadtime ";
if ($start->hour > 0) {
print " AT ";
print $start->strftime("%H:%M");
print " SCHED _sfun MSG %a %2 ";
} else {
print " MSG %a ";
}
print "%\"$event->{'SUMMARY'}";
print " at $event->{'LOCATION'}" if $event->{'LOCATION'};
print "\%\"%\n";
}
}
}
}
exit 0;
#:vim set ft=perl ts=4 sts=4 expandtab :

View File

@@ -0,0 +1,13 @@
DESTDIR?=
PREFIX?=/usr
BINDIR?=$(PREFIX)/bin
MANDIR?=$(PREFIX)/share/man
default: rem2ics.1
rem2ics.1:
pod2man -c "" rem2ics > rem2ics.1
install: rem2ics.1
install -p -D rem2ics $(DESTDIR)$(BINDIR)/rem2ics
install -p -D -m 0644 rem2ics.1 $(DESTDIR)$(MANDIR)/man1/rem2ics.1

847
contrib/rem2ics-0.93/rem2ics Executable file
View File

@@ -0,0 +1,847 @@
#!/usr/bin/perl -w
# rem2ics -- convert the output of "remind -s" into RFC2445 iCalendar format.
# Copyright 2007,2008,2009
# Mark Atwood <me@mark.atwood.name>
# Paul Hinze <paul dot t dot hinze at gmail dot com>
# Michael Schultz <mjschultz at gmail dot com>
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the
# Free Software Foundation, Inc.
# 51 Franklin Street, Fifth Floor
# Boston MA 02110-1301 USA
use strict;
use warnings;
=head1 NAME
rem2ics - convert the output of "remind -s" into RFC2445 iCalendar format.
=head1 SYNOPSIS
TZ=I<timezone> B<rem2ics> [B<-man>] [B<-do>] [B<-norecur>] [B<-usetag>] E<lt>input E<gt>output
=head1 OPTIONS AND ARGUMENTS
=over 8
=item B<-man>
Print the manual page and exit.
=item B<-do>
Actually do the conversion. Otherwise just print a brief help message
and usage example, and then exit.
=item B<-norecur>
Do not attempt to detect and fold together recurring events.
=item B<-usetag>
Generate UIDs using remind TAG clauses.
=back
Input is from standard input
Output is to standard output.
=head1 USAGE
remind -s360 -irem2ics=1 ~/.reminders 1 Jan 1991 | TZ=PST8PDT rem2ics -do >reminders.ics
This tells B<remind> to use ~/.reminders, and to process the entire
range of dates it can handle (from Jan 1 1991 to Dec 31 2020), and to
define a variable named C<rem2ics>, which can be used in
C<IF !defined("rem2ics")> / C<ENDIF> pairs.
B<rem2ics> will use a timezone of PST8PDT, and will fold events that
have the same name and duration into a single iCalendar VEVENT object.
=head1 NOTES
=head2 Timezones and the TZ environment variable.
B<rem2ics> uses the TZ environment variable to determine the value of
the RFC2445 TZID property. If you are running on a Linux or other GNU
libc based system, you probably don't (and probably shouldn't)
normally have TZ set. You can confirm this by running C<printenv TZ>
at a shell prompt. If your remind data is in your "local time", and
it probably is, you should probably set TZ to a good name for your
local timezone just for the run of this script. You probably should
NOT set TZ in your login scripts.
You can use TZ like this:
remind -s ~/.reminders | TZ=PST8PDT rem2ics -do >reminders.ics
or
remind -s ~/.reminders | TZ=US/Pacific rem2ics -do >reminders.ics
If, for some reason, your remind files are all in GMT instead of
localtime (you smart person you!), you can do this:
remind -s ~/.reminders | TZ=GMT rem2ics -do >reminders.ics
or
remind -s ~/.reminders | TZ=0 rem2ics -do >reminders.ics
and B<rem2ics> will use the ISO8601 "Z" notation for GMT time in the ics
file. (Other synonyms for GMT are the empty string (not the same as
the TZ not set), "I<0>", "I<Z>", "I<Zulu>", "I<Greenwitch>", "I<GMT>",
"I<GMT+0>, and "I<GMT-0>".)
If you leave TZ undefined and unset, B<rem2ics> will use the ISO8601
"T" notation date strings with no TZID property, which RFC2445 calls a
"floating time". Who knows, it might work for you!
The TZ string value is literally incorporated into the iCalendar
stream, so whatever your iCalendar-using application needs is what you
should use. You may have to experiment a bit.
You can look around in C</usr/share/zoneinfo> to get the names of
every timezone anywhere. This is the "Olson database" that RFC2445
refers to. Read the man page for L<tzfile(5)> for more than you ever
wanted to know about the format of these files, and about GNU libc's
handling of timezones. As complex as it is, it's certainly better
than what POSIX defines or what most legacy UNIX systems do, and most
certainly better than Microsoft, who in their "cutting edge" "state of
the art" "server" OS, still hasn't figured out that daylight time
rules might be different in different years.
If you just ran B<rem2ics> without reading all this stuff, or if you
don't want to worry about it at all, and somehow your iCalendar
application manager is able to guess the proper timezone for you, just
leave TZ undefined, and B<rem2ics> will use the ISO8601 "T" notation
date strings with no TZID property, which RFC2445 calls a "floating
time". Who knows, it might work for you!
=head2 Detecting recurring events
B<rem2ics> tries to detect recurring events. If any multiple events
appear with exactly the text and exactly the same duration (including
"no duration"), instead of multiple VEVENT objects, there will be just
one VEVENT object, that will have a RFC2445 C<RDATE> property.
B<rem2ics> is not yet smart enough to derive an C<RRULE> based
recurrance. If you really want that feature, either implement it and
send in a patch, or contact the author and convince him to do it.
=head2 Other iCalendar Properties
B<rem2ics> does not generate C<DESCRIPTION> or C<LOCATION>. One
would have to heuristically parse them out of the text, and everyone
uses a idiosyncratic way of putting things in B<remind>.
If the B<-usetag> option is not used or no C<TAG> is set for a
reminder, B<rem2ics> will synthesize C<UID> properties for each
VEVENT, but the UIDs will be different (and unique) for each run of
B<rem2ics>. If you run rem2ics twice and import the two resulting ICS
streams into your new scheduling program, your appointments will
appear twice. If, however, you have set C<TAG> clauses in your
reminders and activated B<-usetag>, these will be used. The same
applies for tags synthesized by B<remind>'s B<-y> option. Hence, it
is more useful to use the B<-y> option than to let B<rem2ics>
synthesize UIDs, because the UIDs will stay the same across multiple
runs.
=head2 Other iCalendar Perl objects
Why does't B<rem2ics> use any of the iCalendar Perl stuff in CPAN?
Because I don't trust them, and they are too big for this app. One
links to a binary library. Another hasn't been maintained since 1991,
and is full of notes as to how buggy and incomplete it is. And so
forth. I am not at this moment interested in groveling around in
L<Net::iCal>, L<DateTime::Format::iCal>, L<Tie::iCal>,
L<iCal::Parser>, or C<libical>.
=head2 Previous implementation
There is a working quick & dirty rem2ics written in awk
by Anthony J. Chivetta E<lt>achivetta@gmail.comE<gt>.
But it has the following problems: it doesn't escape the text, it
doesn't handle events that cross over midnight, it doesn't do
timezones, it doesn't enforce the correct EOL sequence, and it doesn't
fold long lines. This is a replacement for that script.
=head1 TODO
If TZ not set, grab out of system config somewhere
Detect recurring events.
If I'm REALLY smart, derive RRULE
Handle characters not in US-ASCII. Latin1? UTF8?
=head1 VERSION HISTORY
=over 8
=item version 0.1 2007-02-08
First cut.
=item version 0.2 2007-02-09
Reorg into multipass over a data structure.
=item version 0.3 2007-02-10
Collapse repeating events. Fold output lines.
=item version 0.9 2007-02-11
POD. Command line options. First public release.
=item version 0.91 2007-02-14
Bug fix, error message for non-recurring events
=item version 0.92 2008-01-28
Bug fix,
rem2ics 0.91 chokes on timed reminders with
duration using `remind -s` as it functions in remind-03.01.03.
Remind 3.01 changed how the -s data is formated for events that have a duration
Patch by Paul Hinze E<lt>paul dot t dot hinze at gmail dot comE<gt>
and Michael Schultz E<lt>mjschultz at gmail dot comE<gt>
=item version 0.93 2009-06-25
Add B<-usetag> option to allow for UIDs to stay the same across multiple runs
by using the remind TAG clause.
Patch by Tim Weber E<lt>scy at scytale dot nameE<gt>
=back
=head1 SEE ALSO
L<http://mark.atwood.name/code/rem2ics>
L<http://en.wikipedia.org/wiki/ICalendar>
L<http://tools.ietf.org/html/rfc2445>
L<https://dianne.skoll.ca/projects/remind/>
L<remind(1)>
=head1 AUTHOR
Copyright 2007,2008,2009 by Mark Atwood E<lt>me+rem2ics@mark.atwood.nameE<gt>. L<http://mark.atwood.name/>.
Please report bugs (with patches, if possible).
Inspired by Anthony J. Chivetta E<lt>achivetta@gmail.comE<gt>'s
rem2ics in awk.
Thank you to Dianne Skoll E<lt>dianne@skoll.ca<gt> for Remind,
and to the IETF calsch wg for the iCalendar specification.
=cut
use Getopt::Long;
use Pod::Usage;
my $app_name = "rem2ics";
my $app_version = "0.93";
# process the command line
my %options;
GetOptions(\%options, qw(man do norecurr usetag)) || pod2usage(2);
pod2usage(-verbose => 2) if ($options{man});
unless ($options{do}) {
print STDERR "Run \"$0 -man\" for information and usage examples.\n"
. "Pay special attention to information about timezone.\n";
exit(99);
}
# grab the hostname
# this is used as part of the UID property of each VEVENT
my $ical_uid_hostname = $ENV{'HOSTNAME'};
unless ($ical_uid_hostname) {
print STDERR "Warning! "
. "The environment variable HOSTNAME was not properly set.\n"
. "Will use \"localhost\" in the RFC2445 UID property\n";
$ical_uid_hostname = "localhost";
}
# look for the TZ
my $ical_tzid = undef;
if (exists $ENV{'TZ'}) {
$ical_tzid = $ENV{'TZ'};
my %synonyms_for_gmt = (
'' => 1, '0' => 1, 'z' => 1, 'zulu' => 1, 'greenwitch' => 1,
'gmt' => 1, 'gmt+0' => 1, 'gmt-0' => 1, );
if (exists $synonyms_for_gmt{lc($ical_tzid)}) {
$ical_tzid = ''; # empty means GMT, below
}
} else {
# leave it undefined, that has a meaning below
}
# RFC2445 DTSTAMP property will be the time we started running ($^T)
my ($ical_dtstamp);
{
my @gt = gmtime($^T);
$ical_dtstamp = sprintf("%04d%02d%02dZ%02d%02d%02dZ",
1900+$gt[5], $gt[4]+1, $gt[3],
$gt[2], $gt[1], $gt[0]);
}
my ($cnt, $v, @events);
$cnt = 0;
foreach (<STDIN>) {
$cnt++;
s/#.*//; # toss comments
next if /^\s*$/; # skip blank lines
chomp;
$v = undef;
# store the raw line
$v->{src} = $_;
$v->{cnt} = $cnt;
# split and parse the line
# if we don't like it, skip it and go around again
# sf[0] = date, in yyyy/mm/dd format
# sf[1] = special, usually "*"
# sf[2] = tag, usually "*"
# sf[3] = duration, in minutes
# sf[4] = time, since midnight, in minutes
# sf[5] = text
my @sf = split(' ', $_, 6);
next unless ($sf[1] eq '*'); # ignore SPECIAL lines
next unless (($sf[3] eq '*') or ($sf[3] =~ m/\d+/));
next unless (($sf[4] eq '*') or ($sf[4] =~ m/\d+/));
next unless (length($sf[5]) > 0);
my @dt = split('/', $sf[0], 3);
next unless ($dt[0] =~ m/^\d{4}$/); # year
next unless ($dt[1] =~ m/^\d{2}$/); # month
next unless ($dt[2] =~ m/^\d{2}$/); # day
if ($sf[4] ne "*") { # a time was given
# When an event has a time, remind -s "helpfully" also
# puts it as text at the start of the text portion.
# This takes the following form:
# ##:##[a|p]m <rest of MSG>
# or, if the event has a duration:
# ##:##[a|p]m-##:##[a|p]m <rest of MSG>
# Rather than a nasty regex, just splitting at the
# first space does the trick.
my($extra_time, $textmsg) = split(' ', $sf[5], 2);
$sf[5] = $textmsg;
}
$v->{sf} = \@sf;
$v->{dt} = \@dt;
push @events, $v;
}
# generate the "date time string" for each event
foreach $v (@events) {
if (${$v->{sf}}[4] eq "*") { # no time was given
$v->{dts} = sprintf("%04d%02d%02d", @{$v->{dt}});
} else { # a time was given
my ($t_hr, $t_mn) = &idiv(${$v->{sf}}[4], 60);
$v->{dts} = sprintf("%04d%02d%02dT%02d%02d00",
@{$v->{dt}}, $t_hr, $t_mn);
}
}
my(%grovel);
# if the user doesnt want recurrance detection
unless ($options{norecurr}) {
# then dont put events in the grovel hash
foreach $v (@events) {
# key is duration followed by text
# \036 is "ASCII RS Record Separator"
my $k = ${$v->{sf}}[3] . "\036" . ${$v->{sf}}[5];
push @{$grovel{$k}}, $v;
}
foreach my $k (keys %grovel) {
if ((scalar @{$grovel{$k}}) > 1) {
$v = ${$grovel{$k}}[0];
$v->{recurlist} = \@{$grovel{$k}};
foreach my $v0 (@{$grovel{$k}}) {
$v0->{is_recurrance} = $v;
}
}
}
}
# All of the individual events are in the @events array. All of the
# unique combinations of duration/event name are the keys in the
# %grovel hash, the elements of which are references to an arrays of
# references to the events, in the same ordering as they we read by
# us, which *ought* to be in datewise order. I don't know if "remind
# -s" actually sorts into true chronological order. If it doesn't, we
# might have a problem if a recurring event has two instances both on
# the first day.
# Every event that is recurring has a "is_recurrance" property.
# Additionally, (hopefully) the first/earliest event in a set of
# recurrances has a "recurlist" property. The "recurlist" is a
# reference to a list of references to each of the events. The first
# one on that list will be the same event that has the "recurlist"
# property. The "is_recurrance" property is a reference back to the
# event that has the "recurlist" property.
foreach my $k (keys %grovel) {
next if ((scalar @{$grovel{$k}}) <= 1);
my $recur_str = "";
foreach $v (@{$grovel{$k}}) {
if (${$v->{sf}}[4] eq "*") { # no time was given
$recur_str .= ($v->{dts} . ",");
} else {
if (defined($ical_tzid)) {
if ($ical_tzid eq '') { # tz is defined but empty, so in GMT
$recur_str .= $v->{dts} . "Z,";
} else { # tz is non-zero, so output the tz as well
$recur_str .= $v->{dts} . ",";
}
} else { # undefined tz, just floating time
$recur_str .= $v->{dts} . ",";
}
}
}
# the recur_str now has an extra comma at the end. chop it off
chop($recur_str);
${$grovel{$k}}[0]->{recur_str} = $recur_str;
}
foreach my $k (keys %grovel) {
next if ((scalar @{$grovel{$k}}) <= 1);
my $v = ${$grovel{$k}}[0]; # grab the head of each list
if (${$v->{sf}}[4] eq "*") { # no time was given
# the default value type for an RDATE is DATE-TIME,
# we much change the type to DATE
$v->{i_rdate} = sprintf("RDATE;VALUE=DATE:");
} else {
if (defined($ical_tzid)) {
if ($ical_tzid eq '') { # tz is defined but empty, so in GMT
$v->{i_rdate} = sprintf("RDATE:");
} else { # tz is non-zero, so output the tz as well
$v->{i_rdate} = sprintf("RDATE;TZID=%s:", $ical_tzid);
}
} else { # undefined tz, just floating time
$v->{i_rdate} = sprintf("RDATE:");
}
}
# now stick the recur_str onto the end
$v->{i_rdate} .= $v->{recur_str};
# if we ever get memory tight, we can probably undef($v->{recur_str})
}
foreach $v (@events) {
# for recurrant events, skip those that arnt the "head"
next if ($v->{is_recurrance} and (not $v->{recurlist}));
if (${$v->{sf}}[4] eq "*") { # no time was given
$v->{i_dtstart} = sprintf("DTSTART:%s", $v->{dts});
} else {
if (defined($ical_tzid)) {
if ($ical_tzid eq '') { # tz is defined but empty, so in GMT
$v->{i_dtstart} = sprintf("DTSTART:%sZ", $v->{dts});
} else { # tz is non-zero, so output the tz as well
$v->{i_dtstart} = sprintf("DTSTART;TZID=%s:%s",
$ical_tzid, $v->{dts});
}
} else { # undefined tz, just floating time
$v->{i_dtstart} = sprintf("DTSTART:%s", $v->{dts});
}
}
if (${$v->{sf}}[3] ne "*") { # a duration was given
# It's convienient that RFC2445 defines DURATION, thus we
# don't need to calculate DTEND, with awkward figuring out
# crossing hours, days, months, year, etc. Instead we
# will let the iCalendar consuming application worry about it.
$v->{i_duration} = sprintf("PT%dM", ${$v->{sf}}[3]);
}
}
# output header
print "BEGIN:VCALENDAR\015\012"
. "VERSION:2.0\015\012"
. "PRODID:http://mark.atwood.name/code/rem2ics"
. " $app_name $app_version\015\012";
# output each vevent
foreach $v (@events) {
# for recurrant events, only output the "head", skip the others
next if ($v->{is_recurrance} and (not $v->{recurlist}));
print "BEGIN:VEVENT\015\012";
my $tag = ${$v->{sf}}[2];
# if $tag is not set, fake up a UID from start time, process id & input line count
if ($tag eq "*" || !$options{usetag}) {
$tag = sprintf("%x.%x.%x", $^T, $$, $v->{cnt});
}
# add rem2ics and hostname to UID
print &lineify(sprintf("UID:rem2ics.%s@%s",
$tag, $ical_uid_hostname));
print &lineify("SUMMARY:" . &quotify(${$v->{sf}}[5]));
print &lineify($v->{i_dtstart});
print &lineify("DURATION:" . $v->{i_duration})
if ($v->{i_duration});
print &lineify($v->{i_rdate})
if ($v->{i_rdate});
print &lineify("DTSTAMP:" . $ical_dtstamp);
print &lineify("COMMENT: generated by $app_name $app_version\\n"
. " http://mark.atwood.name/code/rem2ics\\n"
. " data[" . $v->{cnt} . "]=|" . &quotify($v->{src}) . "|");
print "END:VEVENT\015\012";
}
# output trailer
print "END:VCALENDAR\015\012";
# integer division, return both quotient and remainder
sub idiv {
my $n = shift; my $d = shift;
my $r = $n; my $q = 0;
while ($r >= $d) {
$r = $r - $d;
$q = $q + 1;
}
return ($q, $r);
}
# todo, perl5 version that defines ()*, need to specify a requires up top
sub lineify {
return join("\015\012 ", unpack('(A72)*', shift)) . "\015\012";
}
sub quotify {
my $s = shift;
return $s if $s =~ m/^(\w| )*$/;
$s =~ s/\\/\\\\/gso;
$s =~ s/\n/\\n/gso;
$s =~ s/\s/ /gso;
$s =~ s/\"/\\"/gso;
$s =~ s/\,/\\,/gso;
$s =~ s/\:/\\:/gso;
$s =~ s/\;/\\;/gso;
return $s;
}
__END__
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Lesser General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
EOF

View File

@@ -0,0 +1,50 @@
Name: rem2ics
Version: 0.93
Release: 1%{?dist}
Summary: Converts the output of "remind -s" into RFC2445 iCalendar format
Group: Applications/Productivity
License: GPLv2+
URL: http://mark.atwood.name/code/rem2ics/
Source0: http://mark.atwood.name/code/rem2ics/rem2ics-%{version}.tar.gz
Source1: rem2ics-Makefile
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
BuildArch: noarch
BuildRequires: perl
%description
rem2ics converts the output of "remind -s" into RFC2445 iCalendar format.
You may want to install remind if you install this package.
%prep
%setup -q -c
cp -a %SOURCE1 Makefile
%build
make %{?_smp_mflags}
%install
rm -rf $RPM_BUILD_ROOT
mkdir $RPM_BUILD_ROOT
make install DESTDIR=$RPM_BUILD_ROOT
%clean
rm -rf $RPM_BUILD_ROOT
%files
%defattr(-,root,root,-)
%doc
%{_bindir}/rem2ics
%{_mandir}/man1/rem2ics.1*
%changelog
* Tue Mar 25 2008 Till Maas <opensource till name> - 0.92-1
- initial spec for Fedora

View File

@@ -0,0 +1,56 @@
;;; setup for remind autocompletion (totally optional)
;; put something like
;; (add-hook 'remind-conf-mode '(load-library "ac-remind")) in your .emacs file.
(require 'auto-complete)
(define-key ac-complete-mode-map "\r" nil)
(defvar ac-remind-keywords
'((candidates
. (lambda ()
(all-completions ac-target remind-keywords ))))
"Source for remind-conf completion keywords.")
(defvar ac-remind-time-words
'((candidates
. (lambda ()
(all-completions ac-target remind-time-words))))
"Source for remind-conf time words completions.")
(defvar ac-remind-builtin-variables
'((candidates
. (lambda ()
(all-completions ac-target remind-builtin-variables))))
"Source for remind-conf builtin variables.")
(defvar ac-remind-type-keywords
'((candidates
. (lambda ()
(all-completions ac-target remind-type-keywords))))
"Source for remind-conf type keywords.")
(defvar ac-remind-builtin-functions
'((candidates
. (lambda ()
(all-completions ac-target remind-builtin-functions))))
"Source for remind-conf completion builtin functions.")
(add-hook 'remind-conf-mode-hook
(lambda () "Makes auto-completion work in remind-conf-mode"
(make-local-variable 'ac-sources)
(setq ac-sources '(ac-remind-keywords
ac-remind-builtin-variables
ac-remind-builtin-functions
ac-remind-type-keywords
ac-remind-time-words
ac-source-abbrev))
(auto-complete-mode 1)))
(provide 'ac-remind)
;; (define-skeleton ac-look
;; ""
;; (skeleton-read "well? ")
;; "(when (looking-at (regexp-opt remind-" str " 'words))" \n
;; >"(setq ac-sources '(ac-remind-" str ")))"
;; )

View File

@@ -0,0 +1,444 @@
;;; remind-conf-mode.el --- A mode to help configure remind.
;; Copyright (C) 2008 Shelagh Manton <shelagh.manton@gmail.com>
;; Author: Shelagh Manton <shelagh.manton@gmail.com> with help from
;; Dianne Skoll
;; Keywords: remind configure mode
;; Version: .04
;; This program is free software; you can redistribute it and/or
;; modify it under the terms of the GNU General Public License
;; as published by the Free Software Foundation; either version 2
;; of the License, or (at your option) any later version.
;; This program is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
;; GNU General Public License for more details.
;; You should have received a copy of the GNU General Public License
;; along with this program; if not, write to the Free Software
;; Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
;; 02111-1307, USA.
;;; Commentary:
;; Use this mode to help with the configuration of remind configuration files.
;; Put (require 'remind-conf-mode) in your .emacs file
;; or (autoload 'remind-conf-mode "remind-conf-mode" "Mode to help with remind files" t)
;; also put (add-to-list 'auto-mode-alist '("\\.rem\\'" . remind-conf-mode)) and
;; (setq auto-mode-alist
;; (cons '(".reminders$" . remind-conf-mode) auto-mode-alist))
;; if you want to have the mode work automatically when you open a remind configuration file.
;; If you want to use the auto-complete stuff, you will need to download and install the
;; auto-complete library from http://www.cx4a.org/pub/auto-complete.el and put
;; (require 'auto-complete) in your emacs with
;; (add-hook 'remind-conf-mode-hook
;; (lambda ()
;; (make-local-variable 'ac-sources)
;; (setq ac-sources '(ac-remind-conf ac-remind-builtin-variables ac-remind-builtin-functions))
;; (auto-complete t)))
;; in your .emacs file
;; PS. you could add ac-source-abbrev ac-source-words-in-buffer to have abbrevs and
;; other words in buffer auto-complete too
;;; History:
;; Thu, Feb 14, 2008
;; Based mode on wpld-mode tutorial and sample-mode on emacs wiki.
;; Ideas from mupad.el for font-lock styles.
;; Mon, Jan 26, 2008
;; Added rem-setup-colors to make it easy for colourised remind output.
;; Added a demo skeleton for people to copy for easy entry of coloured remind entries.
;; tried to hook in the auto-complete library so that all known functions and keywords can be easily entered.
;; EXPERIMENTAL, but seems to work well here (emacs cvs).
;; Seems to work without case folding which is nice. wonder why it didn't yesterday?
;;; Code:
(require 'font-lock); this goes in the define-derived-mode part.
(when (featurep 'xemacs)
(require 'overlay)) ;I wonder if this will help with font-lock and xemacs?
(defgroup remind-conf nil
"Options for remind-conf-mode."
:group 'remind-conf
:prefix "remind-conf-")
(defvar remind-conf-mode-hook nil
"Hook to run in `remind-conf-mode'.")
;; keymap
(defvar remind-conf-mode-map
(let ((remind-conf-mode-map (make-sparse-keymap)))
remind-conf-mode-map)
"Keymap for `remind-conf-mode'.")
(define-key remind-conf-mode-map "\C-cr" 'rem-skel)
(define-key remind-conf-mode-map "\C-ct" 'rem-today)
(define-key remind-conf-mode-map "\C-cd" 'rem-today-skel)
(define-key remind-conf-mode-map "\C-cw" 'rem-week-away)
(define-key remind-conf-mode-map "\C-cx" 'rem-tomorrow)
(define-key remind-conf-mode-map "\C-ca" 'rem-days-away)
(define-key remind-conf-mode-map "\M-j" 'remind-indent-line)
(define-key remind-conf-mode-map (kbd "RET") 'remind-indent-line)
(define-key remind-conf-mode-map "\C-c\C-c" 'rem-save-file)
;; syntax-table
(defvar remind-conf-syntax-table
(let ((remind-conf-syntax-table (make-syntax-table text-mode-syntax-table)))
(modify-syntax-entry ?\; ". 1b" remind-conf-syntax-table)
(modify-syntax-entry ?\# ". 1b" remind-conf-syntax-table)
(modify-syntax-entry ?\n "> b" remind-conf-syntax-table)
;Names with _ are still one word.
(modify-syntax-entry ?_ "w" remind-conf-syntax-table)
(modify-syntax-entry ?. "w" remind-conf-syntax-table)
remind-conf-syntax-table)
"Syntax table for `remind-conf-mode'.")
;;; keyword sets
(defconst remind-keywords
(sort
(list "RUN" "REM" "ONCE" "SATISFY" "BEFORE" "UNSET" "OMIT"
"OMIT" "DATE" "SKIP" "ONCE" "AFTER" "WARN" "PRIORITY" "AT" "SCHED" "IF" "ELSE" "ENDIF"
"WARN" "UNTIL" "THROUGH" "SCANFROM" "DURATION" "TAG" "MSG" "MSF" "CAL" "SPECIAL" "IFTRIG"
"PS" "PSFILE" "BANNER" "INCLUDE" "PUSH-OMIT-CONTEXT" "DEBUG" "DUMPVARS"
"CLEAR-OMIT-CONTEXT" "POP-OMIT-CONTEXT" "SET" "ERRMSG" "FSET"
"EXIT" "FLUSH" "PRESERVE" "MOON" "COLOR" "COLOUR")
#'(lambda (a b) (> (length a) (length b)))))
(defconst remind-type-keywords
(sort
(list "INT" "STRING" "TIME" "DATE" "SHADE")
#'(lambda (a b) (> (length a) (length b)))))
(defconst remind-builtin-variables
(sort
(list "$CalcUTC" "$CalMode" "$DefaultPrio" "$EndSent" "$EndSentIg" "$NumTrig"
"$FirstIndent" "$FoldYear" "$FormWidth" "$MinsFromUTC" "$LatDeg" "$LatMin" "$LatSec"
"$Location" "$LongDeg" "$LongMin" "$LongSec" "$MaxSatIter" "$SubsIndent")
#'(lambda (a b) (> (length a) (length b)))))
(defconst remind-time-words
(sort
(list "Jan" "January" "Feb" "Mar" "Apr" "Jun" "Jul" "Aug" "Sept" "Sep" "Oct" "Nov" "Dec" "February" "March" "April" "May" "June" "July" "August" "September" "October" "November" "December" "Mon" "Monday" "Tue" "Tues" "Tuesday" "Wed" "Wednesday" "Thu" "Thursday" "Fri" "Friday" "Saturday" "Sat" "Sun" "Sunday")
#'(lambda (a b) (> (length a) (length b)))))
(defconst remind-builtin-functions
(sort
(list "abs" "access" "shell" "args" "asc" "baseyr" "char" "choose" "coerce" "date"
"dawn" "today" "day" "daysinmon" "defined" "dosubst" "dusk" "easterdate" "easter"
"filedir" "filename" "getenv" "hour" "iif" "trigger" "index" "isdst" "isleap"
"isomitted" "hebdate" "hebday" "hebmon" "hebyear" "language" "ord" "thisyear"
"sunrise" "sunset" "lower" "max" "min" "minute" "mon" "moondate" "moontime"
"moonphase" "now" "ostype" "plural" "realnow" "realtoday" "sgn" "strlen" "psshade"
"substr" "trigdate" "trigger" "trigtime" "trigvalid" "typeof" "upper" "psmoon"
"value" "version" "wkday" "wkdaynum" "msgprefix" "msgsuffix" "year")
#'(lambda (a b) (> (length a) (length b)))))
;;; faces
;;example of setting up special faces for a mode.
(defvar remind-conf-command-face 'remind-conf-command-face
"Remind commands.")
(defface remind-conf-command-face
'((t :foreground "SeaGreen4" :bold t))
"Font Lock mode face used to highlight commands."
:group 'remind-conf)
(defvar remind-conf-keyword-face 'remind-conf-keyword-face
"Remind keywords.")
(defface remind-conf-keyword-face
'((t :foreground "blue violet"))
"Font Lock mode face used to highlight keywords."
:group 'remind-conf)
(defvar remind-conf-substitutes-face 'remind-conf-substitutes-face
"Remind substitutes.")
(defface remind-conf-substitutes-face
'((t :foreground "blue2"))
"Font Lock mode face used to highlight substitutes."
:group 'remind-conf)
(defvar remind-conf-endline-face 'remind-conf-endline-face
"Remind endline.")
(defface remind-conf-endline-face
'((t :foreground "goldenrod2" :bold t))
"Font Lock mode face used to highlight commands."
:group 'remind-conf)
(defvar remind-conf-variable-face 'remind-conf-variable-face
"Remind variable.")
(defface remind-conf-variable-face
'((t :foreground "DeepPink2" :bold t))
"Font Lock mode face used to highlight commands."
:group 'remind-conf)
(defvar remind-conf-color-face 'remind-conf-color-face
"Remind color variables.")
(defface remind-conf-color-face
'((t :foreground "gold" :bold t))
"Font Lock mode face used to highlight color changes."
:group 'remind-conf)
(defvar remind-conf-delta-face 'remind-conf-delta-face
"Remind deltas.")
(defface remind-conf-delta-face
'((t :foreground "sandy brown" :bold t))
"Font Lock mode face used to highlight deltas."
:group 'remind-conf)
(defvar remind-comment-face 'remind-comment-face
"Remind comments.")
(defface remind-comment-face
'((t :foreground "brown"))
"Font-lock face for highlighting comments."
:group 'remind-conf)
(defvar remind-string-face 'remind-string-face
"Remind strings.")
(defface remind-string-face
'((t :foreground "tomato"))
"Font lock mode face used to highlight strings."
:group 'remind-conf)
(defvar remind-time-face 'remind-time-face
"Remind time words.")
(defface remind-time-face
'((t :foreground "LightSeaGreen" :bold t))
"Font lock mode face to highlight time phrases."
:group 'remind-conf)
(defvar remind-conf-type-face 'remind-conf-type-face
"Remind type keywords.")
(defface remind-conf-type-face
'((t :foreground "orange" :bold t))
"Font lock mode face to highlight type keywords."
:group 'remind-conf)
(defcustom rem-post-save-function ""
"Name of shell function that can be run when you save and close a remind file.
If you put a & after the name of the function, it will run asyncronously. This might
be useful if the process takes a long time."
:type 'string
:group 'remind-conf
)
;; keywords
(defconst remind-conf-font-lock-keywords-1
(list
'("^[\;\#]\\s-+.*$" . remind-comment-face)
(cons (regexp-opt remind-keywords 'words) remind-conf-keyword-face)
'("%[\"_]" . font-lock-warning-face)
'("\\(%[a-mops-w]\\)" . remind-conf-substitutes-face)
'("\"[^\"]*\"" . remind-string-face))
"Minimal font-locking for `remind-conf-mode'.")
(defconst remind-conf-font-lock-keywords-2
(append remind-conf-font-lock-keywords-1
(list
(cons (regexp-opt remind-time-words 'words) remind-time-face)
(cons (regexp-opt remind-builtin-functions 'words) remind-conf-command-face)
'("%$" . remind-conf-endline-face)))
"Additional commands to highlight in `remind-conf-mode'.")
(defconst remind-conf-font-lock-keywords-3
(append remind-conf-font-lock-keywords-2
(list
(cons (regexp-opt remind-type-keywords 'words) remind-conf-type-face)
'("\[[a-zA-Z]\\{3,6\\}\]" . remind-conf-color-face)
'("\\s-+\\([12][0-9]\\|3[01]\\|0?[0-9]\\)\\s-+" . remind-conf-substitutes-face);better date regexp
'("\\s-+\\(\\(?:20\\|19\\)[0-9][0-9]\\)\\s-+" . remind-conf-substitutes-face);years
'("\\s-+\\(2[0-4]\\|[01]?[0-9][.:][0-5][0-9]\\)\\s-+" . remind-conf-substitutes-face);24hour clock, more precise
'("\\s-+\\([+-][+-]?[1-9][0-9]*\\)\\s-+" 1 remind-conf-delta-face prepend)
(cons (regexp-opt remind-builtin-variables 'words) remind-conf-variable-face)))
"The ultimate in highlighting experiences for `remind-conf-mode'.")
(defcustom remind-conf-font-lock-keywords 'remind-conf-font-lock-keywords-3
"Font-lock highlighting level for `remind-conf-mode'."
:group 'remind-conf
:type '(choice (const :tag "Barest minimum of highlighting." remind-conf-font-lock-keywords-1)
(const :tag "Medium highlighting." remind-conf-font-lock-keywords-2)
(const :tag "Highlighting deluxe." remind-conf-font-lock-keywords-3)))
;;; Indentation (I'm sure this could be made more simple. But at least it works.)
(defcustom remind-indent-level 4
"User definable indentation."
:group 'remind-conf
:type '(integer)
)
(defun remind-indent-line ()
"Indent current line for remind configuration files."
(interactive)
(forward-line 0) ;remember this happens on every line as it is done per line basis
(if (bobp)
(indent-line-to 0)
(let ((not-indented t) cur-indent)
(if (looking-at "^[ \t]*\\<\\(ENDIF\\|POP\\(?:-OMIT-CONTEXT\\)?\\)\\>")
(progn
(save-excursion
(forward-line -1)
(setq cur-indent (- (current-indentation) remind-indent-level))) ;note that not-indented is still t
(if (< cur-indent 0) (setq cur-indent 0)))
(save-excursion
(while not-indented
(forward-line -1)
(if (looking-at "^[ \t]*\\<\\(ENDIF\\|POP\\(?:-OMIT-CONTEXT\\)?\\)\\>")
(progn
(setq cur-indent 0)
(delete-horizontal-space) ;don't know why I need this when other similar indent functions don't.
(setq not-indented nil))
(if (looking-at "\\<\\(IF\\(?:TRIG\\)?\\|PUSH\\(?:-OMIT-CONTEXT\\)?\\)\\>")
(progn
(setq cur-indent remind-indent-level)
(setq not-indented nil))
(if (bobp)
(setq not-indented nil))))))
(if cur-indent
(indent-line-to cur-indent)
(indent-line-to 0))))))
;;; Convenience functions
(define-skeleton rem-skel
"Skeleton to insert a rem line in a remind configuration file."
nil
"REM "(skeleton-read "Date? " )
("Optional: How many days ahead? " " +" str )
resume:
("Optional: At what time? Format eg 13:00. " " AT " str)
resume:
("Optional: How many minutes ahead? " " +" str )
resume:
("Optional: At what priority? eg 0-9999" " PRIORITY " str )
resume:
" MSG %\"" (skeleton-read "Your message? " )"%b%\"%" \n
)
(define-skeleton rem-today-skel
"Skeleton to insert a line for today's date."
nil
"REM " (format-time-string "%d %b %Y")
("Optional: At what time? Format eg 13:20. " " AT " str)
resume:
("Optional: How many minutes ahead? " " +" str )
resume:
("Optional: At what priority? eg 0-9999" " PRIORITY " str )
resume:
" MSG " (skeleton-read "Your message? " )"%b.%" \n
)
(defun rem-today ()
"Insert the date for today in a remind friendly style."
(interactive)
(insert (format-time-string "%e %b %Y")))
(defun rem-tomorrow ()
"Insert tomorrow's date in a remind friendly style."
(interactive)
(insert (format-time-string "%e %b %Y" (time-add (current-time) (days-to-time 1)))))
(defun rem-days-away (arg)
"Insert a day N number of days in the future.
Takes a prefix argument, but defaults to 4."
(interactive "nHow many Days?: ")
(insert (format-time-string "%e %b %Y" (time-add (current-time) (days-to-time arg)))))
(defun rem-week-away ()
"Insert a day 7 days in the future."
(interactive)
(insert (format-time-string "%e %b %Y" (time-add (current-time) (days-to-time 7)))))
(setq skeleton-end-hook nil) ; so the skeletons will not automatically go to a new line.
;;; private function
;; could make it useful for others. Put somethin like the following in your .emacs
;(setq rem-post-save-function "~/bin/dailypic &")
(defun rem-save-file ()
"Save the file and start the shell function in one go.
This function will close the window after running. It needs the
variable `rem-post-save-function' to be set. It will be most
useful to people who have some sort of function they run to use
remind data ie procucing calendars."
(interactive)
(if (boundp 'rem-post-save-function)
(progn (save-buffer)
(shell-command rem-post-save-function)
(kill-buffer-and-window))
(error "`rem-post-save-function' variable is not set")))
(defun rem-setup-colors ()
"Insert set of variables for coloured output in remind messages."
(interactive)
(find-file (expand-file-name "~/.reminders"))
(goto-char 0) ;we do want it somewhere near the top of the file.
(save-excursion
(re-search-forward "\n\n"); squeeze it in where you have a free line.
(insert "\nSET Esc CHAR(27)
SET Nrm Esc + \"[0m\"
SET Blk Esc + \"[0;30m\"
SET Red Esc + \"[0;31m\"
SET Grn Esc + \"[0;32m\"
SET Ylw Esc + \"[0;33m\"
SET Blu Esc + \"[0;34m\"
SET Mag Esc + \"[0;35m\"
SET Cyn Esc + \"[0;36m\"
SET Wht Esc + \"[0;37m\"
SET Gry Esc + \"[30;1m\"
SET BrRed Esc + \"[31;1m\"
SET BrGrn Esc + \"[32;1m\"
SET BrYlw Esc + \"[33;1m\"
SET BrBlu Esc + \"[34;1m\"
SET BrMag Esc + \"[35;1m\"
SET BrCyn Esc + \"[36;1m\"
SET BrWht Esc + \"[37;1m\" \n \n")))
;; So now you can do things like:
(define-skeleton birthcol
"Make birthdays magenta.
Acts on the region or places point where it needs to be."
nil
"[Mag]" _ " [Nrm]")
;; finally the derived mode.
;;;###autoload
(define-derived-mode remind-conf-mode text-mode "REM"
"Major mode for editing remind calendar configuration files.
\\{remind-conf-mode-map}"
:syntax-table remind-conf-syntax-table
(set (make-local-variable 'font-lock-keywords-case-fold-search) t) ;this is not working atm 2009-04-13
(set (make-local-variable 'font-lock-defaults) '(remind-conf-font-lock-keywords))
(set (make-local-variable 'comment-start) ";")
(set (make-local-variable 'comment-start) "#")
(set (make-local-variable 'comment-end) "\n")
(set (make-local-variable 'fill-column) '100);cause I was having problems with autofill.
(set (make-local-variable 'indent-line-function) 'remind-indent-line)
(use-local-map remind-conf-mode-map)
)
(provide 'remind-conf-mode)
;;; remind-conf-mode.el ends here
;;; Indentation code
;;; work out how to make the syntax highlighting work only before the (MSG|MSF)
;;; keywords and not after.
;;; for my own use. keymap to save file and do dailypic C-c C-c in time honoured tradition?

104
docs/README.UNIX Normal file
View File

@@ -0,0 +1,104 @@
REMIND version 3.2 for UNIX
REMIND is a sophisticated alarm/calendar program. Details are given
in the man page, "remind.1".
INSTALLING REMIND:
-----------------
If you have Tcl/Tk (wish 4.1 or higher) installed and are running X11:
----------------------------------------------------------------------
1) Type: wish ./build.tk from the top-level Remind directory.
Fill in the various options and hit "Build Remind"
2) Type: "make install" -- you may need to be root to do this.
If you do NOT have Tcl/Tk or are NOT running X11:
-------------------------------------------------
1) Edit the file "src/custom.h" according to your preferences.
2) Edit the file "src/lang.h" to choose a language.
3) Type: "make"
4) Type: "make install" -- you may need to be root to do this.
The subdirectory "www" contains scripts for making a nice calendar
web server. See the files README and Makefile in that directory.
The file "examples/defs.rem" has some sample Remind definitions and
commands, as well as U.S. and Jewish holidays.
OTHER LANGUAGE SUPPORT
Remind has support for languages other than English. See the file
"src/lang.h" for details. The language support may vary - you can change
only the substitution filter, or you can translate all of the usage
instructions and error messages as well. See "src/langs/french.h" for an
example of the latter.
To compile Remind for a non-english language, look at the constants
defined in "src/lang.h". Then, to compile Remind for Italian (as an
example), type:
make "LANGDEF=-DLANG=ITALIAN"
If you add support for a non-English language, Remind will accept both the
English and non-English names of months and weekdays in an input script.
However, you should not rely on this feature if you want to write portable
Remind scripts.
At a minimum, you should support month and day names in the foreign
language, and should modify the substitution filter appropriately.
If you are truly diligent, you can translate usage and error messages
too.
Take a look at the files "src/langs/english.h" and
"src/langs/german.h" if you want to add support for your favourite
language. If you do add another language to Remind, please let me
know! Here are the basic guidelines:
- Your language file should be called "src/langs/lxxx.h", where lxxx
is the first 8 characters of the ENGLISH name of your language.
- Your language file should define L_LANGNAME to be the full English
name of your language, with the first letter capitalized and the rest
lower-case.
- You can test your language file with the script "tests/tstlang.rem"
RELEASE NOTES -- miscellaneous info that couldn't go anywhere else!
1. POPUP REMINDERS
If you're running under X11 and you have the Tcl tools, you can create
simple pop-up reminders by creating the following Tcl script called
'popup'. It pops a message on to the screen and waits for you to
press the 'OK' button. If you don't press the OK button within 15
seconds, it exits anyway. To use it, you can use the '-k' option for
Remind as follows:
remind "-kpopup '%s'&" .reminders
Or use the following in your Remind script:
REM AT 17:00 RUN popup 'Time to go home.' &
This Tcl script is a slightly modified version of one submitted by
Norman Walsh.
-------------- Cut Here ---------- Cut Here ---------- Cut Here -------------
#!/usr/local/bin/wish
wm withdraw .
after 15000 { destroy . ; exit }
tk_dialog .d { Message } $argv warning 0 { OK }
destroy .
exit
-------------- Cut Here ---------- Cut Here ---------- Cut Here -------------
--
Dianne Skoll <dianne@skoll.ca>
https://dianne.skoll.ca/projects/remind/

1584
docs/WHATSNEW Normal file

File diff suppressed because it is too large Load Diff

880
dorem.c
View File

@@ -1,880 +0,0 @@
/***************************************************************/
/* */
/* DOREM.C */
/* */
/* Contains routines for parsing reminders and evaluating */
/* triggers. Also contains routines for parsing OMIT */
/* commands. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: dorem.c,v 1.3 1996-04-28 02:01:54 dfs Exp $";
#include "config.h"
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#include "globals.h"
#include "err.h"
#include "types.h"
#include "protos.h"
#include "expr.h"
/* Define the shell characters to escape */
static char const EscapeMe[] =
#ifdef QDOS
"\"'!$%^&*()|<>[]{}\x9F~;?\\";
#else
"\"'!$%^&*()|<>[]{}`~;?\\";
#endif
PRIVATE int ParseTimeTrig ARGS ((ParsePtr s, TimeTrig *tim));
PRIVATE int ParseLocalOmit ARGS ((ParsePtr s, Trigger *t));
PRIVATE int ParseScanFrom ARGS ((ParsePtr s, Trigger *t));
PRIVATE int ParsePriority ARGS ((ParsePtr s, Trigger *t));
PRIVATE int ParseUntil ARGS ((ParsePtr s, Trigger *t));
PRIVATE int ShouldTriggerBasedOnWarn ARGS ((Trigger *t, int jul));
/***************************************************************/
/* */
/* DoRem */
/* */
/* Do the REM command. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int DoRem(ParsePtr p)
#else
int DoRem(p)
ParsePtr p;
#endif
{
Trigger trig;
TimeTrig tim;
int r;
int jul;
char buf[TOKSIZE];
Token tok;
/* Parse the trigger date and time */
if ( (r=ParseRem(p, &trig, &tim)) ) return r;
if (trig.typ == NO_TYPE) return E_EOLN;
if (trig.typ == SAT_TYPE) {
r=DoSatRemind(&trig, &tim, p);
if (r) return r;
r=ParseToken(p, buf);
if (r) return r;
FindToken(buf, &tok);
if (tok.type == T_Empty || tok.type == T_Comment) return OK;
if (tok.type != T_RemType || tok.val == SAT_TYPE) return E_PARSE_ERR;
trig.typ = tok.val;
jul = LastTriggerDate;
if (!LastTrigValid) return OK;
} else {
/* Calculate the trigger date */
jul = ComputeTrigger(trig.scanfrom, &trig, &r);
if (r) return r;
}
/* Queue the reminder, if necessary */
#ifdef HAVE_QUEUED
if (jul == JulianToday &&
!(!IgnoreOnce &&
trig.once != NO_ONCE &&
FileAccessDate == JulianToday))
QueueReminder(p, trig.typ, &tim, trig.sched);
/* If we're in daemon mode, do nothing over here */
if (Daemon) return OK;
#endif
if (ShouldTriggerReminder(&trig, &tim, jul)) {
#ifdef OS2_POPUP
if ( (r=TriggerReminder(p, &trig, &tim, jul, 0)) ) {
#else
if ( (r=TriggerReminder(p, &trig, &tim, jul)) ) {
#endif
return r;
}
}
return OK;
}
/***************************************************************/
/* */
/* ParseRem */
/* */
/* Given a parse pointer, parse line and fill in a */
/* trigger structure. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int ParseRem(ParsePtr s, Trigger *trig, TimeTrig *tim)
#else
int ParseRem(s, trig, tim)
ParsePtr s;
Trigger *trig;
TimeTrig *tim;
#endif
{
register int r;
Token tok;
trig->y = NO_YR;
trig->m = NO_MON;
trig->d = NO_DAY;
trig->wd = NO_WD;
trig->back = NO_BACK;
trig->delta = NO_DELTA;
trig->until = NO_UNTIL;
trig->rep = NO_REP;
trig->localomit = NO_WD;
trig->skip = NO_SKIP;
trig->once = NO_ONCE;
trig->typ = NO_TYPE;
trig->scanfrom = NO_DATE;
trig->priority = DefaultPrio;
trig->sched[0] = 0;
trig->warn[0] = 0;
tim->ttime = NO_TIME;
tim->delta = NO_DELTA;
tim->rep = NO_REP;
while(1) {
/* Read space-delimited string */
r = ParseToken(s, TokBuffer);
if (r) return r;
/* Figure out what we've got */
FindToken(TokBuffer, &tok);
switch(tok.type) {
case T_WkDay:
if (trig->wd & (1 << tok.val)) return E_WD_TWICE;
trig->wd |= (1 << tok.val);
break;
case T_Month:
if (trig->m != NO_MON) return E_MON_TWICE;
trig->m = tok.val;
break;
case T_Skip:
if (trig->skip != NO_SKIP) return E_SKIP_ERR;
trig->skip = tok.val;
break;
case T_Priority:
r=ParsePriority(s, trig);
if (r) return r;
break;
case T_At:
r=ParseTimeTrig(s, tim);
if (r) return r;
break;
case T_Scanfrom:
r=ParseScanFrom(s, trig);
if (r) return r;
break;
case T_RemType:
trig->typ = tok.val;
if (s->isnested) return E_CANT_NEST_RTYPE;
if (trig->scanfrom == NO_DATE) trig->scanfrom = JulianToday;
return OK;
case T_Until:
r=ParseUntil(s, trig);
if (r) return r;
break;
case T_Year:
if (trig->y != NO_YR) return E_YR_TWICE;
trig->y = tok.val;
break;
case T_Day:
if (trig->d != NO_DAY) return E_DAY_TWICE;
trig->d = tok.val;
break;
case T_Rep:
if (trig->rep != NO_REP) return E_REP_TWICE;
trig->rep = tok.val;
break;
case T_Delta:
if (trig->delta != NO_DELTA) return E_DELTA_TWICE;
trig->delta = tok.val;
break;
case T_Back:
if (trig->back != NO_BACK) return E_BACK_TWICE;
trig->back = tok.val;
break;
case T_Once:
if (trig->once != NO_ONCE) return E_ONCE_TWICE;
trig->once = ONCE_ONCE;
break;
case T_Omit:
r = ParseLocalOmit(s, trig);
if (r) return r;
break;
case T_Empty:
if (trig->scanfrom == NO_DATE) trig->scanfrom = JulianToday;
return OK;
case T_Warn:
r=ParseToken(s, TokBuffer);
if(r) return r;
StrnCpy(trig->warn, TokBuffer, VAR_NAME_LEN);
break;
case T_Sched:
r=ParseToken(s, TokBuffer);
if(r) return r;
StrnCpy(trig->sched, TokBuffer, VAR_NAME_LEN);
break;
default:
Eprint("%s: %s", ErrMsg[E_UNKNOWN_TOKEN], TokBuffer);
return E_UNKNOWN_TOKEN;
}
}
}
/***************************************************************/
/* */
/* ParseTimeTrig - parse the AT part of a timed reminder */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ParseTimeTrig(ParsePtr s, TimeTrig *tim)
#else
static int ParseTimeTrig(s, tim)
ParsePtr s;
TimeTrig *tim;
#endif
{
Token tok;
int r;
while(1) {
r = ParseToken(s, TokBuffer);
if (r) return r;
FindToken(TokBuffer, &tok);
switch(tok.type) {
case T_Time:
tim->ttime = tok.val;
break;
case T_Delta:
tim->delta = (tok.val > 0) ? tok.val : -tok.val;
break;
case T_Rep:
tim->rep = tok.val;
break;
default:
if (tim->ttime == NO_TIME) return E_EXPECT_TIME;
/* Save in global variable */
LastTriggerTime = tim->ttime;
PushToken(TokBuffer);
return OK;
}
}
}
/***************************************************************/
/* */
/* ParseLocalOmit - parse the local OMIT portion of a */
/* reminder. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ParseLocalOmit(ParsePtr s, Trigger *t)
#else
static int ParseLocalOmit(s, t)
ParsePtr s;
Trigger *t;
#endif
{
Token tok;
int r;
while(1) {
r = ParseToken(s, TokBuffer);
if (r) return r;
FindToken(TokBuffer, &tok);
switch(tok.type) {
case T_WkDay:
t->localomit |= (1 << tok.val);
break;
default:
PushToken(TokBuffer);
return OK;
}
}
}
/***************************************************************/
/* */
/* ParseUntil - parse the UNTIL portion of a reminder */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ParseUntil(ParsePtr s, Trigger *t)
#else
static int ParseUntil(s, t)
ParsePtr s;
Trigger *t;
#endif
{
int y = NO_YR,
m = NO_MON,
d = NO_DAY;
Token tok;
int r;
if (t->until != NO_UNTIL) return E_UNTIL_TWICE;
while(1) {
r = ParseToken(s, TokBuffer);
if (r) return r;
FindToken(TokBuffer, &tok);
switch(tok.type) {
case T_Year:
if (y != NO_YR) {
Eprint("UNTIL: %s", ErrMsg[E_YR_TWICE]);
return E_YR_TWICE;
}
y = tok.val;
break;
case T_Month:
if (m != NO_MON) {
Eprint("UNTIL: %s", ErrMsg[E_MON_TWICE]);
return E_MON_TWICE;
}
m = tok.val;
break;
case T_Day:
if (d != NO_DAY) {
Eprint("UNTIL: %s", ErrMsg[E_DAY_TWICE]);
return E_DAY_TWICE;
}
d = tok.val;
break;
default:
if (y == NO_YR || m == NO_MON || d == NO_DAY) {
Eprint("UNTIL: %s", ErrMsg[E_INCOMPLETE]);
return E_INCOMPLETE;
}
if (!DateOK(y, m, d)) return E_BAD_DATE;
t->until = Julian(y, m, d);
PushToken(TokBuffer);
return OK;
}
}
}
/***************************************************************/
/* */
/* ParseScanFrom - parse the SCANFROM portion of a reminder */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ParseScanFrom(ParsePtr s, Trigger *t)
#else
static int ParseScanFrom(s, t)
ParsePtr s;
Trigger *t;
#endif
{
int y = NO_YR,
m = NO_MON,
d = NO_DAY;
Token tok;
int r;
if (t->scanfrom != NO_DATE) return E_SCAN_TWICE;
while(1) {
r = ParseToken(s, TokBuffer);
if (r) return r;
FindToken(TokBuffer, &tok);
switch(tok.type) {
case T_Year:
if (y != NO_YR) {
Eprint("SCANFROM: %s", ErrMsg[E_YR_TWICE]);
return E_YR_TWICE;
}
y = tok.val;
break;
case T_Month:
if (m != NO_MON) {
Eprint("SCANFROM: %s", ErrMsg[E_MON_TWICE]);
return E_MON_TWICE;
}
m = tok.val;
break;
case T_Day:
if (d != NO_DAY) {
Eprint("SCANFROM: %s", ErrMsg[E_DAY_TWICE]);
return E_DAY_TWICE;
}
d = tok.val;
break;
default:
if (y == NO_YR || m == NO_MON || d == NO_DAY) {
Eprint("SCANFROM: %s", ErrMsg[E_INCOMPLETE]);
return E_INCOMPLETE;
}
if (!DateOK(y, m, d)) return E_BAD_DATE;
t->scanfrom = Julian(y, m, d);
PushToken(TokBuffer);
return OK;
}
}
}
/***************************************************************/
/* */
/* TriggerReminder */
/* */
/* Trigger the reminder if it's a RUN or MSG type. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
#ifdef OS2_POPUP
PUBLIC int TriggerReminder(ParsePtr p, Trigger *t, TimeTrig *tim, int jul,
int AsPopUp)
#else /* ! OS2_POPUP */
PUBLIC int TriggerReminder(ParsePtr p, Trigger *t, TimeTrig *tim, int jul)
#endif /* OS2_POPUP */
#else /* ! HAVE_PROTOS */
#ifdef OS2_POPUP
int TriggerReminder(p, t, tim, jul, AsPopUp)
ParsePtr p;
Trigger *t;
TimeTrig *tim;
int jul;
int AsPopUp;
#else /* ! OS2_POPUP */
int TriggerReminder(p, t, tim, jul)
ParsePtr p;
Trigger *t;
TimeTrig *tim;
int jul;
#endif /* OS2_POPUP */
#endif /* HAVE_PROTOS */
{
int r, y, m, d;
char PrioExpr[25];
static char buf[LINELEN+TOKSIZE];
char *s, *s2;
Value v;
if (t->typ == RUN_TYPE && RunDisabled) return E_RUN_DISABLED;
if (t->typ == CAL_TYPE || t->typ == PS_TYPE || t->typ == PSF_TYPE)
return OK;
/* If it's a MSG-type reminder, and no -k option was used, issue the banner. */
if ((t->typ == MSG_TYPE || t->typ == MSF_TYPE)
&& !NumTriggered && !NextMode && !MsgCommand) {
if (!DoSubstFromString(Banner, SubstBuffer, JulianToday, NO_TIME) && *SubstBuffer)
#ifdef OS2_POPUP
if (AsPopUp)
PutlPopUp(SubstBuffer);
else
printf("%s\n", SubstBuffer);
#else
printf("%s\n", SubstBuffer);
#endif
}
/* If it's NextMode, process as a CAL-type entry, and issue simple-calendar
format. */
if (NextMode) {
if ( (r=DoSubst(p, SubstBuffer, t, tim, jul, CAL_MODE)) ) return r;
if (!*SubstBuffer) return OK;
FromJulian(jul, &y, &m, &d);
#ifdef OS2_POPUP
if (AsPopUp) {
sprintf(buf, "%04d%c%02d%c%02d %s", y, DATESEP, m+1, DATESEP, d,
SimpleTime(tim->ttime, NULL));
StartPopUp();
PutsPopUp(buf);
PutlPopUp(SubstBuffer);
}
else
printf("%04d%c%02d%c%02d %s%s\n", y, DATESEP, m+1, DATESEP, d,
SimpleTime(tim->ttime, NULL),
SubstBuffer);
#else
printf("%04d%c%02d%c%02d %s%s\n", y, DATESEP, m+1, DATESEP, d,
SimpleTime(tim->ttime, NULL),
SubstBuffer);
#endif
return OK;
}
/* Put the substituted string into the SubstBuffer */
s2 = buf;
*s2 = 0;
if (UserFuncExists("msgprefix") == 1) {
sprintf(PrioExpr, "msgprefix(%d)", t->priority);
s = PrioExpr;
r = EvalExpr(&s, &v);
if (!r) {
if (!DoCoerce(STR_TYPE, &v)) {
sprintf(s2, "%s", v.v.str);
s2 += strlen(s2);
}
DestroyValue(v);
}
}
if ( (r=DoSubst(p, s2, t, tim, jul, NORMAL_MODE)) ) return r;
s2 += strlen(s2);
if (UserFuncExists("msgsuffix") == 1) {
sprintf(PrioExpr, "msgsuffix(%d)", t->priority);
s = PrioExpr;
r = EvalExpr(&s, &v);
if (!r) {
if (!DoCoerce(STR_TYPE, &v)) {
sprintf(s2, "%s", v.v.str);
s2 += strlen(s2);
}
DestroyValue(v);
}
}
if ((!MsgCommand && t->typ == MSG_TYPE) || t->typ == MSF_TYPE) {
*s2++ = '\n';
}
*s2 = 0;
/* If we are sorting, just queue it up in the sort buffer */
if (SortByDate) {
if (InsertIntoSortBuffer(jul, tim->ttime, buf, t->typ, t->priority) == OK) {
NumTriggered++;
return OK;
}
}
/* If we didn't insert the reminder into the sort buffer, issue the
reminder now. */
switch(t->typ) {
case MSG_TYPE:
if (MsgCommand) {
DoMsgCommand(MsgCommand, buf);
} else {
#ifdef OS2_POPUP
if (AsPopUp)
PutlPopUp(buf);
else
printf("%s", buf);
#else
printf("%s", buf);
#endif
}
break;
case MSF_TYPE:
#ifdef OS2_POPUP
if (AsPopUp) {
StartPopUp();
FillParagraph(buf, 1);
EndPopUp();
} else {
FillParagraph(buf, 0);
}
#else
FillParagraph(buf);
#endif
break;
case RUN_TYPE:
system(buf);
break;
default: /* Unknown/illegal type? */
return E_SWERR;
}
NumTriggered++;
return OK;
}
/***************************************************************/
/* */
/* ShouldTriggerReminder */
/* */
/* Return 1 if we should trigger a reminder, based on today's */
/* date and the trigger. Return 0 if reminder should not be */
/* triggered. */
/* */
/***************************************************************/
#ifdef __TURBOC__
#pragma argsused
#endif
#ifdef HAVE_PROTOS
PUBLIC int ShouldTriggerReminder(Trigger *t, TimeTrig *tim, int jul)
#else
int ShouldTriggerReminder(t, tim, jul)
Trigger *t;
TimeTrig *tim;
int jul;
#endif
{
int r;
/* Handle the ONCE modifier in the reminder. */
if (!IgnoreOnce && t->once !=NO_ONCE && FileAccessDate == JulianToday)
return 0;
if (jul < JulianToday) return 0;
/* Don't trigger timed reminders if DontIssueAts is true, and if the
reminder is for today */
#ifdef HAVE_QUEUED
if (jul == JulianToday && DontIssueAts && tim->ttime != NO_TIME) return 0;
#endif
/* Don't trigger "old" timed reminders */
/*** REMOVED...
if (jul == JulianToday &&
tim->ttime != NO_TIME &&
tim->ttime < SystemTime(0) / 60) return 0;
*** ...UNTIL HERE */
/* If "infinite delta" option is chosen, always trigger future reminders */
if (InfiniteDelta || NextMode) return 1;
/* If there's a "warn" function, it overrides any deltas */
if (t->warn[0] != 0) {
return ShouldTriggerBasedOnWarn(t, jul);
}
/* Move back by delta days, if any */
if (t->delta != NO_DELTA) {
if (t->delta < 0)
jul = jul + t->delta;
else {
r = t->delta;
while(r && jul > JulianToday) {
jul--;
if (!IsOmitted(jul, t->localomit)) r--;
}
}
}
/* Should we trigger the reminder? */
return (jul <= JulianToday);
}
/***************************************************************/
/* */
/* DoSatRemind */
/* */
/* Do the "satisfying..." remind calculation. */
/* */
/***************************************************************/
#ifdef __TURBOC__
#pragma argsused
#endif
#ifdef HAVE_PROTOS
PUBLIC int DoSatRemind(Trigger *trig, TimeTrig *tim, ParsePtr p)
#else
int DoSatRemind(trig, tim, p)
Trigger *trig;
TimeTrig *tim;
ParsePtr p;
#endif
{
int iter, jul, r;
Value v;
char *s, *t;
t = p->pos;
iter = 0;
jul = trig->scanfrom;
while (iter++ < MaxSatIter) {
jul = ComputeTrigger(jul, trig, &r);
if (r) {
if (r == E_CANT_TRIG) return OK; else return r;
}
s = p->pos;
r = EvaluateExpr(p, &v);
t = p->pos;
if (r) return r;
if (v.type != INT_TYPE && v.type != STR_TYPE) return E_BAD_TYPE;
if (v.type == INT_TYPE && v.v.val) return OK;
if (v.type == STR_TYPE && *v.v.str) return OK;
p->pos = s;
jul++;
}
p->pos = t;
LastTrigValid = 0;
return OK;
}
/***************************************************************/
/* */
/* ParsePriority - parse the PRIORITY portion of a reminder */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ParsePriority(ParsePtr s, Trigger *t)
#else
static int ParsePriority(s, t)
ParsePtr s;
Trigger *t;
#endif
{
int p, r;
char *u;
r = ParseToken(s, TokBuffer);
if(r) return r;
u = TokBuffer;
if (!isdigit(*u)) return E_EXPECTING_NUMBER;
p = 0;
while (isdigit(*u)) {
p = p*10 + *u - '0';
u++;
}
if (*u) return E_EXPECTING_NUMBER;
/* Tricky! The only way p can be < 0 is if overflow occurred; thus,
E2HIGH is indeed the appropriate error message. */
if (p<0 || p>9999) return E_2HIGH;
t->priority = p;
return OK;
}
/***************************************************************/
/* */
/* DoMsgCommand */
/* */
/* Execute the '-k' command, escaping shell chars in message. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC void DoMsgCommand(char *cmd, char *msg)
#else
void DoMsgCommand(cmd, msg)
char *cmd;
char *msg;
#endif
{
#ifdef WANT_SHELL_ESCAPING
char buf[2*LINELEN+TOKSIZE];
char *s, *t;
/* Escape shell characters in msg INCLUDING WHITESPACE! */
for (t=buf, s=msg; *s; s++) {
if (isspace(*s) || strchr(EscapeMe, *s)) *t++ = '\\';
*t++ = *s;
}
*t = 0;
/* Use SubstBuffer -- not too safe, since no check for overflow... */
sprintf(SubstBuffer, cmd, buf);
#else
sprintf(SubstBuffer, cmd, msg);
#endif /* WANT_SHELL_ESCAPING */
system(SubstBuffer);
}
/***************************************************************/
/* */
/* ShouldTriggerBasedOnWarn */
/* */
/* Determine whether to trigger a reminder based on its WARN */
/* function. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ShouldTriggerBasedOnWarn(Trigger *t, int jul)
#else
static int ShouldTriggerBasedOnWarn(t, jul)
Trigger *t;
int jul;
#endif
{
char buffer[VAR_NAME_LEN+15];
int i;
char *s;
int r;
Value v;
int lastReturnVal = 0; /* Silence compiler warning */
/* If no proper function exists, barf... */
if (UserFuncExists(t->warn) != 1) {
Eprint("%s: `%s'", ErrMsg[M_BAD_WARN_FUNC], t->warn);
return (jul == JulianToday);
}
for (i=1; ; i++) {
sprintf(buffer, "%s(%d)", t->warn, i);
s = buffer;
r = EvalExpr(&s, &v);
if (r) {
Eprint("%s: `%s': %s", ErrMsg[M_BAD_WARN_FUNC],
t->warn, ErrMsg[r]);
return (jul == JulianToday);
}
if (v.type != INT_TYPE) {
DestroyValue(v);
Eprint("%s: `%s': %s", ErrMsg[M_BAD_WARN_FUNC],
t->warn, ErrMsg[E_BAD_TYPE]);
return (jul == JulianToday);
}
/* If absolute value of return is not monotonically
decreasing, exit */
if (i > 1 && abs(v.v.val) >= lastReturnVal) {
return (jul == JulianToday);
}
lastReturnVal = abs(v.v.val);
/* Positive values: Just subtract. Negative values:
skip omitted days. */
if (v.v.val >= 0) {
if (JulianToday + v.v.val == jul) return 1;
} else {
int j = jul;
while (v.v.val) {
j--;
if (!IsOmitted(j, t->localomit)) v.v.val++;
}
if (j == JulianToday) return 1;
}
}
}

View File

@@ -17,21 +17,17 @@
# "#COLORS" for examples of ANSI color escape sequences. #
# #
# This file is part of REMIND. #
# Copyright (C) 1992-1996 by David F. Skoll #
# Copyright (C) 1992-2018 Dianne Skoll #
# #
#############################################################################
#
# $Id: defs.rem,v 1.1 1996-03-27 03:25:51 dfs Exp $
#
RUN OFF
################################################
# Ensure required version of remind is used... #
################################################
IF version() < "03.00.10"
ERRMSG This file requires at least version 03.00.10 of Remind.%
IF version() < "03.01.09"
ERRMSG This file requires at least version 03.01.09 of Remind.%
ERRMSG This version is version [version()].
EXIT
ENDIF
@@ -88,7 +84,6 @@ SET December 12
###########################################################
# Other symbolic constants and functions for "pasting"... #
###########################################################
SET Quote CHAR(34)
# Handy constants/function for specifing week of month...
@@ -96,94 +91,33 @@ SET Week_1 1
SET Week_2 8
SET Week_3 15
SET Week_4 22
FSET _last(mo) "1 " + MON((mo%12)+1)+" --7"
# Shorthand for commonly used expression...
FSET _trig() TRIGGER(TRIGDATE())
FSET _last(mo) "1 " + MON((mo%12)+1) + " --7"
# Handy function to provide SCANFROM dates...
FSET _back(days) TRIGGER(TODAY()-days)
###########################################################
# On MS-DOS systems, the standard C library functions are #
# not reliable for computing offsets from local time to #
# UTC. The following provides a work-around for the #
# sunrise() and sunset() functions. Note, however, that #
# if Daylight Savings Time is in effect for today(), the #
# sun functions return times in DST even for dates on #
# which DST is not in effect; the converse can also occur.#
# #
# Change the timezone to your timezone - the default is #
# for EST which is 5 hours (300 minutes) behind UTC. #
# The code is correct for places in which Daylight Savings#
# Time begins on the last Sunday in April and ends on the #
# last Sunday in October. #
###########################################################
IF OSTYPE() == "MSDOS"
# Eastern Standard Time
SET TimeZone -300
# Use --8 rather than --7 because we want the last day BEFORE
# the time switch occurs.
REM Sun 1 May --8 SATISFY 1
SET BegDst TRIGDATE()
REM Sun 1 Nov --8 SATISFY 1
SET EndDst TRIGDATE()
SET $CalcUTC 0
# Check out the following IF statement and figure out why it works!
IF EndDst < BegDst
# Daylight Savings Time
SET $MinsFromUTC TimeZone+60
ELSE
# Standard Time
SET $MinsFromUTC TimeZone
ENDIF
ENDIF
###########################################################
# Function which returns a string in "am/pm" format based #
# on the time. For example, set a am_pm(NOW())... #
###########################################################
FSET _am_pm(tm) IIF(tm<01:00, tm+12*60+"am", \
tm<12:00, tm+"am", \
tm<13:00, tm+"pm", \
tm-12*60+"pm")
FSET _back(days) $U-days
#################################################################
# Function which removes a single leading zero from a string... #
# Function that removes a single leading zero from a string... #
#################################################################
FSET _no_lz(s) IIF(SUBSTR(s, 1, 1)=="0", SUBSTR(s, 2), s)
#################################################################
# Return the length of the daylight/night portion of a date, #
# in minutes. #
#################################################################
FSET _light_len(date) MAX(SUNSET(date)-SUNRISE(date), 0)
FSET _dark_len(date) 1440-_light_len(date)
############################################################
# Function to calculate number of years since a given year #
# or number of months since a given month and year... #
############################################################
FSET _yr_num(yr) ORD(YEAR(TRIGDATE()) - yr)
FSET _mo_num(mo, yr) ORD(12 * (YEAR(TRIGDATE()) - yr) + \
MONNUM(TRIGDATE()) - mo)
FSET _yr_num(yr) ORD($Ty - yr)
FSET _mo_num(mo, yr) ORD(12 * ($Ty - yr) + $Tm - mo)
# Here's an example of how to use them:
REM 1 Nov ++12 MSG %"Dean's [_yr_num(1984)] birthday%" is %b.
REM 1 MSG Dean's [_mo_num(11, 1984)] 'monthly' anniversary
###########################################################
# Function to send mail via elm's "fastmail" (by GMS!)... #
###########################################################
#FSET _mail(from, subj) "mailx -s " + \
# Quote + from + " : " + subj + Quote \
# GETENV("LOGNAME") + " < /dev/null 1>&0"
FSET _mail(from, subj) "fastmail -f " + \
Quote + from + Quote + \
" -s " + Quote + subj + Quote + \
" /dev/null " + GETENV("LOGNAME")
REM 1 Nov ++12 MSG %"John's [_yr_num(1984)] birthday%" is %b.
REM 1 MSG John's [_mo_num(11, 1984)] 'monthly' anniversary
#############################################################################
# Here's a tricky problem: The 4th of July is a holiday in the U.S.
@@ -197,29 +131,28 @@ FSET _mail(from, subj) "fastmail -f " + \
# dependent upon the current date, it's tricky and results may not be
# what you expect. You should try to make sure that the OMIT context
# "near" any current reminders will not change during a calendar run.
# The SCANFROM clause should help make these OMITs very safe.
# The SCANFROM clause will make these OMITs safe.
############################################################################
# Calculate the weekday of the holiday.
REM 4 July SCANFROM [_back(7)] SATISFY 1
IF WKDAYNUM(TRIGDATE()) == Sat
REM [TRIGGER(TRIGDATE())] MSG Independence day (actual)
OMIT [TRIGGER(TRIGDATE()-1)] MSG Independence day (observed)
SET iday $T
IF WKDAYNUM(iday) == Sat
REM [iday] MSG Independence day (actual)
OMIT [iday-1] MSG Independence day (observed)
ELSE
IF WKDAYNUM(TRIGDATE()) == Sun
REM [TRIGGER(TRIGDATE())] MSG Independence day (actual)
OMIT [TRIGGER(TRIGDATE()+1)] MSG Independence day (observed)
IF WKDAYNUM(iday) == Sun
REM [iday] MSG Independence day (actual)
OMIT [iday+1] MSG Independence day (observed)
ELSE
OMIT [TRIGGER(TRIGDATE())] MSG Independence day
OMIT [iday] MSG Independence day
ENDIF
ENDIF
############################################################################
# #
# A meeting on the first Monday of every month which is moved to the #
# second Monday in the event of a holiday. #
# #
############################################################################
# First, the normal meeting. However, the SKIP keyword means this
@@ -231,118 +164,40 @@ REM Mon 8 SATISFY 1
# But only actually trigger the delayed meeting if the previous
# Monday was a holiday
IF ISOMITTED(TRIGDATE()-7)
REM [TRIGGER(TRIGDATE())] MSG Delayed meeting
IF ISOMITTED($T-7)
REM [$T] MSG Delayed meeting
ENDIF
############################################################################
# #
# A very complicated reminder sent in by a Remind user. #
# This person gets paid every two weeks, starting from 8 January 1993. #
# If a pay date occurs before the twelfth of a month, then that #
# he pays his mortgage on that pay date. Otherwise, he pays the mortgage #
# on the previous pay date. Furthermore, he has to schedule his #
# mortgage payment six days before it is due. He wants to be reminded #
# a further four days before the scheduling deadline. He also #
# wants to be mailed a notice two weeks before the scheduling deadline. #
# #
# Here's the solution - if you can follow this, consider yourself a #
# Remind programmer extraordinaire! #
# #
############################################################################
# A function to determine whether or not a pay-date is a mortgage-date.
FSET _IsMortDate(x) DAY(x) < 12 || (DAY(x+14) >= 12 && DAY(x+14) <= 14)
# Paydays - for reference
REM 8 Jan 1993 *14 MSG Payday
# Calculate the mortgage payment six days ahead of time. Note that this
# is done "implicitly" by subtracting 6 from the starting date - we start
# on 2 Jan rather than 8 Jan. We add 6 to TRIGDATE() in _IsMortDate to
# compensate.
REM 2 Jan 1993 *14 ++4 SATISFY [_IsMortDate(TRIGDATE()+6)] \
MSG %"Schedule mortgage payment%" for %a.
# Now the mail reminder two weeks before the payment date - because two
# weeks before a payment date is also a payment date, no pre-compensation
# in the starting date of 8 Jan is necessary - convince yourself of this!
# This uses the _mail() function defined earlier.
REM ONCE 8 Jan 1993 *14 SATISFY [_IsMortDate(TRIGDATE()+14)] \
RUN [_mail("Decatur Federal", \
"Pay mortgage by the " + ORD(DAY(TRIGDATE()+14)))]
# Make an entry on the calendar when the mortgage should be paid
REM 8 Jan 1993 *14 SATISFY [_IsMortDate(TRIGDATE())] \
CAL Mortgage payment
##########################################################################
# #
# On our UNIX system, I run a program which queries the university #
# On our UNIX system, I run a program that queries the university #
# library and creates a file called ".booksdue". This file is #
# a REMIND script to tell me when my library books are due. Here's #
# an example from my reminder file - it shows the use of filedate(). #
# When the .booksdue file is at least 7 days old, I create a new version #
# by querying the library computer. Note the use of realtoday() rather #
# than today. #
# than today(). #
# #
##########################################################################
IF !$RunOff && !$CalMode && !$SimpleCal
IF REALTODAY()-FILEDATE("/home/dfs/.booksdue") >= 7
REM RUN /home/dfs/bilge/library/getbooks
ENDIF
ENDIF
#PSSTUFF
#PSSTUFF1
##########################################################################
# #
# This portion of the file contains some cute examples of the new #
# PS-type reminders. You need a PostScript printer or viewer to #
# appreciate these. To use them, pipe the output of remind -p into the #
# rem2ps program. #
# rem2ps program. More examples are in the PSSTUFF2 section, below. #
# #
##########################################################################
# Convenient to stick all the PostScript code in a string var - makes
# reminders easier to understand and faster. The variable "shade" will
# contain PostScript code to shade in a particular box on the calendar.
SET shade psshade(95)
# The following reminder will shade the Saturday and Sunday calendar
# entries.
REM Sat Sun PS [shade]
# The following will fill in the Hebrew dates on the calendar. For this
# example, I recommend that you use the -sd 10 option for Rem2PS.
REM PS Border Border moveto \
/DayFont findfont DaySize scalefont setfont \
([hebday(today())] [hebmon(today())]) show
# Fill in the phases of the moon on the PostScript calendar
[trigger(moondate(0))] PS [psmoon(0)]
[trigger(moondate(1))] PS [psmoon(1)]
[trigger(moondate(2))] PS [psmoon(2)]
[trigger(moondate(3))] PS [psmoon(3)]
# The following example puts sunrise and sunset times in PostScript in the
# calendar - the sizes are hard-coded, however, and work best in landscape.
REM PS Border Border 5 sub moveto \
/SmallFont findfont 4 scalefont setfont \
(Sunrise: [sunrise(trigdate())] Sunset: [sunset(trigdate())]) show
# The next one puts the day number (1-366) and days left in the year at the
# bottom of the post-script calendar. Again, the hard-coded sizes work best
# in landscape.
FSET _DayOfYear(x) x-(date(year(x),1,1) - 1)
REM PS BoxWidth 3 mul 4 div Border 5 sub moveto \
/SmallFont findfont 4 scalefont setfont \
([_DayOfYear(today())]([365+isleap(today())-_DayOfYear(today())])) show
REM Sat Sun SPECIAL SHADE 220
#USHOLS
#############################################################################
@@ -353,13 +208,13 @@ REM PS BoxWidth 3 mul 4 div Border 5 sub moveto \
#############################################################################
SET SaveTrig $NumTrig
SET easter EASTERDATE(YEAR(TODAY()))
REM [TRIGGER(easter-46)] MSG %"Ash Wednesday%"
REM [TRIGGER(easter-7)] MSG %"Palm Sunday%"
OMIT [TRIGGER(easter-2)] MSG %"Good Friday%"
OMIT [TRIGGER(easter)] MSG %"Easter%" Sunday
REM [TRIGGER(easter+39)] MSG %"Ascension Day%"
REM [TRIGGER(easter+49)] MSG %"Pentecost%"
SET easter EASTERDATE($Uy)
REM [easter-46] MSG %"Ash Wednesday%"
REM [easter-7] MSG %"Palm Sunday%"
OMIT [easter-2] MSG %"Good Friday%"
OMIT [easter] MSG %"Easter%" Sunday
REM [easter+39] MSG %"Ascension Day%"
REM [easter+49] MSG %"Pentecost%"
# Some holidays are omitted, some are not. You may want to change
# which ones are omitted - use the general forms shown below.
@@ -371,9 +226,17 @@ REM Mon Jan [Week_3] MSG Martin Luther King - %"MLK Day%"
REM Feb 2 MSG %"Ground Hog Day%"
REM Feb 14 MSG %"Valentine's%" Day
REM Mon Feb [Week_3] SCANFROM [_back(7)] SATISFY 1
OMIT [_trig()] MSG %"President's Day%"
OMIT [$T] MSG %"President's Day%"
REM Mar 17 MSG %"St. Patrick's%" Day
REM Sun Apr 1 ++2 MSG Daylight Savings Time - %"DST starts%" %b
# The DST rules are accurate for most locations in
# North America
REM Sun Apr 1 ++2 UNTIL 1 Jan 2007 MSG Daylight Saving Time - %"DST starts%" %b
REM Sun Mar 8 ++2 FROM 1 Jan 2007 MSG Daylight Saving Time - %"DST starts%" %b
REM Sun [_last(Oct)] ++2 UNTIL 1 Jan 2007 MSG Daylight Saving Time - %"DST ends%" %b
REM Sun 1 Nov ++2 FROM 1 Jan 2007 MSG Daylight Saving Time - %"DST ends%" %b
REM Apr 1 MSG %"April Fool's%" Day
REM Mon Tue Wed Thu Fri Sat 15 Apr MSG %"Income tax%" due
REM May 5 MSG %"Cinco de Mayo%"
@@ -381,44 +244,71 @@ REM Sat May [Week_1] MSG %"Kentucky Derby%"
REM Sun May [Week_2] MSG %"Mother's Day%"
REM Sat May [Week_3] MSG %"Armed Forces Day%"
REM Mon [_last(May)] SCANFROM [_back(7)] SATISFY 1
OMIT [_trig()] MSG %"Memorial Day%"
OMIT [$T] MSG %"Memorial Day%"
REM Jun 14 MSG %"Flag Day%"
REM Sun Jun [Week_3] MSG %"Father's Day%"
REM Mon Sep [Week_1] SCANFROM [_back(7)] SATISFY 1
OMIT [_trig()] MSG %"Labor Day%"
OMIT [$T] MSG %"Labor Day%"
REM Mon Oct [Week_2] MSG %"Columbus Day%"
REM Nov 11 MSG %"Veterans Day%"
REM Sun [_last(Oct)] MSG Daylight Savings Time - %"DST over%"
REM Oct 30 MSG %"Mischief Night%"
REM Oct 31 MSG %"Halloween%"
REM Tue Nov 2 SCANFROM [_back(7)] \
SATISFY [(YEAR(TRIGDATE()) % 4) == 0] \
SATISFY [($Ty % 4) == 0] \
MSG %"Election%" Day
REM Thu Nov [Week_4] SCANFROM [_back(7)] SATISFY 1
OMIT [_trig()] MSG %"Thanksgiving%" Day
OMIT [$T] MSG %"Thanksgiving%" Day
REM Fri Nov [Week_4+1] SCANFROM [_back(7)] SATISFY 1
OMIT [_trig()] MSG %"Thanksgiving%" (cont.)
OMIT [$T] MSG %"Thanksgiving%" (cont.)
OMIT Dec 24 MSG %"Christmas Eve%"
OMIT Dec 25 MSG %"Christmas%" Day
##########################################################################
# #
# The next block uses the shade variable defined in PSSTUFF above. #
# If any US holidays were triggered above, shade in the calendar #
# entry in PostScript. This is not quite correct, as it blots out the #
# entry in PostScript. This is not quite correct, as it blots out any #
# other PostScript stuff above. I was too lazy to do it properly :-) #
# #
##########################################################################
if $NumTrig > SaveTrig
REM PS [shade]
REM SPECIAL SHADE 220
endif
# Seasons (valid from 1992 to 2000)...
REM Mar 20 MSG %"Spring%" begins
REM Jun [IIF(YEAR(TODAY())%4, 21, 20)] MSG %"Summer%" begins
REM Sep [CHOOSE(YEAR(TODAY())-1991, 22,22,23,23,22,22,22,23,22)] \
MSG %"Fall%" begins
REM Dec [IIF((YEAR(TODAY())+1)%4, 21, 22)] MSG %"Winter%" begins
#PSSTUFF2
##########################################################################
# #
# Since the SHADE special blots out any previous PostScript #
# reminders for a date, these examples need to follow the US Holidays #
# section, which uses SHADE. #
# #
##########################################################################
# The following will fill in the Hebrew dates on the calendar. For this
# example, I recommend that you use the -sd 10 option for Rem2PS.
REM PS Border Border moveto \
/DayFont findfont DaySize scalefont setfont \
([hebday($U)] [hebmon($U)]) show
# Fill in the phases of the moon on the PostScript calendar
[moondate(0)] SPECIAL MOON 0
[moondate(1)] SPECIAL MOON 1
[moondate(2)] SPECIAL MOON 2
[moondate(3)] SPECIAL MOON 3
# The following example puts sunrise and sunset times in PostScript in the
# calendar - the sizes are hard-coded, however, and work best in landscape.
REM PS Border Border 5 sub moveto \
/SmallFont findfont 4 scalefont setfont \
(Sunrise: [sunrise($T)] Sunset: [sunset($T)]) show
# The next one puts the day number (1-366) and days left in the year at the
# bottom of the post-script calendar. Again, the hard-coded sizes work best
# in landscape.
FSET _DayOfYear(x) x-(date(year(x),1,1) - 1)
REM PS BoxWidth 3 mul 4 div Border 5 sub moveto \
/SmallFont findfont 4 scalefont setfont \
([_DayOfYear($U)]([365+isleap($U)-_DayOfYear($U)])) show
#JHOLS
##########################################################################
@@ -427,7 +317,7 @@ REM Dec [IIF((YEAR(TODAY())+1)%4, 21, 22)] MSG %"Winter%" begins
# dates were obtained from "The First Jewish Catalog" by Richard Siegel #
# and Michael and Sharon Strassfeld, published by the Jewish Publication #
# Society of America. The Reform version of the calendar was guessed #
# at by David Skoll based on experience. There is probably no standard #
# at by Dianne Skoll based on experience. There is probably no standard #
# Reform position on many of the holidays, so you may have to adjust #
# the file as required. #
# #
@@ -457,9 +347,11 @@ SET InIsrael 0
SET Reform 0
# Convenient function definition to save typing
FSET _h(x, y) TRIGGER(HEBDATE(x,y))
FSET _h2(x, y) HEBDATE(x, y, TODAY()-7)
FSET _PastSat(x, y) TRIGGER(IIF(WKDAYNUM(_h2(x,y))!=6, _h2(x,y), _h2(x,y)+1))
FSET _h(x, y) HEBDATE(x,y)
FSET _h2(x, y) HEBDATE(x, y, $U-7)
FSET _PastSat(x, y) IIF(WKDAYNUM(_h2(x,y))!=6, _h2(x,y), _h2(x,y)+1)
FSET _PastSun(x, y) IIF(WKDAYNUM(_h2(x,y))!=0, _h2(x,y), _h2(x,y)+1)
FSET _PastMon(x, y) IIF(WKDAYNUM(_h2(x,y))!=1, _h2(x,y), _h2(x,y)+1)
# Default values in case InIsrael and Reform are not set
SET InIsrael VALUE("InIsrael", 0)
@@ -480,7 +372,7 @@ IF !InIsrael
[_h(16, "Tishrey")] MSG %"Sukkot 2%"
ENDIF
[_h(21, "Tishrey")] ++4 MSG %"Hashana Rabba%" is %b.
[_h(21, "Tishrey")] ++4 MSG %"Hoshana Rabba%" is %b.
[_h(22, "Tishrey")] ++4 MSG %"Shemini Atzeret%" is %b.
IF InIsrael
@@ -490,7 +382,7 @@ ELSE
ENDIF
# Because Kislev can change length, we must be more careful about Chanukah
FSET _chan(x) TRIGGER(HEBDATE(24, "Kislev", today()-9)+x)
FSET _chan(x) HEBDATE(24, "Kislev", $U-9)+x
[_chan(1)] ++4 MSG %"Chanukah 1%" is %b.
[_chan(2)] MSG %"Chanukah 2%"
[_chan(3)] MSG %"Chanukah 3%"
@@ -508,15 +400,17 @@ IF !Reform
ENDIF
[_h(15, "Shvat")] ++4 MSG %"Tu B'Shvat%" is %b.
[_h(15, "Adar A")] ++4 MSG %"Purim Katan%" is %b.
[_h(14, "Adar A")] ++4 MSG %"Purim Katan%" is %b.
[_h(15, "Adar A")] ++4 MSG %"Shushan Purim Katan%" is %b.
# If Purim is on Sunday, then Fast of Esther is 11 Adar.
IF WKDAYNUM(_h2(13, "Adar")) != 6
REM [TRIGGER(_h2(13, "Adar"))] ++4 MSG %"Fast of Esther%" is %b.
REM [_h2(13, "Adar")] ++4 MSG %"Fast of Esther%" is %b.
ELSE
REM [TRIGGER(_h2(11, "Adar"))] ++4 MSG %"Fast of Esther%" is %b.
REM [_h2(11, "Adar")] ++4 MSG %"Fast of Esther%" is %b.
ENDIF
[_h(14, "Adar")] ++4 MSG %"Purim%" is %b.
[_h(15, "Adar")] ++4 MSG %"Shushan Purim%" is %b.
[_h(15, "Nisan")] ++4 MSG %"Pesach%" is %b.
IF !InIsrael
@@ -529,9 +423,30 @@ IF !InIsrael && !Reform
[_h(22, "Nisan")] MSG %"Pesach 8%"
ENDIF
[_h(27, "Nisan")] ++4 MSG %"Yom HaShoah%" is %b.
[_h(4, "Iyar")] ++4 MSG %"Yom HaZikaron%" is %b.
[_h(5, "Iyar")] ++4 MSG %"Yom Ha'atzmaut%" is %b.
REM [_PastSun(27, "Nisan")] SATISFY 1
IF $Tw == 5
REM [_PastSun(26, "Nisan")] ++4 MSG %"Yom HaShoah%" is %b.
ELSE
REM [_PastSun(27, "Nisan")] ++4 MSG %"Yom HaShoah%" is %b.
ENDIF
# If 4 Iyar is a Thursday or Friday, then Yom Hazikaron is
# the Wednesday before and Yom Ha'atzmaut is on
# Thursday. If 4 Iyar is a Sunday, then Yom Hazikaron
# moves to 5 Iyar and Yom Ha'atzmaut to 6 Iyar.
IF WKDAYNUM(_h2(4, "Iyar")) == 4 || WKDAYNUM(_h2(4, "Iyar")) == 5
[_h(2, "Iyar")] ++4 MSG %"Yom Hazikaron%" is %b.
[_h(3, "Iyar")] ++4 MSG %"Yom Ha'atzmaut%" is %b.
ELSE
IF WKDAYNUM(_h2(4, "Iyar")) == 0
[_h(5, "Iyar")] ++4 MSG %"Yom Hazikaron%" is %b.
[_h(6, "Iyar")] ++4 MSG %"Yom Ha'atzmaut%" is %b.
ELSE
[_h(4, "Iyar")] ++4 MSG %"Yom Hazikaron%" is %b.
[_h(5, "Iyar")] ++4 MSG %"Yom Ha'atzmaut%" is %b.
ENDIF
ENDIF
# Not sure about Reform's position on Lag B'Omer
IF !Reform
@@ -556,9 +471,9 @@ ENDIF
# Counting the omer - do the whole spiel, i.e:
# "This is the xth day of the omer, being y weeks and z days of the omer."
# Nice Remind programming example here!
SET ostart HEBDATE(16, "Nisan", TODAY()-50)
IF ostart <= TODAY() && (TODAY() - ostart < 49)
SET odays TODAY()-ostart+1
SET ostart HEBDATE(16, "Nisan", $U-50)
IF ostart <= $U && ($U - ostart < 49)
SET odays $U-ostart+1
IF odays < 7
MSG %"%"Today is the [ORD(odays)] day of the Omer.
ELSE
@@ -576,8 +491,8 @@ ENDIF
### for Friday and Saturday. Note: You must set your latitude, longitude
### and possibly time zone for these to work properly!
REM Friday CAL Candle lighting at [sunset(trigdate())-18]
REM Saturday CAL Havdalah at [sunset(trigdate())+42]
REM Friday CAL Candle lighting at [sunset($T)-18]
REM Saturday CAL Havdalah at [sunset($T)+42]
#COLORS
##########################################################################

79
examples/remind.vim Normal file
View File

@@ -0,0 +1,79 @@
" Vim syntax file
" Language: Remind
" Maintainer: Davide Alberani <alberanid@libero.it>
" Last Change: 18 Sep 2009
" Version: 0.5
" URL: http://erlug.linux.it/~da/vim/syntax/remind.vim
"
" remind is a sophisticated reminder service
" you can download remind from:
" https://dianne.skoll.ca/projects/remind/
if version < 600
syntax clear
elseif exists("b:current_syntax")
finish
endif
" shut case off.
syn case ignore
syn keyword remindCommands REM OMIT SET FSET UNSET
syn keyword remindExpiry UNTIL FROM SCANFROM SCAN WARN SCHED THROUGH
syn keyword remindTag PRIORITY TAG
syn keyword remindTimed AT DURATION
syn keyword remindMove ONCE SKIP BEFORE AFTER
syn keyword remindSpecial INCLUDE INC BANNER PUSH-OMIT-CONTEXT PUSH CLEAR-OMIT-CONTEXT CLEAR POP-OMIT-CONTEXT POP COLOR COLOUR
syn keyword remindRun MSG MSF RUN CAL SATISFY SPECIAL PS PSFILE SHADE MOON
syn keyword remindConditional IF ELSE ENDIF IFTRIG
syn keyword remindDebug DEBUG DUMPVARS DUMP ERRMSG FLUSH PRESERVE
syn match remindComment "#.*$"
syn region remindString start=+'+ end=+'+ skip=+\\\\\|\\'+ oneline
syn region remindString start=+"+ end=+"+ skip=+\\\\\|\\"+ oneline
syn match remindVar "\$[_a-zA-Z][_a-zA-Z0-9]*"
syn match remindSubst "%[^ ]"
syn match remindAdvanceNumber "\(\*\|+\|-\|++\|--\)[0-9]\+"
" XXX: use different separators for dates and times?
syn match remindDateSeparators "[/:@\.-]" contained
syn match remindTimes "[0-9]\{1,2}[:\.][0-9]\{1,2}" contains=remindDateSeparators
" XXX: why not match only valid dates? Ok, checking for 'Feb the 30' would
" be impossible, but at least check for valid months and times.
syn match remindDates "'[0-9]\{4}[/-][0-9]\{1,2}[/-][0-9]\{1,2}\(@[0-9]\{1,2}[:\.][0-9]\{1,2}\)\?'" contains=remindDateSeparators
" This will match trailing whitespaces that seem to break rem2ps.
" Courtesy of Michael Dunn.
syn match remindWarning display excludenl "\S\s\+$"ms=s+1
if version >= 508 || !exists("did_remind_syn_inits")
if version < 508
let did_remind_syn_inits = 1
command -nargs=+ HiLink hi link <args>
else
command -nargs=+ HiLink hi def link <args>
endif
HiLink remindCommands Function
HiLink remindExpiry Repeat
HiLink remindTag Label
HiLink remindTimed Statement
HiLink remindMove Statement
HiLink remindSpecial Include
HiLink remindRun Function
HiLink remindConditional Conditional
HiLink remindComment Comment
HiLink remindTimes String
HiLink remindString String
HiLink remindDebug Debug
HiLink remindVar Identifier
HiLink remindSubst Constant
HiLink remindAdvanceNumber Number
HiLink remindDateSeparators Comment
HiLink remindDates String
HiLink remindWarning Error
delcommand HiLink
endif
let b:current_syntax = "remind"
" vim: ts=8 sw=2

558
files.c
View File

@@ -1,558 +0,0 @@
/***************************************************************/
/* */
/* FILES.C */
/* */
/* Controls the opening and closing of files, etc. Also */
/* handles caching of lines and reading of lines from */
/* files. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: files.c,v 1.3 1996-05-25 19:10:12 dfs Exp $";
#include "config.h"
#include <stdio.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#include <string.h>
#include <ctype.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <time.h>
#if defined(__MSDOS__)
#include <io.h>
#endif
#ifdef __MSC__
#include <dos.h>
#endif
#include "types.h"
#include "protos.h"
#include "globals.h"
#include "err.h"
/* Convenient macro for closing files */
#define FCLOSE(fp) (((fp)&&((fp)!=stdin)) ? (fclose(fp),(fp)=NULL) : ((fp)=NULL))
/* Define the structures needed by the file caching system */
typedef struct cache {
struct cache *next;
char *text;
int LineNo;
} CachedLine;
typedef struct cheader {
struct cheader *next;
char *filename;
CachedLine *cache;
} CachedFile;
/* Define the structures needed by the INCLUDE file system */
typedef struct {
char *filename;
int LineNo;
unsigned int IfFlags;
int NumIfs;
long offset;
CachedLine *CLine;
} IncludeStruct;
static CachedFile *CachedFiles = (CachedFile *) NULL;
static CachedLine *CLine = (CachedLine *) NULL;
static FILE *fp;
static IncludeStruct IStack[INCLUDE_NEST];
static int IStackPtr = 0;
PRIVATE int ReadLineFromFile ARGS ((void));
PRIVATE int CacheFile ARGS ((const char *fname));
PRIVATE void DestroyCache ARGS ((CachedFile *cf));
/***************************************************************/
/* */
/* ReadLine */
/* */
/* Read a line from the file or cache. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int ReadLine(void)
#else
int ReadLine()
#endif
{
int r;
/* If we're at the end of a file, pop */
while (!CLine && !fp) {
r = PopFile();
if (r) return r;
}
/* If it's cached, read line from the cache */
if (CLine) {
CurLine = CLine->text;
LineNo = CLine->LineNo;
CLine = CLine->next;
FreshLine = 1;
if (DebugFlag & DB_ECHO_LINE) OutputLine(ErrFp);
return OK;
}
/* Not cached. Read from the file. */
return ReadLineFromFile();
}
/***************************************************************/
/* */
/* ReadLineFromFile */
/* */
/* Read a line from the file pointed to by fp. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int ReadLineFromFile(void)
#else
static ReadLineFromFile()
#endif
{
int l;
char *ptr;
char *tmp;
CurLine = LineBuffer;
*LineBuffer = (char) 0;
l = 0;
ptr = LineBuffer;
while(fp) {
tmp=fgets(ptr, LINELEN-l, fp);
LineNo++;
if (ferror(fp)) return E_IO_ERR;
if (feof(fp) || !tmp) {
FCLOSE(fp);
}
l = strlen(LineBuffer);
if (l && (LineBuffer[l-1] == '\n')) LineBuffer[--l] = '\0';
if (l && (LineBuffer[l-1] == '\\')) {
l--;
ptr = LineBuffer+l;
if (l >= LINELEN-1) return E_LINE_2_LONG;
continue;
}
FreshLine = 1;
if (DebugFlag & DB_ECHO_LINE) OutputLine(ErrFp);
return OK;
}
return OK;
}
/***************************************************************/
/* */
/* OpenFile */
/* */
/* Open a file for reading. If it's in the cache, set */
/* CLine. Otherwise, open it on disk and set fp. If */
/* ShouldCache is 1, cache the file */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int OpenFile(const char *fname)
#else
int OpenFile(fname)
char *fname;
#endif
{
CachedFile *h = CachedFiles;
int r;
/* If it's in the cache, get it from there. */
while (h) {
if (!strcmp(fname, h->filename)) {
CLine = h->cache;
STRSET(FileName, fname);
LineNo = 0;
if (FileName) return OK; else return E_NO_MEM;
}
h = h->next;
}
/* If it's a dash, then it's stdin */
if (!strcmp(fname, "-")) {
fp = stdin;
} else {
fp = fopen(fname, "r");
}
if (!fp) return E_CANT_OPEN;
CLine = NULL;
if (ShouldCache) {
LineNo = 0;
r = CacheFile(fname);
if (r == OK) {
fp = NULL;
CLine = CachedFiles->cache;
} else {
if (strcmp(fname, "-"))
fp = fopen(fname, "r");
else
fp = stdin;
if (!fp) return E_CANT_OPEN;
}
}
STRSET(FileName, fname);
LineNo = 0;
if (FileName) return OK; else return E_NO_MEM;
}
/***************************************************************/
/* */
/* CacheFile */
/* */
/* Cache a file in memory. If we fail, set ShouldCache to 0 */
/* Returns an indication of success or failure. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int CacheFile(const char *fname)
#else
static int CacheFile(fname)
char *fname;
#endif
{
int r;
CachedFile *cf;
CachedLine *cl;
char *s;
cl = NULL;
/* Create a file header */
cf = NEW(CachedFile);
cf->cache = NULL;
if (!cf) { ShouldCache = 0; FCLOSE(fp); return E_NO_MEM; }
cf->filename = StrDup(fname);
if (!cf->filename) {
ShouldCache = 0;
FCLOSE(fp);
free(cf);
return E_NO_MEM;
}
/* Read the file */
while(fp) {
r = ReadLineFromFile();
if (r) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return r;
}
/* Skip blank chars */
s = LineBuffer;
while (isspace(*s)) s++;
if (*s && *s!=';' && *s!='#') {
/* Add the line to the cache */
if (!cl) {
cf->cache = NEW(CachedLine);
if (!cf->cache) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
cl = cf->cache;
} else {
cl->next = NEW(CachedLine);
if (!cl->next) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
cl = cl->next;
}
cl->next = NULL;
cl->LineNo = LineNo;
cl->text = StrDup(s);
if (!cl->text) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
}
}
/* Put the cached file at the head of the queue */
cf->next = CachedFiles;
CachedFiles = cf;
return OK;
}
/***************************************************************/
/* */
/* PopFile - we've reached the end. Pop up to the previous */
/* file, or return E_EOF */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int PopFile(void)
#else
int PopFile()
#endif
{
IncludeStruct *i;
if (!Hush && NumIfs) Eprint("%s", ErrMsg[E_MISS_ENDIF]);
if (!IStackPtr) return E_EOF;
IStackPtr--;
i = &IStack[IStackPtr];
LineNo = i->LineNo;
IfFlags = i->IfFlags;
NumIfs = i->NumIfs;
CLine = i->CLine;
fp = NULL;
STRSET(FileName, i->filename);
if (!CLine && (i->offset != -1L)) {
/* We must open the file, then seek to specified position */
if (strcmp(i->filename, "-"))
fp = fopen(i->filename, "r");
else
fp = stdin;
if (!fp) return E_CANT_OPEN;
if (fp != stdin)
(void) fseek(fp, i->offset, 0); /* Trust that it works... */
}
free(i->filename);
return OK;
}
/***************************************************************/
/* */
/* DoInclude */
/* */
/* The INCLUDE command. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int DoInclude(ParsePtr p)
#else
int DoInclude(p)
ParsePtr p;
#endif
{
char tok[TOKSIZE];
int r, e;
if ( (r=ParseToken(p, tok)) ) return r;
e = VerifyEoln(p);
if (e) Eprint("%s", ErrMsg[e]);
if ( (r=IncludeFile(tok)) ) return r;
NumIfs = 0;
IfFlags = 0;
return OK;
}
/***************************************************************/
/* */
/* IncludeFile */
/* */
/* Process the INCLUDE command - actually do the file */
/* inclusion. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int IncludeFile(const char *fname)
#else
int IncludeFile(fname)
char *fname;
#endif
{
IncludeStruct *i;
int r;
if (IStackPtr+1 >= INCLUDE_NEST) return E_NESTED_INCLUDE;
i = &IStack[IStackPtr];
i->filename = StrDup(FileName);
if (!i->filename) return E_NO_MEM;
i->LineNo = LineNo;
i->NumIfs = NumIfs;
i->IfFlags = IfFlags;
i->CLine = CLine;
i->offset = -1L;
if (fp) {
i->offset = ftell(fp);
FCLOSE(fp);
}
IStackPtr++;
/* Try to open the new file */
if (!OpenFile(fname)) {
return OK;
}
/* Ugh! We failed! */
if ( (r=PopFile()) ) return r;
Eprint("%s: %s", ErrMsg[E_CANT_OPEN], fname);
return E_CANT_OPEN;
}
/***************************************************************/
/* */
/* GetAccessDate - get the access date of a file. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int GetAccessDate(char *file)
#else
int GetAccessDate(file)
char *file;
#endif
{
struct stat statbuf;
struct tm *t1;
if (stat(file, &statbuf)) return -1;
#ifdef __TURBOC__
t1 = localtime( (time_t *) &(statbuf.st_atime) );
#else
t1 = localtime(&(statbuf.st_atime));
#endif
if (t1->tm_year + 1900 < BASE)
return 0;
else
return Julian(t1->tm_year+1900, t1->tm_mon, t1->tm_mday);
}
/***************************************************************/
/* */
/* SetAccessDate */
/* */
/* Used only by DOS to set access date after we close the */
/* file. Not needed for UNIX. */
/* */
/***************************************************************/
#if defined(__MSDOS__)
/*
* WARNING WARNING WARNING WARNING
* In the version of Turbo C which I have, there is a bug in the
* stdio.h file. The following lines correct the bug. YOU MAY
* HAVE TO REMOVE THESE LINES FOR LATER VERSIONS OF TURBOC
*/
#ifdef __TURBOC__
#ifndef fileno
#define fileno(f) ((f)->fd)
#endif
#endif
#ifdef HAVE_PROTOS
PUBLIC int SetAccessDate(char *fname, int jul)
#else
int SetAccessDate(fname, jul)
char *fname;
int jul;
#endif
{
#ifdef __TURBOC__
int y, m, d;
struct ftime ft;
FILE *f;
FromJulian(jul, &y, &m, &d);
ft.ft_tsec = 0;
ft.ft_min = 0;
ft.ft_hour = 12; /* Arbitrarily set time to noon. */
ft.ft_day = (unsigned int) d;
ft.ft_month = (unsigned int) m+1;
ft.ft_year = (unsigned int) (y - 1980);
f = fopen(fname, "r");
if (!f || setftime(fileno(f) , &ft)) {
#else /* Must be MSC */
if (utime(fname, (struct utimbuf *) NULL)) {
#endif
fprintf(ErrFp, ErrMsg[M_CANTSET_ACCESS], fname);
#ifdef __TURBOC__
if (f) FCLOSE(f);
#endif
return -1;
}
#ifdef __TURBOC__
FCLOSE(f);
#endif
return 0;
}
#endif /* __MSDOS__ */
/***************************************************************/
/* */
/* DestroyCache */
/* */
/* Free all the memory used by a cached file. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void DestroyCache(CachedFile *cf)
#else
static void DestroyCache(cf)
CachedFile *cf;
#endif
{
CachedLine *cl, *cnext;
CachedFile *temp;
if (cf->filename) free(cf->filename);
cl = cf->cache;
while (cl) {
if (cl->text) free (cl->text);
cnext = cl->next;
free(cl);
cl = cnext;
}
if (CachedFiles == cf) CachedFiles = cf->next;
else {
temp = CachedFiles;
while(temp) {
if (temp->next == cf) {
temp->next = cf->next;
break;
}
temp = temp->next;
}
}
free(cf);
}
/***************************************************************/
/* */
/* TopLevel */
/* */
/* Returns 1 if current file is top level, 0 otherwise. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int TopLevel(void)
#else
int TopLevel()
#endif
{
return !IStackPtr;
}

2380
funcs.c

File diff suppressed because it is too large Load Diff

238
install-sh Executable file
View File

@@ -0,0 +1,238 @@
#! /bin/sh
#
# install - install a program, script, or datafile
# This comes from X11R5.
#
# Calling this script install-sh is preferred over install.sh, to prevent
# `make' implicit rules from creating a file called install from it
# when there is no Makefile.
#
# This script is compatible with the BSD install script, but was written
# from scratch.
#
# set DOITPROG to echo to test this script
# Don't use :- since 4.3BSD and earlier shells don't like it.
doit="${DOITPROG-}"
# put in absolute paths if you don't have them in your path; or use env. vars.
mvprog="${MVPROG-mv}"
cpprog="${CPPROG-cp}"
chmodprog="${CHMODPROG-chmod}"
chownprog="${CHOWNPROG-chown}"
chgrpprog="${CHGRPPROG-chgrp}"
stripprog="${STRIPPROG-strip}"
rmprog="${RMPROG-rm}"
mkdirprog="${MKDIRPROG-mkdir}"
transformbasename=""
transform_arg=""
instcmd="$mvprog"
chmodcmd="$chmodprog 0755"
chowncmd=""
chgrpcmd=""
stripcmd=""
rmcmd="$rmprog -f"
mvcmd="$mvprog"
src=""
dst=""
dir_arg=""
while [ x"$1" != x ]; do
case $1 in
-c) instcmd="$cpprog"
shift
continue;;
-d) dir_arg=true
shift
continue;;
-m) chmodcmd="$chmodprog $2"
shift
shift
continue;;
-o) chowncmd="$chownprog $2"
shift
shift
continue;;
-g) chgrpcmd="$chgrpprog $2"
shift
shift
continue;;
-s) stripcmd="$stripprog"
shift
continue;;
-t=*) transformarg=`echo $1 | sed 's/-t=//'`
shift
continue;;
-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
shift
continue;;
*) if [ x"$src" = x ]
then
src=$1
else
# this colon is to work around a 386BSD /bin/sh bug
:
dst=$1
fi
shift
continue;;
esac
done
if [ x"$src" = x ]
then
echo "install: no input file specified"
exit 1
else
true
fi
if [ x"$dir_arg" != x ]; then
dst=$src
src=""
if [ -d $dst ]; then
instcmd=:
else
instcmd=mkdir
fi
else
# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
# might cause directories to be created, which would be especially bad
# if $src (and thus $dsttmp) contains '*'.
if [ -f $src -o -d $src ]
then
true
else
echo "install: $src does not exist"
exit 1
fi
if [ x"$dst" = x ]
then
echo "install: no destination specified"
exit 1
else
true
fi
# If destination is a directory, append the input filename; if your system
# does not like double slashes in filenames, you may need to add some logic
if [ -d $dst ]
then
dst="$dst"/`basename $src`
else
true
fi
fi
## this sed command emulates the dirname command
dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
# Make sure that the destination directory exists.
# this part is taken from Noah Friedman's mkinstalldirs script
# Skip lots of stat calls in the usual case.
if [ ! -d "$dstdir" ]; then
defaultIFS='
'
IFS="${IFS-${defaultIFS}}"
oIFS="${IFS}"
# Some sh's can't handle IFS=/ for some reason.
IFS='%'
set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
IFS="${oIFS}"
pathcomp=''
while [ $# -ne 0 ] ; do
pathcomp="${pathcomp}${1}"
shift
if [ ! -d "${pathcomp}" ] ;
then
$mkdirprog "${pathcomp}"
else
true
fi
pathcomp="${pathcomp}/"
done
fi
if [ x"$dir_arg" != x ]
then
$doit $instcmd $dst &&
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
else
# If we're going to rename the final executable, determine the name now.
if [ x"$transformarg" = x ]
then
dstfile=`basename $dst`
else
dstfile=`basename $dst $transformbasename |
sed $transformarg`$transformbasename
fi
# don't allow the sed command to completely eliminate the filename
if [ x"$dstfile" = x ]
then
dstfile=`basename $dst`
else
true
fi
# Make a temp file name in the proper directory.
dsttmp=$dstdir/#inst.$$#
# Move or copy the file name to the temp name
$doit $instcmd $src $dsttmp &&
trap "rm -f ${dsttmp}" 0 &&
# and set any options; do chmod last to preserve setuid bits
# If any of these fail, we abort the whole thing. If we want to
# ignore errors from any of these, just make sure not to ignore
# errors from the above "$doit $instcmd $src $dsttmp" command.
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
# Now rename the file to the real destination.
$doit $rmcmd -f $dstdir/$dstfile &&
$doit $mvcmd $dsttmp $dstdir/$dstfile
fi &&
exit 0

42
kall
View File

@@ -1,42 +0,0 @@
#!/bin/sh
#
# $Id: kall,v 1.1 1996-03-27 03:25:59 dfs Exp $
#
# kall - kill all processes belonging to this user that match
# specified string.
signal=`echo $1 | grep '^\-.*'`
me=`basename $0`
if [ "$signal" != "" ]; then
shift
else
signal="-TERM"
fi
if [ "$1" = "" ]; then
echo "usage: $me [-signal] string [string...]"
echo " kills all of your processes where command name matches"
echo " any of the given strings."
exit
fi
msg="0"
while [ "$1" != "" ]; do
# NOTE: You may have to modify the next line, since PS is non-portable.
# The 'awk' command picks out the process IDs to pass them on to kill.
rprocs=`ps cx | awk '{if(prog == $NF && $1 != mypid) print $1}' prog=$1 mypid=$$ -`
if [ "$rprocs" != "" ]; then
msg="1"
echo -n "${me}: Sending $signal signal to $1 process(es)"
echo '...'
kill $signal $rprocs
fi
shift
done
if [ $msg = "1" ]; then
echo "${me}: Done."
fi

28
kall.1
View File

@@ -1,28 +0,0 @@
.\" $Id: kall.1,v 1.2 1996-04-28 02:01:58 dfs Exp $
.TH KALL 1 "26 February 1991"
.UC 4
.SH NAME
kall \- kill processes by command name
.SH SYNOPSIS
.B kall
[\-\fIsignal\fR] prog1 [prog2...]
.SH DESCRIPTION
.B Kall
sends the specified \fIsignal\fR (defaults to \fB-TERM\fR) to all processes
whose command name is specified on the command line. For example:
.PP
.nf
kall -HUP remind foobar
.fi
.PP
sends a \fBHUP\fR signal to all \fIremind\fR and \fIfoobar\fR programs.
Note that \fBkall\fR sends signals only to those processes owned by the
user invoking \fBkall\fR.
.SH AUTHOR
David F. Skoll
.SH BUGS
.B Kall
is a sh(1) script and depends on the behaviour of ps(1); thus, it is
not especially portable.
.SH SEE ALSO
remind, rem

20
lnk.bcc
View File

@@ -1,20 +0,0 @@
calendar.obj
dorem.obj
dosubst.obj
expr.obj
files.obj
funcs.obj
globals.obj
hbcal.obj
init.obj
main.obj
moon.obj
omit.obj
os2func.obj
queue.obj
sort.obj
token.obj
trigger.obj
userfns.obj
utils.obj
var.obj

23
lnk.msc
View File

@@ -1,23 +0,0 @@
calendar.obj +
dorem.obj +
dosubst.obj +
expr.obj +
files.obj +
funcs.obj +
globals.obj +
hbcal.obj +
init.obj +
main.obj +
moon.obj +
omit.obj +
sort.obj +
token.obj +
trigger.obj +
userfns.obj +
utils.obj +
var.obj
remind.exe
nul

19
lnk.tc
View File

@@ -1,19 +0,0 @@
-eremind.exe
calendar.obj
dorem.obj
dosubst.obj
expr.obj
files.obj
funcs.obj
globals.obj
hbcal.obj
init.obj
main.obj
moon.obj
omit.obj
sort.obj
token.obj
trigger.obj
userfns.obj
utils.obj
var.obj

View File

@@ -1,97 +0,0 @@
# Makefile for REMIND for Borland C++
# $Id: makefile.bcc,v 1.3 1996-09-28 18:17:07 dfs Exp $
VERSION= 03.00.15
MODEL=l
!if $d(__OS2__)
CFLAGS= -DOS2_POPUP -w-pia -O2
BINDIR= ..\OS2-EX
DELFLAG= /f
!else
CFLAGS= -w-pia -O2 -m$(MODEL)
BINDIR= ..\MSDOS-EX
DELFLAG=
!endif
HDRS= config.h err.h expr.h globals.h protos.h types.h version.h \
lang.h english.h german.h dutch.h finnish.h french.h norwgian.h \
danish.h polish.h
STDHDRS= config.h types.h protos.h globals.h err.h lang.h
LANGHDRS= english.h german.h dutch.h finnish.h french.h norwgian.h danish.h \
polish.h
SRCS= calendar.c dorem.c dosubst.c expr.c files.c funcs.c globals.c init.c \
main.c omit.c sort.c token.c trigger.c userfns.c utils.c var.c hbcal.c \
queue.c moon.c os2func.c
OBJS=calendar.obj dorem.obj dosubst.obj expr.obj files.obj funcs.obj \
globals.obj init.obj main.obj omit.obj sort.obj token.obj trigger.obj \
utils.obj userfns.obj var.obj hbcal.obj queue.obj moon.obj os2func.obj
all: exes test-rem.cmd test-rem.bat
test-rem
clean:
-del $(DELFLAG) *.obj
-del $(DELFLAG) $(BINDIR)\*.exe
exes: $(BINDIR)\remind.exe $(BINDIR)\rem2ps.exe
..\os2-ex\remind.exe: $(OBJS)
bcc -e..\os2-ex\remind @lnk.bcc -lap;Toe
..\msdos-ex\remind.exe: $(OBJS)
bcc -e..\msdos-ex\remind -m$(MODEL) @lnk.bcc
..\os2-ex\rem2ps.exe: rem2ps.obj
bcc -e..\os2-ex\rem2ps rem2ps.obj -lap;Toe
..\msdos-ex\rem2ps.exe: rem2ps.obj
bcc -e..\msdos-ex\rem2ps -m$(MODEL) rem2ps.obj
.c.obj:
bcc $(CFLAGS) -c {$< }
rem2ps.obj: rem2ps.c rem2ps.h config.h lang.h
calendar.obj: calendar.c $(STDHDRS) expr.h
dorem.obj: dorem.c $(STDHDRS) expr.h
dosubst.obj: dosubst.c $(STDHDRS) $(LANGHDRS)
expr.obj: expr.c $(STDHDRS) expr.h
files.obj: files.c $(STDHDRS)
funcs.obj: funcs.c $(STDHDRS) expr.h version.h
globals.obj: globals.c config.h types.h globals.h err.h lang.h
init.obj: init.c $(STDHDRS) expr.h version.h
main.obj: main.c $(STDHDRS) expr.h
moon.obj: moon.c $(STDHDRS) expr.h
omit.obj: omit.c $(STDHDRS)
os2func.obj: os2func.c $(STDHDRS)
queue.obj: queue.c $(STDHDRS)
sort.obj: sort.c $(STDHDRS)
token.obj: token.c $(STDHDRS)
trigger.obj: trigger.c $(STDHDRS) expr.h
userfns.obj: userfns.c $(STDHDRS) expr.h
utils.obj: utils.c $(STDHDRS)
var.obj: var.c $(STDHDRS) expr.h

View File

@@ -1,74 +0,0 @@
# Makefile for REMIND for Microsoft C for MSDOS
# $Id: makefile.msc,v 1.1 1996-03-27 03:26:01 dfs Exp $
OBJS= calendar.obj dorem.obj dosubst.obj expr.obj files.obj funcs.obj \
globals.obj init.obj main.obj omit.obj token.obj trigger.obj userfns.obj \
utils.obj var.obj sort.obj hbcal.obj moon.obj
DEFINES= /D__MSDOS__ /D__MSC__
MODEL= /AM
calendar.obj: calendar.c
cl /c $(DEFINES) $(MODEL) /Focalendar.obj calendar.c
dorem.obj: dorem.c
cl /c $(DEFINES) $(MODEL) /Fodorem.obj dorem.c
dosubst.obj: dosubst.c
cl /c $(DEFINES) $(MODEL) /Fodosubst.obj dosubst.c
expr.obj: expr.c
cl /c $(DEFINES) $(MODEL) /Foexpr.obj expr.c
hbcal.obj: hbcal.c
cl /c $(DEFINES) $(MODEL) /Fohbcal.obj hbcal.c
sort.obj: sort.c
cl /c $(DEFINES) $(MODEL) /Fosort.obj sort.c
files.obj: files.c
cl /c $(DEFINES) $(MODEL) /Fofiles.obj files.c
funcs.obj: funcs.c
cl /c $(DEFINES) $(MODEL) /Fofuncs.obj funcs.c
globals.obj: globals.c
cl /c $(DEFINES) $(MODEL) /Foglobals.obj globals.c
init.obj: init.c
cl /c $(DEFINES) $(MODEL) /Foinit.obj init.c
main.obj: main.c
cl /c $(DEFINES) $(MODEL) /Fomain.obj main.c
moon.obj: moon.c
cl /c $(DEFINES) $(MODEL) /Fomoon.obj moon.c
omit.obj: omit.c
cl /c $(DEFINES) $(MODEL) /Foomit.obj omit.c
token.obj: token.c
cl /c $(DEFINES) $(MODEL) /Fotoken.obj token.c
trigger.obj: trigger.c
cl /c $(DEFINES) $(MODEL) /Fotrigger.obj trigger.c
userfns.obj: userfns.c
cl /c $(DEFINES) $(MODEL) /Fouserfns.obj userfns.c
utils.obj: utils.c
cl /c $(DEFINES) $(MODEL) /Foutils.obj utils.c
var.obj: var.c
cl /c $(DEFINES) $(MODEL) /Fovar.obj var.c
remind.exe: $(OBJS)
link /NOI @lnk.msc
rem2ps.obj: rem2ps.c
cl /c $(DEFINES) $(MODEL) /Forem2ps.obj rem2ps.c
rem2ps.exe: rem2ps.obj
link /NOI rem2ps,rem2ps.exe,,,

View File

@@ -1,112 +0,0 @@
# Makefile for REMIND
#
# $Id: makefile.os2,v 1.2 1996-10-12 02:49:34 dfs Exp $
#
# THIS IS OUT OF DATE!
#
# - for GNU gcc (emx 0.8g kit) [executables for OS/2 2.x or DOS (32-bit)]
# - for Microsoft C 6.00A [executables for OS/2 or MSDOS (16-bit)]
# To use, enter "make -f Makefile.os2" (this makefile depends on its
# name being "Makefile.os2").
#
# Tested with dmake 3.8 and GNU make 3.68 under OS/2
default:
@echo "Enter $(MAKE) -f Makefile.os2 target "
@echo " where 'target' is chosen from "
@echo " msc OS/2 exe [Microsoft C 6.00a] "
@echo " mscbnd OS/2 and DOS exe [Microsoft C 6.00a] "
@echo " emx OS/2 and DOS 32-bit exe [EMX/gcc] "
msc:
$(MAKE) -f Makefile.os2 all \
CC="cl -nologo -AM" O=".obj" \
CFLAGS="-D__STDC__ -D__OS2__" \
LFLAGS="-Lp" \
LFLAGS2="setargv.obj remind.def -link /NOE"
mscbnd:
$(MAKE) -f Makefile.os2 all \
CC="cl -nologo -AM" O=".obj" \
CFLAGS="-D__STDC__ -D__OS2__ -D__MSDOS__" \
LFLAGS="-Lp" LBIND="-Fb" \
LFLAGS2="setargv.obj remind.def -link /NOE" \
BIND="bind remind /n DOSMAKEPIPE DOSCWAIT VIOENDPOPUP VIOPOPUP"
emx:
$(MAKE) -f Makefile.os2 all \
CC="gcc -O -s" O=".o" \
CFLAGS="-D__OS2__ -D__MSDOS__" \
LFLAGS=""
# OS2_POPUP enables Russ Herman's popup reminders
#OS2_POPUP =
OS2_POPUP = -DOS2_POPUP
HDRS= config.h err.h expr.h globals.h protos.h types.h version.h \
lang.h english.h german.h dutch.h finnish.h french.h norwgian.h \
danish.h polish.h
STDHDRS= config.h types.h protos.h globals.h err.h lang.h
LANGHDRS= english.h german.h dutch.h finnish.h french.h norwgian.h danish.h \
polish.h
SRCS= calendar.c dorem.c dosubst.c expr.c files.c funcs.c globals.c hbcal.c \
init.c main.c moon.c omit.c sort.c queue.c token.c trigger.c userfns.c \
utils.c var.c os2func.c
MANIFEST= README.UNIX README.DOS COPYRIGHT $(HDRS) $(SRCS) Makefile rem rem.1 \
remind.1 remind-all.csh remind-all.sh test.rem test-rem test.cmp makefile.tc \
makefile.msc lnk.msc lnk.tc MANIFEST.UNX MANIFEST.DOS WHATSNEW.30 kall kall.1 \
defs.rem README.OS2 makefile.os2 rem2ps.c rem2ps.h remind.def rem2ps.1 \
tstlang.rem README.BCC lnk.bcc makefile.bcc os2func.c \
test-rem.bat test-rem.cmd test1.cmp test2.cmp
OBJS= $(SRCS:.c=$O)
all: remind.exe rem2ps.exe
.c$O:
$(CC) -c $(CFLAGS) $(OS2_POPUP) $*.c
rem2ps.exe: rem2ps$O
$(CC) $(LFLAGS) $(LBIND) -o $@ rem2ps$O $(LFLAGS2)
remind.exe: $(OBJS)
$(CC) $(LFLAGS) -o $@ $(OBJS) $(LFLAGS2)
$(BIND)
clean:
rm -f *.o *.obj *~ core *.bak
clobber:
rm -f *.o *.obj *~ remind.exe rem2ps.exe test.out core *.bak
test:
test-rem.cmd
rem2ps$O: rem2ps.c rem2ps.h lang.h config.h
calendar$O: calendar.c $(STDHDRS) expr.h
dorem$O: dorem.c $(STDHDRS) expr.h
dosubst$O: dosubst.c $(STDHDRS) $(LANGHDRS)
expr$O: expr.c $(STDHDRS) expr.h
files$O: files.c $(STDHDRS)
funcs$O: funcs.c $(STDHDRS) expr.h version.h
globals$O: globals.c config.h types.h globals.h err.h lang.h $(LANGHDRS)
hbcal$O: hbcal.c $(STDHDRS)
init$O: init.c $(STDHDRS) expr.h version.h $(LANGHDRS)
main$O: main.c $(STDHDRS) expr.h
moon$O: moon.c $(STDHDRS)
omit$O: omit.c $(STDHDRS)
sort$O: sort.c $(STDHDRS)
queue$O: queue.c $(STDHDRS)
token$O: token.c $(STDHDRS)
trigger$O: trigger.c $(STDHDRS) expr.h
userfns$O: userfns.c $(STDHDRS) expr.h
utils$O: utils.c $(STDHDRS)
var$O: var.c $(STDHDRS) expr.h

View File

@@ -1,68 +0,0 @@
# Makefile for REMIND for Turbo C for MSDOS
# $Id: makefile.tc,v 1.3 1996-09-28 18:17:08 dfs Exp $
CC= tcc
VERSION= 03.00.15
HDRS= config.h err.h expr.h globals.h protos.h types.h version.h \
lang.h english.h german.h dutch.h finnish.h french.h norwgian.h \
danish.h polish.h
STDHDRS= config.h types.h protos.h globals.h err.h lang.h
LANGHDRS= english.h german.h dutch.h finnish.h french.h norwgian.h danish.h \
polish.h
SRCS= calendar.c dorem.c dosubst.c expr.c files.c funcs.c globals.c init.c \
moon.c main.c omit.c sort.c token.c trigger.c userfns.c utils.c var.c hbcal.c
OBJS=calendar.obj dorem.obj dosubst.obj expr.obj files.obj funcs.obj \
globals.obj init.obj main.obj omit.obj sort.obj token.obj trigger.obj \
utils.obj userfns.obj var.obj hbcal.obj
all: remind.exe rem2ps.exe
remind.exe: $(OBJS)
$(CC) @lnk.tc
rem2ps.exe: rem2ps.obj
$(CC) -erem2ps.exe rem2ps.obj
.c.obj:
$(CC) -w-pia -c -O -mm {$< }
rem2ps.obj: rem2ps.c rem2ps.h config.h lang.h
calendar.obj: calendar.c $(STDHDRS) expr.h
dorem.obj: dorem.c $(STDHDRS) expr.h
dosubst.obj: dosubst.c $(STDHDRS) $(LANGHDRS)
expr.obj: expr.c $(STDHDRS) expr.h
files.obj: files.c $(STDHDRS)
funcs.obj: funcs.c $(STDHDRS) expr.h version.h
globals.obj: globals.c config.h types.h globals.h err.h lang.h
init.obj: init.c $(STDHDRS) expr.h version.h
main.obj: main.c $(STDHDRS) expr.h
moon.obj: moon.c $(STDHDRS) expr.h
omit.obj: omit.c $(STDHDRS)
sort.obj: sort.c $(STDHDRS)
token.obj: token.c $(STDHDRS)
trigger.obj: trigger.c $(STDHDRS) expr.h
userfns.obj: userfns.c $(STDHDRS) expr.h
utils.obj: utils.c $(STDHDRS)
var.obj: var.c $(STDHDRS) expr.h

25
man/cm2rem.1 Normal file
View File

@@ -0,0 +1,25 @@
.TH CM2REM 1 "18 October 1999"
.UC 4
.SH NAME
cm2rem.tcl \- Convert Sun's "cm" input file to Remind format
.SH SYNOPSIS
.B cm2rem.tcl < cm_file > remind_file
.SH DESCRIPTION
\fBcm2rem.tcl\fR reads the Sun calendar manager data file and converts
it into a \fBRemind\fR script. Note that \fBcm2rem.tcl\fR can convert
\fIonly\fR version 3 calendar manager files. If you are using version 4
files, there should be a system utility to convert them to version 3 files.
.SH AUTHOR
\fBcm2rem.tcl\fR was written by Dianne Skoll <dianne@skoll.ca>.
.SH BUGS
Not all of the Sun calendar manager options are respected. In particular,
nothing is done for e-mail actions. Also, the resulting Remind script
is not editable with \fBTkRemind\fR; you can only edit it with a text
editor.
.PP
\fBcm2rem.tcl\fR requires Tcl/Tk version 8.0 or higher. The
\fBtclsh\fR interpreter must be on your \fBpath\fR.
.SH SEE ALSO
\fBremind(1)\fR, \fBtkremind(1)\fR

20
man/rem.1 Normal file
View File

@@ -0,0 +1,20 @@
.TH REM 1 "1 January 2020"
.UC 4
.SH NAME
rem \- Invoke Remind with a default filename
.SH SYNOPSIS
.B rem [\fIoptions\fR] [\fIdate\fR] [\fI*rep\fR] [\fItime\fR]
.SH DESCRIPTION
\fBrem\fR is a symbolic link to \fBremind\fR. When \fBremind\fR
determines that it has been invoked as \fBrem\fR, it uses a default
filename rather than expecting a filename to be supplied on the command
line.
.PP
If the environment variable DOTREMINDERS is set, \fBremind\fR uses the
value of DOTREMINDERS as the filename. Otherwise, \fBremind\fR uses
the filename $HOME/.reminders
.PP
.SH AUTHOR
Remind was written by Dianne Skoll <dianne@skoll.ca>
.SH SEE ALSO
\fBremind\fR

665
man/rem2ps.1 Normal file
View File

@@ -0,0 +1,665 @@
.TH REM2PS 1 "5 January 2021"
.UC 4
.SH NAME
rem2ps \- draw a PostScript calendar from Remind output
.SH SYNOPSIS
.B rem2ps [\fIoptions\fR]
.SH DESCRIPTION
\fBRem2ps\fR reads the standard input, which should be the results of
running \fBRemind\fR with the \fB\-p\fR or \fB\-pp\fR option. It
emits PostScript code (which draws a calendar) to the standard output.
.PP
See the section "Rem2PS Input Format" for details about the \fB\-p\fR
data. This may be useful if you wish to create other \fBRemind\fR
back-ends.
.SH OPTIONS
.TP
.B \-v
Be more verbose. This causes \fBRem2ps\fR to print progress messages
to the standard error stream. Normally, it is silent.
.TP
.B \-p file
Include the contents of \fIfile\fR in the PostScript prologue. This
allows you to define procedures, variables etc. which can be used
by the \fBPS\fR and \fBPSFILE\fR reminders. You should not
include any document structuring comments in your prologue.
.TP
.B \-l
Produce the calendar in landscape mode rather than the default
portrait mode.
.TP
.B \-x
When printing the calendar, place the day numbers in the top-left of each
day's box. If this option is omitted, the day numbers appear in the
top-right.
.TP
\fB\-c\fR[\fIn\fR]
If \fIn\fR is omitted, disables the small calendars for next and previous
months which are normally generated. If \fIn\fR is supplied, it can range
from 0 to 3, with the following meanings:
.RS
.TP
.B 0
Disable small calendars
.TP
.B 1
Place the small calendars at the bottom-right if there is room; otherwise,
place them at the top-left.
.TP
.B 2
Place the small calendars at the top-left if there is room; otherwise,
place them at the bottom-right.
.TP
.B 3
Place the previous month's small calendar at the top-left and the next
month's at the bottom-right if there is room; otherwise, follow \fIn\fR=1.
A moment's thought reveals that an option which splits the calendars if
there is room and otherwise follows \fIn\fR=2 yields the same results as
\fIn\fR=3.
.RE
.TP
.B \-i
Use ISO 8859-1 standard encoding for the PostScript fonts. If you do
not use this option, the default encoding is used.
.TP
.B \-e
Make the calendar fill the entire page. By default, the calendar is
slightly smaller than the page. This allows days with many reminders
to "expand" as needed. However, if you don't have days which expand,
you can use this option to make all of the boxes slightly bigger.
One caveat: If you do use the \fB\-e\fR option and one day has many
reminders, the calendar may expand off the page, losing some information.
Experiment!
.TP
.B \-m media
Set the page size. If you use the \-m option, you must specify the
media type, which can be one of the
following. (Sizes are approximate.)
.RS
.TP
Letter
8.5 x 11 in.
.TP
Legal
8.5 x 14 in.
.TP
Ledger
11 x 17 in.
.TP
Statement
5.5 x 8.5 in.
.TP
Executive
7.5 x 10 in.
.TP
A3
29.7 x 42 cm.
.TP
A4
21 x 29.7 cm.
.TP
A5
14.8 x 21 cm.
.TP
B4
25.7 x 36.4 cm.
.TP
B5
18.3 x 25.7 cm.
.TP
Folio
8.5 x 13 in.
.TP
Quarto
8.5 x 10.8 in.
.TP
10x14
10 x 14 in.
.TP
\fIX\fRx\fIY\fRin
\fIX\fR by \fIY\fR inches, where \fIX\fR and \fIY\fR can be floating-point
numbers.
.TP
\fIX\fRx\fIY\fRcm
\fIX\fR by \fIY\fR centimetres, where \fIX\fR and \fIY\fR can be floating-point
numbers.
.PP
Type "rem2ps \-m help" for a list of available media. Note that the media
type (and all \fBRem2ps\fR options) are case-sensitive. If you don't use
the \fB\-m\fR option, the media defaults to a compiled-in default - this
is usually Letter for North America and A4 for Europe. The "\-m help"
option will display the compiled-in default.
.RE
.TP
\fB\-f\fR[\fBtshed\fR] \fIfont\fR
Set the font for the calendar title,
the small calendars, the day-of-week headings, the calendar
entries, and the day numbers, respectively. \fIFont\fR must be the
name of a valid PostScript font. The default fonts are equivalent to
specifying:
.RS
.PP
.nf
\-ftshe Helvetica \-fd Helvetica-BoldOblique
.fi
.PP
In other words, the heading, entry and small-calendar fonts are set
to Helvetica, and the font for the day numbers is set to
Helvetica-BoldOblique.
.RE
.TP
\fB\-s\fR[\fBthed\fR] \fIsize\fR
Set the size (in points) of the text for the the calendar title,
day-of-week headings, the calendar entries, and the day numbers,
respectively. \fISize\fR must be a decimal number. The default sizes
are equivalent to specifying:
.RS
.PP
.nf
\-sthd 14 \-se 8
.fi
.PP
In other words, the heading and day numbers are 14-point fonts, and the
calendar entries are printed in 8-point text.
.RE
.TP
\fB\-b\fR \fIsize\fR
Set the size of the blank white border in each calendar box to \fIsize\fR
points. The default border size is 6 points, or 1/12 in.
.TP
\fB\-t\fR \fIsize\fR
Set the thickness of the black calendar grid lines. The default is 1,
for a line thickness of one point (1/72 in.)
.TP
\fB\-o\fR[\fBlrtb\fR] \fIsize\fR
Set the left, right, top, and/or bottom margins to \fIsize\fR points.
For this option only, \fIsize\fR must be an integer. It represents the
margin size in units of 1/72 in. The default margin sizes are 36, for
half-inch margins. If you wish to punch holes in the calendar page to insert
it into a binder, you may wish to increase the left margin to one inch.
In that case, you should also decrease the heading font size to 12 points
for good output:
.PP
.nf
# This gives good results for putting into a binder
rem2ps \-ol 72 \-sh 12
.fi
.SH USAGE
To use \fBRem2ps\fR, you should pipe the output of \fBRemind\fR with the \fB\-p\fR
option to \fBRem2ps\fR, and then send the result to a printer. This is most easily
illustrated with examples:
.PP
.nf
remind \-p12 /dev/null 1 jan 1994 | rem2ps | lpr \-Plaser
.fi
.PP
That example creates a blank calendar for the entire year of 1994, and
sends it the the printer named "laser."
.PP
.nf
remind \-p ~/.reminders | rem2ps \-l \-sd 18 > cal.ps
.fi
.PP
This reminder creates a calendar for the current month, filling in
entries from the reminder file "~/.reminders." The calendar is produced
in landscape mode, with a font size of 18 for the day numbers. The result
is put in the PostScript file "cal.ps."
.PP
.SH VARIABLES AVAILABLE TO USER-SUPPLIED POSTSCRIPT CODE
.PP
The following variables are available to \fBPS\fR and
\fBPSFILE\fR-type reminders. (This material is duplicated
in the \fBRemind\fR manual page.)
.TP
LineWidth
The width of the black grid lines making up the calendar.
.TP
Border
The border between the center of the grid lines and the space used to print
calendar entries. This border is normally blank space.
.TP
BoxWidth and BoxHeight
The width and height of the calendar box, from center-to-center of the
black gridlines.
.TP
InBoxHeight
The height from the center of the bottom black gridline to the top
of the regular calendar entry area. The space from here to the top
of the box is used only to draw the day number.
.TP
/DayFont, /TitleFont, /EntryFont, /SmallFont and /HeadFont
The fonts used to draw the day numbers, the month and year title,
the calendar entries, the small
calendars, and the day-of-week headings, respectively.
.TP
DaySize, TitleSize, EntrySize and HeadSize
The sizes of the above fonts. (The size of the small calendar font
is \fInot\fR defined here.) For example, if you wanted to print
the Hebrew date next to the regular day number in the calendar, use:
.PP
.nf
REM PS Border BoxHeight Border sub DaySize sub moveto \\
/DayFont findfont DaySize scalefont setfont \\
([hebday(today())] [hebmon(today())]) show
.fi
.PP
.RS
Note how /DayFont and DaySize are used.
.RE
.PP
Note that if you supply PostScript code, it is possible to produce invalid
PostScript files. Always test your PostScript thoroughly with a PostScript
viewer before sending it to the printer. You should not use any document
structuring comments in your PostScript code.
.PP
In addition, prior to drawing a calendar page, \fBRem2ps\fR emits
the following PostScript code:
.PP
.nf
save (mon) (yr) PreCal restore
.fi
.PP
where \fImon\fR and \fIyr\fR are the month and year of the calendar
page. The default \fBPreCal\fR procedure simply pops
the arguments and does nothing. However, you can define a \fBPreCal\fR
function in your prologue file to do whatever you want - it can draw a
background for the entire calendar, for instance.
.PP
In the context of the \fBPreCal\fR procedure, the following conditions
hold:
.TP
o
The PostScript origin is at the bottom left-hand corner of the page, and
PostScript units of 1/72 inch are in effect.
.TP
o
The variables MinX, MinY, MaxX and MaxY define the bounding box within
which the calendar will be drawn.
.TP
o
The font and font-size variables, as well as Border and LineWidth described
previously, are valid.
.PP
For an example, create a file called "myprolog" whose contents are:
.PP
.nf
/PreCal {
/yr exch def
/mon exch def
/xsiz1 MaxX MinX sub def
/ysiz1 MaxY MinY sub def
/xsiz xsiz1 MinX sub MinX sub def
/ysiz ysiz1 MinY sub MinY sub def
xsiz
ysiz
lt
{/len xsiz 1.41 mul def
MinX MinX add ysiz1 xsiz1 sub 2 div MinY add MinY add moveto}
{/len ysiz 1.41 mul def
xsiz1 ysiz1 sub 2 div MinX add MinX add MinY MinY add moveto}
ifelse
/Helvetica-Bold findfont 1 scalefont setfont
mon stringwidth pop
( ) stringwidth pop add
yr stringwidth pop add
len exch div /len exch def
/Helvetica-Bold findfont len scalefont setfont
0.95 setgray
45 rotate
mon show
( ) show
yr show
} bind def
.fi
.PP
Use that file with the \fBRem2ps\fR \fB\-p\fR option to create calendars
with the year and month in large grey letters in the background of the
calendar.
.PP
.SH REM2PS INPUT FORMAT (-P OPTION)
The \fB\-p\fR option is an older, simpler interchange format used by
\fBRemind\fR to communicate with back-ends. New back-ends are
encoraged to support the new \fB\-pp\fR format preferably, though they
are encouraged to support the older \fB\-p\fR format as well if the
older format contains enough information for them to work properly.
.PP
\fBRemind \-p\fR sends the following lines to standard output.
The information is designed to be easily parsed by back-end programs:
.TP
.B # rem2ps begin
This line signifies the start of calendar data. Back-ends can search
for it to verify they are being fed correct information.
.TP
\fImonth_name year num_days first_day monday_first\fR
On this line, \fImonth_name\fR is the name of the month whose calendar
information is about to follow. \fInum_days\fR is the number of days
in this month. \fIfirst_day\fR is the weekday of the first day of the
month (0 = Sunday, 1 = Monday, 6 = Saturday.) And \fImonday_first\fR is
1 if the \fB\-m\fR flag was supplied to \fBRemind\fR, or 0 if it was not.
All this information is supplied so back-ends don't need any date calculation
facilities.
.TP
\fIsun mon tue wed thu fri sat\fR
This line consists of
space-separated names of days in whatever language \fBRemind\fR was
compiled for. This information can be used by back-ends to annotate
calendars, and means they don't have to be created for a specific
language.
.TP
\fInext_mon next_days\fR
The name of the next month and the number of days in it.
.TP
\fIprev_mon prev_days\fR
The name of the previous month and the number of days in it. The
\fInext_mon\fR and \fIprev_mon\fR lines could be used to generate small
inset calendars for the next and previous months.
.PP
The remaining data consists of calendar entries, in the following format:
.PP
\fIyyyy/mm/dd special tag dur time body\fR
.PP
Here, \fIyyyy\fR is the year, \fImm\fR is the month (01-12) and
\fIdd\fR is the day of the month. Note that the date components are
always separated by "/" even if the date separator in \fBRemind\fR has
been set to "-". The consistent use of "/" is designed to ease parsing.
.PP
\fIspecial\fR is a string used
for "out-of-band" communication with back-ends. If the reminder
is a normal reminder, \fIspecial\fR is "*". The \fBRem2PS\fR
back-end understands the specials \fBPostScript\fR and \fBPSFile\fR.
Other back-ends may understand other specials. A back end should
\fIsilently ignore\fR a reminder with a special it doesn't understand.
.PP
\fItag\fR is whatever tag the user provided with the \fBTAG\fR clause,
or "*" if no tag was provided. If there is more than one \fBTAG\fR clause,
the tags appear in a comma-separated list. For example, the command
\fBREM TAG foo TAG bar TAG quux\fR would result in \fBfoo,bar,quux\fR
in the \fItag\fR field.
.PP
\fIdur\fR is the \fBDURATION\fR value in minutes, or "*" if no duration
was provided.
.PP
\fItime\fR is the time of the reminder in minutes past midnight, or
"*" if the reminder was not a timed reminder.
.PP
\fIbody\fR is the body of the reminder.
.PP
Future versions of \fBRemind\fR may add additional keys to the JSON
object. Back-ends \fImust\fR ignore keys they don't recognize.
.PP
After a month's worth of reminders have been emitted, \fBRemind\fR
emits the line:
.PP
\fB# rem2ps end
.PP
However, back-ends should keep reading until EOF in case more data for
subsequent months is forthcoming.
.PP
If you supply the \fB\-l\fR option to \fBremind\fR, then reminders
may be preceded by a line that looks like this:
.PP
\fB# fileinfo \fIlineno filename\fR
.PP
The word \fBfileinfo\fR is literal; \fIlineno\fR and \fIfilename\fR specify
the line number and file name of the file containing the reminder. Back-ends
that don't care about this information should ignore lines starting with
"#" (except, of course, for the # rem2ps lines.)
.PP
.SH REM2PS PARTIAL JSON INPUT FORMAT (-PP OPTION)
\fBRemind \-pp\fR sends the following lines to standard output. They
are designed to be easily parsed, but contain much more information
than the old-style \fBremind -p\fR output. The extra information
contains a representation of the parsed "REM" statement, which could
allow converters to better preserve semantics of a reminder. For
example, this format passes enough information to allow a back-end to
(in many cases) determine a reminder's recurrence rather than just treating
each reminder as a one-off event.
.PP
The lines emitted by \fBremind \-pp\fR are as follows:
.TP
.B # rem2ps2 begin
This line signifies the start of calendar data. Back-ends can search
for it to verify they are being fed correct information. Note the
"2" after "rem2ps", which distinguishes this format from the older \fB\-p\fR
format.
.TP
\fImonth_name year num_days first_day monday_first\fR
Same as the \fB\-p\fR format
.TP
\fIsun mon tue wed thu fri sat\fR
Same as the \fB\-p\fR format
.TP
\fInext_mon next_days\fR
Same as the \fB\-p\fR format
.TP
\fIprev_mon prev_days\fR
Same as the \fB\-p\fR format
.PP
.B CALENDAR ENTRIES
.PP
The remaining data consists of calendar entries expressed as a JSON object
on a single line. Each such line will begin with "{" and will be a well-formed
JSON object. The keys that may be present in the JSON object are as
follows:
.TP
.B date \fIYYYY-MM-DD\fR
The \fbdate\fR key will \fIalways\fR be present; it is the trigger date
of the reminder expressed as a string in the format \fIYYYY-MM-DD\fR
.TP
.B filename \fIf\fR
The filename in which the reminder was found.
.TP
.B lineno \fIn\fR
The line number within the file on which the reminder was found.
.TP
.B nonconst_expr 1
If the reminder contained a non-constant expression that had to be evaluated
to determine the trigger date, this key will be present with the value 1.
If this key is present, then it is unsafe for a back-end to rely on
recurrence semantics or even the semantics of any part of the parsed
reminder, as they may have been computed in a way that cannot be expressed
in JSON.
.TP
.B if_depth \fIn\fR
If the reminder is inside one or more IF or ELSE statements, this key
will be present and the value will be the number of nested IFs from
the top-level to the reminder. Back-ends should be wary of
interpreting recurrence semantics of reminders within an IF or ELSE
block.
.TP
.B passthru \fIspecial\fR
If the reminder was a SPECIAL reminder, the \fBpassthru\fR key will be
present and the value will be the type of SPECIAL (such as SHADE, COLOR,
MOON, etc.)
.TP
.B tags \fIdata\fR
If any TAG clauses are present, the \fBtag\fR key will be present and consist
of a comma-separated list of tags.
.TP
.B time \fIt\fR
If an AT clause was present, this key will contain the time of the AT clause
in minutes after midnight.
.TP
.B tdelta \fIn\fR
If a time delta (+n after an AT clause) was present, this key contains the
delta value in minutes.
.TP
.B trep \fIn\fR
If a time repeat (*n after an AT clause) was present, this key contains the
repeat value in minutes.
.TP
.B eventduration \fIn\fR
If a DURATION clause was present, this key contains the event duration in
minutes.
.TP
.B duration \fIn\fR
If a DURATION clause was present, this key contains today's duration in
minutes. See the \fBremind(1)\fR man page, "MULTI-DAY EVENTS", for a
discussion of duration vs. event duration.
.TP
.B eventstart \fIdt\fR
If an AT clause was present, this key contains the event start time in
the format \fIYYYY-MM-DDTHH:MM\fR.
.TP
.B back \fIn\fR
If the reminder contained a "back" clause (\-n or \-\-n), this key
contains the back value. If the "back" value was \-n, the value will
be positive; if it was \-\-n, the value will be negative.
.TP
.B delta \fIn\fR
If the reminder contained a "delta" clause (\+n or \+\+n), this key
contains the delta value. If the "delta" value was \+n, the value will
be positive; if it was \+\+n, the value will be negative.
.TP
.B rep \fIn\fR
If the reminder contained a "repeat" clause (*n), this key contains
the repeat value.
.TP
.B skip \fItype\fR
If the reminder contained a SKIP, BEFORE or AFTER keyword, then this
key will contain that keyword.
.TP
.B localomit \fIarray\fR
If the reminder contains a local OMIT keyword, this key will be present.
Its value will be an array of English day names that are OMITted.
.TP
.B wd \fIarray\fR
If the reminder contains one or more weekdays, this key will be present.
Its value will be an array of English day names that are present.
.TP
.B d \fIn\fR
If a day-of-month is present in the reminder specification, this key
will be present and its value will be the day number.
.TP
.B m \fIn\fR
If a month is present in the reminder specification, this key
will be present and its value will be the month number.
.TP
.B y \fIn\fR
If a year is present in the reminder specification, this key
will be present and its value will be the year.
.TP
.B until \fIYYYY-MM-DD\fR
If the reminder contains an UNTIL or THROUGH clause, this key
will be present. Its value will be a string of the form YYYY-MM-DD.
.TP
.B once 1
If the reminder contains a ONCE keyword, this key will be present
with a value of 1.
.TP
.B scanfrom \fIYYYY-MM-DD\fR
If the reminder contains a SCANFROM keyword, this key will be present
and its value will be a string of the form YYYY-MM-DD.
.TP
.B from \fIYYYY-MM-DD\fR
If the reminder contains a FROM keyword, this key will be present
and its value will be a string of the form YYYY-MM-DD.
.TP
.B priority \fIn\fR
The priority of the reminder. Always present; if no PRIORITY keyword
is specified, then a reminder has a default priority of 5000.
.TP
.B r \fIn\fR
For a SHADE or COLOR special, the red color component.
.TP
.B g \fIn\fR
For a SHADE or COLOR special, the green color component.
.TP
.B b \fIn\fR
For a SHADE or COLOR special, the blue color component.
.TP
.B body \fIbody\fR
The body of the reminder to issue. Always present.
.TP
.B rawbody \fIraw\fR
The "raw" body of the reminder, before any expression-pasting or
substitution-sequence processing. If the raw body would be the same
as the processed body, then this key is not present.
.PP
After a month's worth of reminders have been emitted, \fBRemind\fR
emits the line:
.PP
\fB# rem2ps2 end
.PP
However, back-ends should keep reading until EOF in case more data for
subsequent months is forthcoming.
.PP
.SH REM2PS PURE JSON INPUT FORMAT (-PPP OPTION)
\fBRemind \-ppp\fR emits \fIpure JSON\fR output. The format is
as follows:
.PP
\fBRemind\fR outputs a JSON array. Each element of the array is a
\fImonth descriptor\fR.
.PP
Each month descriptor is a JSON object with the following elements:
.TP
.B monthname \fIname\fR
The name of the month.
.TP
.B year \fIyyyy\fR
The year.
.TP
.B daysinmonnth \fIn\fR
The number of days in the current month.
.TP
.B firstwkday \fIn\fR
The weekday of the first day of the month (0 = Sunday, 1 = Monday, 6 = Saturday).
.TP
.B mondayfirst \fIn\fR
An indicator of whether or not the calendar week should start with
Sunday (n=0) or Monday (n=1).
.TP
.B daynames \fR[\fIdays\fR]
A seven-element array of day names; each element is a string representing
the names of the days from Sunday through Saturday.
.TP
.B prevmonthname \fIname\fR
The name of the previous month.
.TP
.B daysinprevmonth \fIn\fR
The number of days in the previous month.
.TP
.B prevmonthyear \fIyyyy\fR
The year of the previous month. (The same as \fByear\fR unless the current
month is January.)
.TP
.B nextmonthname \fIname\fR
The name of the following month.
.TP
.B daysinnextmonth \fIn\fR
The number of days in the following month.
.TP
.B nextmonthyear \fIyyyy\fR
The year of the following month. (The same as \fByear\fR unless the
current month is December.)
.TP
.B entries \fR[\fIarray\fR]
The \fBentries\fR key consists of an array of calendar entries; each
entry is a JSON object that has the same format as described in the
\fBCALENDAR ENTRIES\fR section in the \fB\-PP FORMAT\fR section,
\fIwith the following difference\fR: In \fB\-PP\fR mode, if a reminder
has \fB%"\fR markers, only the text between the markers
is included in the \fBbody\fR element. In \fB\-PPP\fR mode, the
entire text \fIincluding\fR the \fB%"\fR markers is included and it's up to
the back-end to extract the portion between the markers if that
is desired.
.SH AUTHOR
Rem2PS was written by Dianne Skoll <dianne@skoll.ca>
.SH BUGS
All \fBRem2ps\fR options are case-sensitive, unlike \fBRemind\fR.
Any time you supply
a font name or size, line thickness, or border width, it is treated as a
string and sent straight to the PostScript interpreter. Thus, if you
supply invalid fonts or sizes, \fBRem2ps\fR will not complain, but the
resulting PostScript output will probably not work.
.PP
You should ensure that the values you supply for margin widths are sensible.
If they are too big for the media size, \fBRem2ps\fR will not complain,
but again, the PostScript output will probably not work.
.SH SEE ALSO
\fBremind\fR

File diff suppressed because it is too large Load Diff

374
man/tkremind.1 Normal file
View File

@@ -0,0 +1,374 @@
.TH TKREMIND 1 "1 January 2020"
.UC 4
.SH NAME
tkremind \- graphical front-end to Remind calendar program
.SH SYNOPSIS
.B tkremind \fR[\fIoptions\fR] [\fIread_file\fR] [\fIwrite_file\fR]
.SH DESCRIPTION
\fBTkRemind\fR is a graphical front-end to the \fBRemind\fR program.
It provides a friendly graphical interface which allows you to view
your calendar and add reminders without learning the syntax of \fBRemind\fR.
Although not all of \fBRemind\fR's features are available with \fBTkRemind\fR,
\fBTkRemind\fR gives you an opportunity to edit the reminder commands which
it creates. This allows you to learn \fBRemind\fR's syntax and then add
extra features as you become a more sophisticated \fBRemind\fR programmer.
\fBTkRemind\fR is written in Tcl, and requires version 8.0
(or higher). It also requires a \fBwish\fR binary.
.SH OPTIONS
\fBTkRemind\fR itself has no options. However, it passes certain options
on to \fBRemind\fR. The options it passes are
\fB\-b\fR, \fB\-g\fR, \fB\-x\fR, \fB\-i\fR and \fB\-m\fR.
See the \fBRemind\fR man page for details about the options.
Note that \fBTkRemind\fR will respect the \fB\-m\fR and
\fB\-b1\fR options and adjust its appearance accordingly.
\fIRead_file\fR is the file from which \fBTkRemind\fR reads reminders.
It is in standard \fBRemind\fR format. \fIWrite_file\fR is the file
to which \fBTkRemind\fR writes reminders which you add using the GUI.
If \fIRead_file\fR is omitted, it defaults to \fB$HOME/.reminders\fR.
If \fIWrite_file\fR is omitted, it defaults to \fIRead_file\fR.
You may wish to have a different \fIWrite_file\fR from \fIRead_file\fR if
you want to collect all of \fBTkRemind\fR's reminders in one place. Suppose
your main file is \fI$HOME/.reminders\fR and you want \fBTkRemind\fR to put
its reminders in \fI$HOME/.tkreminders\fR. In \fI$HOME/.reminders\fR,
include the line:
.PP
.nf
INCLUDE [getenv("HOME")]/.tkreminders
.fi
.PP
.SH THE CALENDAR WINDOW
When you start \fBTkRemind\fR, it displays a calendar for the current
month, with today's date highlighted. Reminders are filled into each
box on the calendar. If a box contains many reminders, you can scroll
it up and down by dragging mouse button 2 in the box. Note that there
is no specific indication of an over-full box; you'll just have to
notice that the box appears completely full.
.SH NAVIGATING
To change to the previous or next month, click the \fB<\-\fR
or \fB\->\fR button, respectively. To change back to
the current month, click \fBToday\fR. To go to a specific month,
click \fBGo To Date...\fR. This pops up a dialog box which allows you
to select a month and enter a year. Once you've done this, click
\fBGo\fR to go to the date, or \fBCancel\fR to cancel.
To exit \fBTkRemind\fR, click \fBQuit\fR.
.SH ADDING REMINDERS
To add a reminder, click button 1 in any day number in the calendar.
The \fBAdd Reminder...\fR dialog will pop up, with values preselected for
the day you clicked.
The dialog has six basic groups of controls. The first three lines
select one of three types of reminders. Choose the type of reminder
with the radio buttons, and choose the values of the days, months, and
years by selecting values from pull-down menus. The pull-down menus
appear when you click the raised value buttons.
The next control specifies an expiry date for the reminder. Select
the check button to enable an expiry date, and fill in the values
using pull-down menus.
The third control specifies how much advance notice you want (if any),
and whether or not weekends and holidays are counted when computing advance
notice.
The fourth control specifies which days \fBRemind\fR considers
as part of the weekend. This can affect the interpretation of "weekday"
in the second and third types of reminders.
The fifth control associates a time with the reminder.
You can also specify advance notice, possibly repeating.
The sixth control specifies what \fBRemind\fR should do if a reminder
falls on a holiday or weekend.
Enter the body of the reminder into the \fBBody:\fR text entry.
To add the reminder to the reminder file, click \fBAdd to reminder file\fR.
To close the dialog without adding the reminder to the file, click
\fBCancel\fR. To preview the reminder, click \fBPreview reminder\fR.
This pops up the \fBPreview reminder\fR dialog box.
.SH PREVIEWING REMINDERS
The \fBPreview reminder\fR dialog box is an excellent way to learn
\fBRemind\fR. It displays the \fBRemind\fR command which realizes the
reminder you entered using the \fBAdd Reminder...\fR dialog. You can
edit the reminder, thereby gaining access to advanced features of
\fBRemind\fR. You can also use it simply to play around and discover
\fBRemind\fR's idioms for expressing different types of reminders.
.SH PRINTING
To print the current month's calendar, click \fBPrint...\fR on the
main calendar window. This brings up the print dialog. Printing
either produces a PostScript file or sends PostScript to a UNIX command.
Select the print destination by choosing either \fBTo file:\fR or
\fBTo command:\fR in the print dialog. Press \fBBrowse...\fR to bring
up a file browser. In the file browser, you can enter a filename in
the text entry, double-click on a filename in the listbox, or
double-click on a directory to navigate the file system. You can also
type the first few characters of a file name in the text entry box and
press space to complete the name to the first matching entry.
The \fBMatch:\fR box contains a filename wildcard which filters files
in the listbox. You can change the filter and press enter to rescan
the directory.
Select the appropriate paper size and orientation. Activate
\fBFill page\fR if you want the calendar to fill the page. This should
be the normal case unless you have many reminders in a particular
day. (See the \fBRem2PS\fR documentation.)
Finally, click \fBPrint\fR to print or \fBCancel\fR to cancel. Note
that during printing, \fBRemind\fR is called with the
\fB-itkremind=1\fR option and also an additional \fB-itkprint=1\fR
option.
.SH EDITING REMINDERS
If you created a reminder with \fBTkRemind\fR, it will turn red as the
mouse cursor passes over it in the calendar window. Click
button-1 over the reminder and you will be presented with a dialog
window whose state is identical to the one used to create the reminder.
At this point, you can change the reminder by editing the dialog
entries and selecting \fBReplace reminder\fR. You can delete the
reminder entirely by selecting \fBDelete reminder\fR. The remaining
buttons, \fBPreview reminder\fR and \fBCancel\fR operate identically
to the dialog in "ADDING REMINDERS."
Note that if you edit a reminder (using \fBPreview reminder\fR),
any edits you made are \fInot\fR retained in the dialog box. You
should not attempt to edit such reminders; you have to retype them
in the \fBPreview reminder\fR dialog.
If the reminder was not created with \fBTkRemind\fR, you can't edit
it with \fBTkRemind\fR.
.SH USING A TEXT EDITOR
If you have set the "text editor" option correctly, right-clicking
on a reminder will bring up a text editor on the file containing
the reminder. The cursor will be positioned on the line that
generated the reminder.
.SH BACKGROUND REMINDERS
If you create "timed" reminders, \fBTkRemind\fR will queue them in
the background and pop up boxes as they are triggered. Additionally,
if you created the reminder using \fBTkRemind\fR, you will be given the
option of "turning off" the reminder for the rest of the day.
\fBTkRemind\fR achieves queueing of background reminders by running
\fBRemind\fR in \fIserver mode\fR, described later.
.SH OPTIONS
The final button on the calendar window, \fBOptions\fR, lets you configure
certain aspects of \fBTkRemind\fR. The configuration options are:
.TP
.B Start up Iconified
If this is selected, \fBTkRemind\fR starts up iconified. Otherwise,
it starts up in a normal window.
.TP
.B Show Today's Reminders on Startup
If this is selected, \fBTkRemind\fR shows a text window containing reminders
which would be issued by "remind \-q \-a \-r" on startup, and when the date
changes at midnight.
.TP
.B Confirm Quit
If this is selected, you will be asked to confirm when you press
\fBQuit\fR. If not, \fBTkRemind\fR quits without prompting.
.TP
.B Automatically close pop-up reminders after a minute
If this is selected, pop-up reminder boxes will be closed after one minute
has elapsed. Otherwise, they remain on your screen forever until you
explicitly dismiss them.
.TP
.B Beep terminal when popping up a reminder
If selected, \fBTkRemind\fR beeps the terminal bell when a queued reminder
pops up.
.TP
.B Deiconify calendar window when popping up a reminder
If selected, does what it says.
.TP
.B Run command when popping up a reminder
If this entry is not blank, the specified command is run whenever a
background reminder pops up.
.TP
.B Feed popped-up reminder to command's standard input
If selected, feeds the text of the reminder to the command described
above. The text of the reminder is prefixed by "HH:MM ", where HH:MM
is the time of the reminder.
.TP
.B E-mail reminders here if popup not dismissed
If you enter a non-blank e-mail address in this field, then \fBTkRemind\fR
will e-mail you a reminder if you don't dismiss the popup box within
one minute. This is useful if you need to leave your terminal but
want your reminders to "follow" you via e-mail.
.TP
.B Name or IP address of SMTP server
\fBTkRemind\fR uses a direct SMTP connection to send mail. Enter the
IP address of your SMTP server here.
.TP
.B Text Editor
This specifies a text editor to invoke when a reminder is right-clicked.
The characters "%d" are replaced with the lined number of the file
containing the reminder, and "%s" are replaced with the file name.
Useful strings might be "emacs +%d %s" or "gvim +%d %s"
.PP
Once you've configured the options the way you like them,
press \fBApply Options\fR to put them into effect, \fBSave Options\fR
to put them into effect and save them in $HOME/.tkremindrc, or
\fBCancel\fR to cancel any changes you made.
.SH KEYBOARD SHORTCUTS
\fBTkRemind\fR's main window includes the following keyboard shortcuts:
.TP
.B Ctrl-Q
Quit
.TP
.B Left Arrow
Previous Month
.TP
.B Right Arrow
Next Month
.TP
.B Home
Today
.SH ODDS AND ENDS
\fBTkRemind\fR performs some basic consistency checks when you add or
preview a reminder. However, if you edit a reminder in the previewer,
\fBTkRemind\fR does \fInot\fR check the edited reminder. You can
produce illegal reminders which may cause problems. (This is one good
reason to isolate \fBTkRemind\fR's reminders in a separate file.)
.PP
\fBTkRemind\fR does \fInot\fR check the body of the reminder in any
way. You can use the normal \fBRemind\fR substitution sequences in
the body. Furthermore, if you use expression-pasting in the body,
\fBTkRemind\fR does \fInot\fR validate the expressions.
.PP
When \fBTkRemind\fR invokes \fBRemind\fR, it supplies the option:
.PP
.nf
\-itkremind=1
.fi
.PP
on the command line. So, in your \fBRemind\fR file, you can include:
.PP
.nf
IF defined("tkremind")
# Then I'm probably being invoked by TkRemind
ENDIF
.fi
.PP
You can use this to activate certain reminders in different ways
for \fBTkRemind\fR (for example).
.PP
\fBTkRemind\fR uses tags to keep track of reminders in the
script file. It also places special comments in the reminder
file to store additional state. You can certainly mix
"hand-crafted" reminders with reminders created by \fBTkRemind\fR
if you are aware of the following rules and limitations:
.TP
o
\fBTkRemind\fR uses \fBTAG\fRs of the form \fBTKTAG\fR\fInnn\fR
where \fInnn\fR is a number. You should not use such \fBTAG\fRs
in hand-crafted reminders.
.TP
o
Do not edit lines starting with "# TKTAGnnn", "# TKEND", or any
lines in between. You can move such lines, but be careful to move
them as a single block.
.TP
o
Hand-crafted reminders cannot be edited with \fBTkRemind\fR, and
for hand-crafted timed reminders, you will not be presented with
the "Don't remind me again" option when they pop up.
.SH SERVER MODE
\fBRemind\fR has a special mode for interacting with programs like
\fBTkRemind\fR. This mode is called \fIserver mode\fR and is
selected by supplying the \fB\-z0\fR option to \fBRemind\fR.
In server mode, \fBRemind\fR operates similar to daemon mode, except
it reads commands (one per line)
from standard input and writes status lines to standard output.
The commands accepted in server mode are:
.TP
EXIT
Terminate the \fBRemind\fR process. EOF on standard input does the
same thing.
.TP
STATUS
Return the number of queued reminders.
.TP
REREAD
Re-read the reminder file
.PP
The status lines written are as follows:
.TP
NOTE reminder \fItime\fR \fItag\fR
Signifies the beginning of a timed reminder whose trigger time is
\fItime\fR with tag \fItag\fR. If the reminder has no tag, an
asterisk is supplied for \fItag\fR. All lines following this line
are the body of the reminder, until the line \fBNOTE endreminder\fR
is transmitted.
.TP
NOTE newdate
This line is emitted whenever \fBRemind\fR has detected a rollover of
the system date. The front-end program should redraw its calendar
or take whatever other action is needed.
.TP
NOTE reread
This line is emitted whenever the number of reminders in \fBRemind\fR's
queue changes because of a date rollover or a \fBREREAD\fR command.
The front-end should issue a \fBSTATUS\fR command in response to this
message.
.TP
NOTE queued \fIn\fR
This line is emitted in response to a \fBSTATUS\fR command. The number
\fIn\fR is the number of reminders in the queue.
.SH AUTHOR
TkRemind was written by Dianne Skoll <dianne@skoll.ca>
\fBTkRemind\fR is Copyright 1996-2020 by Dianne Skoll.
.SH FILES
$HOME/.reminders -- default reminder file.
$HOME/.tkremindrc -- \fBTkRemind\fR saved options.
.SH SEE ALSO
remind, rem2ps

158
os2func.c
View File

@@ -1,158 +0,0 @@
/***************************************************************/
/* */
/* OS2FUNC.C */
/* */
/* Functions to support OS/2. */
/* */
/* This file is part of REMIND. */
/* */
/* This file is Copyright (C) 1993 by Russ Herman. */
/* REMIND is Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: os2func.c,v 1.1 1996-03-27 03:26:04 dfs Exp $";
#ifdef OS2_POPUP
#define INCL_VIO
#define INCL_KBD
#endif
#ifdef _MSC_VER
#define INCL_DOSPROCESS
#endif
#if defined(OS2_POPUP) || defined(_MSC_VER)
#include <os2.h>
#endif
#ifdef OS2_POPUP
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifdef OS2DBG
#include <dos.h>
#include <stdlib.h>
#endif
#include "config.h"
#include "globals.h"
/* EMX defines PS_TYPE, so we undefine it here to avoid
a redefinition warning when we include "types.h" */
#ifdef PS_TYPE
#undef PS_TYPE
#endif
#include "types.h"
#include "protos.h"
#ifdef _MSC_VER
typedef USHORT APIRET;
#endif
static APIRET apiret = 0;
static KBDKEYINFO kbci;
static char *pszPressAny = "\r\nPress any key to continue";
static USHORT pflags = VP_WAIT; /* | VP_TRANSPARENT; */
static HKBD hkbd = 0;
static char VioSubstBuffer[SHELLSIZE + 1];
void StartPopUp()
{
if (OS2MODE)
if (!(DebugFlag & DB_ECHO_LINE))
VioPopUp(&pflags, 0);
}
void EndPopUp()
{
if (DebugFlag & DB_ECHO_LINE)
return;
if (OS2MODE) {
VioWrtTTY(pszPressAny, strlen(pszPressAny), 0);
KbdCharIn(&kbci, IO_WAIT, hkbd);
VioEndPopUp(0);
}
}
int PutsPopUp(char *s)
{
char c, *os = VioSubstBuffer;
if (DebugFlag & DB_ECHO_LINE)
printf("%s", s);
else {
do {
/* Convert \n to \r\n in auxiliary buffer for VIO */
if ((c= *s++) == '\n')
*os++ = '\r';
*os++ = c;
} while (c > 0);
VioWrtTTY(VioSubstBuffer, strlen(VioSubstBuffer), 0);
}
return(0);
}
int PutlPopUp(char *s)
{
StartPopUp();
PutsPopUp(s);
if (DebugFlag & DB_ECHO_LINE)
fputc('\n', stdout);
else
VioWrtTTY("\r\n", 2, 0);
EndPopUp();
return(0);
}
int PutcPopUp(int c)
{
char *s = " ";
if (DebugFlag & DB_ECHO_LINE)
fputc(c, stdout);
else {
switch (c) {
case '\n':
VioWrtTTY("\r\n", 2, 0);
break;
default:
s[0] = c;
VioWrtTTY(s, 1, 0);
break;
}
}
return(0);
}
#ifdef OS2DBG
#define DB_ECHO_LINE 16
int DebugFlag = 0;
void main(/* int argc, char **argv */)
{
int ret;
ret = os2fputs("Test VIO PopUp Writing");
if (ret)
fprintf(stderr, "Test VIO PopUP Writing returned %d %ld",
ret, apiret);
exit(ret);
}
#endif
#endif
#ifdef _MSC_VER
unsigned sleep(unsigned sec)
{
return DosSleep(sec * 1000L);
}
#endif
#ifndef __EMX__
int fork()
{
return(-1);
}
#endif

176
protos.h
View File

@@ -1,176 +0,0 @@
/***************************************************************/
/* */
/* PROTOS.H */
/* */
/* Function Prototypes. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
/* $Id: protos.h,v 1.2 1996-03-31 04:01:57 dfs Exp $ */
#ifdef HAVE_PROTOS
#define ARGS(x) x
#else
#define ARGS(x) ()
#endif
/* Define a string assignment macro - be careful!!! */
#define STRSET(x, str) { if (x) free(x); (x) = StrDup(str); }
/* Define a general malloc routine for creating pointers to objects */
#define NEW(type) ((type *) malloc(sizeof(type)))
#ifdef NO_STRSTR
char *strstr ARGS ((char *s1, char *s2));
#endif
int CallUserFunc ARGS ((char *name, int nargs));
int DoFset ARGS ((ParsePtr p));
void ProduceCalendar ARGS ((void));
char *SimpleTime ARGS ((int tim, char *out));
int DoRem ARGS ((ParsePtr p));
int DoFlush ARGS ((ParsePtr p));
void DoExit ARGS ((ParsePtr p));
int ParseRem ARGS ((ParsePtr s, Trigger *trig, TimeTrig *tim));
#ifdef OS2_POPUP
int TriggerReminder ARGS ((ParsePtr p, Trigger *t, TimeTrig *tim, int jul,
int AsPopUp));
#else
int TriggerReminder ARGS ((ParsePtr p, Trigger *t, TimeTrig *tim, int jul));
#endif
int ShouldTriggerReminder ARGS ((Trigger *t, TimeTrig *tim, int jul));
int DoSubst ARGS ((ParsePtr p, char *out, Trigger *t, TimeTrig *tt, int jul, int mode));
int DoSubstFromString ARGS ((char *source, char *dest, int jul, int tim));
int EvalExpr ARGS ((char **e, Value *v));
int DoCoerce ARGS ((char type, Value *v));
void PrintValue ARGS ((Value *v, FILE *fp));
int CopyValue ARGS ((Value *dest, const Value *src));
int ReadLine ARGS ((void));
int OpenFile ARGS ((const char *fname));
int PopFile ARGS ((void));
int DoInclude ARGS ((ParsePtr p));
int IncludeFile ARGS ((const char *fname));
int GetAccessDate ARGS ((char *file));
int SetAccessDate ARGS ((char *fname, int jul));
int TopLevel ARGS ((void));
int CallFunc ARGS ((Operator *f, int nargs));
void InitRemind ARGS ((int argc, char *argv[]));
void Usage ARGS ((void));
int main ARGS ((int argc, char *argv[]));
int Julian ARGS ((int year, int month, int day));
void FromJulian ARGS ((int jul, int *y, int *m, int *d));
int ParseChar ARGS ((ParsePtr p, int *err, int peek));
int ParseToken ARGS ((ParsePtr p, char *out));
int ParseIdentifier ARGS ((ParsePtr p, char *out));
int EvaluateExpr ARGS ((ParsePtr p, Value *v));
int Evaluate ARGS ((char **s, Var *locals));
int FnPopValStack ARGS ((Value *val));
void Eprint ARGS ((const char *fmt, ...));
void OutputLine ARGS ((FILE *fp));
void CreateParser ARGS ((char *s, ParsePtr p));
void DestroyParser ARGS ((ParsePtr p));
void PushToken ARGS ((const char *tok));
long SystemTime ARGS ((int realtime));
int SystemDate ARGS ((int *y, int *m, int *d));
int DoIf ARGS ((ParsePtr p));
int DoElse ARGS ((ParsePtr p));
int DoEndif ARGS ((ParsePtr p));
int DoIfTrig ARGS ((ParsePtr p));
int ShouldIgnoreLine ARGS ((void));
int VerifyEoln ARGS ((ParsePtr p));
int DoDebug ARGS ((ParsePtr p));
int DoBanner ARGS ((ParsePtr p));
int DoRun ARGS ((ParsePtr p));
int DoErrMsg ARGS ((ParsePtr p));
int ClearGlobalOmits ARGS ((void));
int DoClear ARGS ((ParsePtr p));
int DestroyOmitContexts ARGS ((void));
int PushOmitContext ARGS ((ParsePtr p));
int PopOmitContext ARGS ((ParsePtr p));
int IsOmitted ARGS ((int jul, int localomit));
int DoOmit ARGS ((ParsePtr p));
int QueueReminder ARGS ((ParsePtr p, int typ, TimeTrig *tim, const char *sched));
void HandleQueuedReminders ARGS ((void));
char *FindInitialToken ARGS ((Token *tok, char *s));
void FindToken ARGS ((const char *s, Token *tok));
void FindNumericToken ARGS ((const char *s, Token *t));
int ComputeTrigger ARGS ((int today, Trigger *trig, int *err));
char *StrnCpy ARGS ((char *dest, const char *source, int n));
int StrMatch ARGS ((const char *s1, const char *s2, int n));
int StrinCmp ARGS ((const char *s1, const char *s2, int n));
char *StrDup ARGS ((const char *s));
int StrCmpi ARGS ((const char *s1, const char *s2));
Var *FindVar ARGS ((const char *str, int create));
int DeleteVar ARGS ((const char *str));
int SetVar ARGS ((const char *str, Value *val));
int GetVarValue ARGS ((const char *str, Value *val, Var *locals));
int DoSet ARGS ((Parser *p));
int DoUnset ARGS ((Parser *p));
int DoDump ARGS ((ParsePtr p));
void DumpVarTable ARGS ((void));
void DestroyVars ARGS ((int all));
int PreserveVar ARGS ((char *name));
int DoPreserve ARGS ((Parser *p));
int DoSatRemind ARGS ((Trigger *trig, TimeTrig *tim, ParsePtr p));
void DoMsgCommand ARGS ((char *cmd, char *msg));
int ParseNonSpaceChar ARGS ((ParsePtr p, int *err, int peek));
unsigned int HashVal ARGS ((const char *str));
int DateOK ARGS ((int y, int m, int d));
Operator *FindFunc ARGS ((char *name, Operator where[], int num));
int InsertIntoSortBuffer ARGS ((int jul, int tim, char *body, int typ, int prio));
void IssueSortedReminders ARGS ((void));
int UserFuncExists ARGS ((char *fn));
void JulToHeb ARGS((int jul, int *hy, int *hm, int *hd));
int HebNameToNum ARGS((const char *mname));
char *HebMonthName ARGS((int m, int y));
int RoshHashana ARGS((int i));
long DaysToHebYear ARGS((int y));
int DaysInHebYear ARGS((int y));
char *DaysInHebMonths ARGS((int ylen));
int HebToJul ARGS((int hy, int hm, int hd));
int GetValidHebDate ARGS((int yin, int min, int din, int adarbehave, int *mout, int *dout, int yahr));
int GetNextHebrewDate ARGS((int julstart, int hm, int hd, int yahr, int adarbehave, int *ans));
int ComputeJahr ARGS ((int y, int m, int d, int *ans));
int GetSysVar ARGS ((const char *name, Value *val));
int SetSysVar ARGS ((const char *name, Value *val));
void DumpSysVarByName ARGS ((const char *name));
int CalcMinsFromUTC ARGS ((int jul, int tim, int *mins, int *isdst));
#ifdef OS2_POPUP
void FillParagraph ARGS ((char *s, int AsPopUp));
#else
void FillParagraph ARGS ((char *s));
#endif
void LocalToUTC ARGS ((int locdate, int loctime, int *utcdate, int *utctime));
void UTCToLocal ARGS ((int utcdate, int utctime, int *locdate, int *loctime));
int MoonPhase ARGS ((int date, int time));
void HuntPhase ARGS ((int startdate, int starttim, int phas, int *date, int *time));
int CompareRems ARGS ((int dat1, int tim1, int prio1, int dat2, int tim2, int prio2, int bydate, int bytime, int byprio));
#ifdef __BORLANDC__
void __cdecl SigIntHandler ARGS ((int d));
#else
#ifdef SIGHANDLER_INT_ARG
void SigIntHandler ARGS ((int d));
#else
void SigIntHandler ARGS ((void));
#endif
#endif
void GotSigInt ARGS ((void));
#if defined(__OS2__)
int fork ARGS ((void));
#if defined(OS2_POPUP)
void StartPopUp ARGS ((void));
void EndPopUp ARGS ((void));
int PutcPopUp ARGS ((int c));
int PutlPopUp ARGS ((char *s));
int PutsPopUp ARGS ((char *s));
#endif
#endif
#ifdef BROKEN_PUTC
int SafePutChar ARGS ((int ch));
int SafePutc ARGS ((int ch, FILE *fp));
#endif

412
queue.c
View File

@@ -1,412 +0,0 @@
/***************************************************************/
/* */
/* QUEUE.C */
/* */
/* Queue up reminders for subsequent execution. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: queue.c,v 1.1 1996-03-27 03:26:05 dfs Exp $";
#include "config.h"
/* We only want object code generated if we have queued reminders */
#ifdef HAVE_QUEUED
#include <stdio.h>
#include <string.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#ifdef HAVE_UNISTD
#include <unistd.h>
#endif
#if defined(__OS2__) || defined(__MSDOS__)
#include <io.h>
#if defined(__BORLANDC__)
#include <dos.h>
#endif
#include <process.h>
#endif
#include "globals.h"
#include "err.h"
#include "types.h"
#include "protos.h"
#include "expr.h"
/* List structure for holding queued reminders */
typedef struct queuedrem {
struct queuedrem *next;
int typ;
int RunDisabled;
int ntrig;
char *text;
char sched[VAR_NAME_LEN+1];
TimeTrig tt;
} QueuedRem;
/* Global variables */
static QueuedRem *QueueHead;
static time_t FileModTime;
static struct stat StatBuf;
PRIVATE void CheckInitialFile ARGS ((void));
PRIVATE int CalculateNextTime ARGS ((QueuedRem *q));
PRIVATE QueuedRem *FindNextReminder ARGS ((void));
PRIVATE int CalculateNextTimeUsingSched ARGS ((QueuedRem *q));
/***************************************************************/
/* */
/* QueueReminder */
/* */
/* Put the reminder on a queue for later, if queueing is */
/* enabled. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int QueueReminder(ParsePtr p, int typ, TimeTrig *tim, const char *sched)
#else
int QueueReminder(p, typ, tim, sched)
ParsePtr p;
int typ;
TimeTrig *tim;
char *sched;
#endif
{
QueuedRem *qelem;
if (DontQueue ||
tim->ttime == NO_TIME ||
typ == CAL_TYPE ||
tim->ttime < SystemTime(0) / 60 ||
((typ == RUN_TYPE) && RunDisabled)) return OK;
qelem = NEW(QueuedRem);
if (!qelem) {
return E_NO_MEM;
}
qelem->text = StrDup(p->pos); /* Guaranteed that parser is not nested. */
if (!qelem->text) {
free(qelem);
return E_NO_MEM;
}
qelem->typ = typ;
qelem->tt = *tim;
qelem->next = QueueHead;
qelem->RunDisabled = RunDisabled;
qelem->ntrig = 0;
strcpy(qelem->sched, sched);
QueueHead = qelem;
NumQueued++;
return OK;
}
/***************************************************************/
/* */
/* HandleQueuedReminders */
/* */
/* Handle the issuing of queued reminders in the background */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC void HandleQueuedReminders(void)
#else
void HandleQueuedReminders()
#endif
{
QueuedRem *q = QueueHead;
long TimeToSleep;
unsigned SleepTime;
Parser p;
Trigger trig;
/* Suppress the BANNER from being issued */
NumTriggered = 1;
/* If we are not connected to a tty, then we must close the
* standard file descriptors. This is to prevent someone
* doing:
* remind file | <filter> | >log
* and have <filter> hung because the child (us) is still
* connected to it. This means the only commands that will be
* processed correctly are RUN commands, provided they mail
* the result back or use their own resource (as a window).
*/
if (!DontFork && (!isatty(1) || !isatty(2))) {
close(1);
close(2);
}
/* If we're a daemon, get the mod time of initial file */
if (Daemon) {
if (stat(InitialFile, &StatBuf)) {
fprintf(ErrFp, "Cannot stat %s - not running as daemon!\n",
InitialFile);
Daemon = 0;
} else FileModTime = StatBuf.st_mtime;
}
/* Initialize the queue - initialize all the entries time of issue */
while (q) {
q->tt.nexttime = (int) (SystemTime(0)/60 - 1);
q->tt.nexttime = CalculateNextTime(q);
q = q->next;
}
#ifdef __BORLANDC__
signal(SIGINT, SigIntHandler);
#else
if (!DontFork || Daemon) signal(SIGINT, SigIntHandler);
#endif
/* Sit in a loop, issuing reminders when necessary */
while(1) {
q = FindNextReminder();
/* If no more reminders to issue, we're done unless we're a daemon. */
if (!q && !Daemon) break;
if (Daemon && !q)
TimeToSleep = (long) 60*Daemon;
else
TimeToSleep = (long) q->tt.nexttime * 60L - SystemTime(0);
while (TimeToSleep > 0L) {
SleepTime = (unsigned) ((TimeToSleep > 30000L) ? 30000 : TimeToSleep);
if (Daemon && SleepTime > 60*Daemon) SleepTime = 60*Daemon;
sleep(SleepTime);
if (Daemon && SleepTime) CheckInitialFile();
if (Daemon && !q)
TimeToSleep = (long) 60*Daemon;
else
TimeToSleep = (long) q->tt.nexttime * 60L - SystemTime(0);
}
/* Trigger the reminder */
CreateParser(q->text, &p);
trig.typ = q->typ;
RunDisabled = q->RunDisabled;
#ifdef OS2_POPUP
(void) TriggerReminder(&p, &trig, &q->tt, JulianToday, 1);
#else
(void) TriggerReminder(&p, &trig, &q->tt, JulianToday);
#endif
fflush(stdout);
/* Calculate the next trigger time */
q->tt.nexttime = CalculateNextTime(q);
}
#ifdef __BORLANDC__
signal(SIGINT, SIG_DFL);
#endif
exit(0);
}
/***************************************************************/
/* */
/* CalculateNextTime */
/* */
/* Calculate the next time when a reminder should be issued. */
/* Return NO_TIME if reminder expired. */
/* Strategy is: If a sched() function is defined, call it. */
/* Otherwise, use AT time with delta and rep. If sched() */
/* fails, revert to AT with delta and rep. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int CalculateNextTime(QueuedRem *q)
#else
static int CalculateNextTime(q)
QueuedRem *q;
#endif
{
int tim = q->tt.ttime;
int rep = q->tt.rep;
int delta = q->tt.delta;
int curtime = q->tt.nexttime+1;
int r;
/* Increment number of times this one has been triggered */
q->ntrig++;
if (q->sched[0]) {
r = CalculateNextTimeUsingSched(q);
if (r != NO_TIME) return r;
}
if (delta == NO_DELTA)
if (tim < curtime) return NO_TIME; else return tim;
tim -= delta;
if (rep == NO_REP) rep = delta;
if (tim < curtime) tim += ((curtime - tim) / rep) * rep;
if (tim < curtime) tim += rep;
if (tim > q->tt.ttime) tim = q->tt.ttime;
if (tim < curtime) return NO_TIME; else return tim;
}
/***************************************************************/
/* */
/* FindNextReminder */
/* */
/* Find the next reminder to trigger */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE QueuedRem *FindNextReminder(void)
#else
static QueuedRem *FindNextReminder()
#endif
{
QueuedRem *q = QueueHead;
QueuedRem *ans = NULL;
while (q) {
if (q->tt.nexttime != NO_TIME) {
if (!ans) ans = q;
else if (q->tt.nexttime < ans->tt.nexttime) ans = q;
}
q = q->next;
}
return ans;
}
/***************************************************************/
/* */
/* GotSigInt */
/* */
/* Split out what's done on a SIGINT from the SIGINT Handler. */
/* This will be necessary for OS/2 multithreaded. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
void GotSigInt(void)
#else
void GotSigInt()
#endif
{
QueuedRem *q = QueueHead;
printf("Contents of AT queue:%s", NL);
while (q) {
if (q->tt.nexttime != NO_TIME) {
printf("Trigger: %02d%c%02d Activate: %02d%c%02d Rep: %d Delta: %d Sched: %s",
q->tt.ttime / 60, TIMESEP, q->tt.ttime % 60,
q->tt.nexttime / 60, TIMESEP, q->tt.nexttime % 60,
q->tt.rep, q->tt.delta, q->sched);
if (*q->sched) printf("(%d)", q->ntrig+1);
printf("%s", NL);
printf("Text: %s %s%s%s", ((q->typ == MSG_TYPE) ? "MSG" :
((q->typ == MSF_TYPE) ? "MSF" :"RUN")),
q->text,
NL, NL);
}
q = q->next;
}
printf(NL);
}
/***************************************************************/
/* */
/* CheckInitialFile */
/* */
/* If the initial file has been modified, then restart the */
/* daemon. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void CheckInitialFile(void)
#else
static void CheckInitialFile()
#endif
{
/* If date has rolled around, or file has changed, spawn a new version. */
time_t tim = FileModTime;
int y, m, d;
if (stat(InitialFile, &StatBuf) == 0) tim = StatBuf.st_mtime;
if (tim != FileModTime ||
RealToday != SystemDate(&y, &m, &d))
execvp(ArgV[0], ArgV);
}
/***************************************************************/
/* */
/* CalculateNextTimeUsingSched */
/* */
/* Call the scheduling function. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE int CalculateNextTimeUsingSched(QueuedRem *q)
#else
static int CalculateNextTimeUsingSched(q)
QueuedRem *q;
#endif
{
/* Use LineBuffer for temp. string storage. */
int r;
Value v;
char *s;
int LastTime = -1;
int ThisTime;
if (UserFuncExists(q->sched) != 1) {
q->sched[0] = 0;
return NO_TIME;
}
RunDisabled = q->RunDisabled; /* Don't want weird scheduling functions
to be a security hole! */
while(1) {
sprintf(LineBuffer, "%s(%d)", q->sched, q->ntrig);
s = LineBuffer;
r = EvalExpr(&s, &v);
if (r) {
q->sched[0] = 0;
return NO_TIME;
}
if (v.type == TIM_TYPE) {
ThisTime = v.v.val;
} else if (v.type == INT_TYPE) {
if (v.v.val > 0)
ThisTime = q->tt.nexttime + v.v.val;
else
ThisTime = q->tt.ttime + v.v.val;
} else {
DestroyValue(v);
q->sched[0] = 0;
return NO_TIME;
}
if (ThisTime < 0) ThisTime = 0; /* Can't be less than 00:00 */
if (ThisTime > 1439) ThisTime = 1439; /* or greater than 11:59 */
if (ThisTime > q->tt.nexttime) return ThisTime;
if (ThisTime <= LastTime) {
q->sched[0] = 0;
return NO_TIME;
}
LastTime = ThisTime;
q->ntrig++;
}
}
#endif /* HAVE_QUEUED from way at the top */

45
rem
View File

@@ -1,45 +0,0 @@
#!/bin/sh
#
# rem - by David Skoll - 26 February 1991
#
# $Id: rem,v 1.1 1996-03-27 03:26:06 dfs Exp $
#
# This script runs 'remind' with a default reminder file assumed. You
# can override the default by using "rem -F newfile ..." (But why would
# you use rem unless you wanted to accept the default??)
# ------ You may wish to change the defaults below this line ------
# The default reminder file
DEFAULT=$HOME/.reminders
# The executable file (you may wish to change this to /usr/local/bin/remind
# or whatever.
EXECUTABLE=remind
# No options yet
OPTIONS=""
# No parameters yet
PARAMETERS=""
# ------ You shouldn't change anything below this line -----
# Scan for options
while test "$1" != ""
do
case $1 in
-F) DEFAULT=$2
shift
shift ;;
-*) OPTIONS="$OPTIONS $1"
shift ;;
*) PARAMETERS=$*
break ;;
esac
done
$EXECUTABLE $OPTIONS $DEFAULT $PARAMETERS

35
rem.1
View File

@@ -1,35 +0,0 @@
.\" $Id: rem.1,v 1.2 1996-04-28 02:02:01 dfs Exp $
.TH REM 1 "26 February 1991"
.UC 4
.SH NAME
rem \- run 'remind' with a default reminder file
.SH SYNOPSIS
.B rem
[\-F \fIfilename\fR] [\fIremind_options\fR] [\fIremind_params\fR]
.SH DESCRIPTION
.B Rem
runs the \fBremind\fR program with a default reminder file of
"$HOME/.reminders". You can supply remind options on the command line,
as well as a date specification, just as with \fBremind\fR.
If you don't want to use the default filename, you can override it with
the "-F" option, followed by a space and a filename. (This, however,
defeats the purpose of \fBrem\fR)
.PP
For example, typing:
.PP
.nf
rem -c 1 jan 1992
.fi
.PP
has the same effect as typing:
.PP
.nf
remind -c $HOME/.reminders 1 jan 1992
.fi
.PP
.SH AUTHOR
David F. Skoll
.SH SEE ALSO
remind, kall

317
rem2ps.1
View File

@@ -1,317 +0,0 @@
.\" $Id: rem2ps.1,v 1.2 1996-04-28 02:02:01 dfs Exp $
.TH REM2PS 1 "27 April 1996"
.UC4
.SH NAME
rem2ps \- draw a PostScript calendar from Remind output
.SH SYNOPSIS
.B rem2ps [\fIoptions\fR]
.SH DESCRIPTION
\fBRem2ps\fR reads the standard input, which should be the results of running
\fBRemind\fR with the \fB\-p\fR option. It emits PostScript code (which
draws a calendar) to the standard output.
.SH OPTIONS
.TP
.B \-v
Be more verbose. This causes \fBRem2ps\fR to print progress messages
to the standard error stream. Normally, it is silent.
.TP
.B \-p file
Include the contents of \fIfile\fR in the PostScript prologue. This
allows you to define procedures, variables etc. which can be used
by the \fBPS\fR and \fBPSFILE\fR reminders. You should not
include any document structuring comments in your prologue.
.TP
.B \-l
Produce the calendar in landscape mode rather than the default
portrait mode.
.TP
\fB\-c\fR[\fIn\fR]
If \fIn\fR is omitted, disables the small calendars for next and previous
months which are normally generated. If \fIn\fR is supplied, it can range
from 0 to 3, with the following meanings:
.RS
.TP
.B 0
Disable small calendars
.TP
.B 1
Place the small calendars at the bottom-right if there is room; otherwise,
place them at the top-left.
.TP
.B 2
Place the small calendars at the top-left if there is room; otherwise,
place them at the bottom-right.
.TP
.B 3
Place the previous month's small calendar at the top-left and the next
month's at the bottom-right if there is room; otherwise, follow \fIn\fR=1.
A moment's thought reveals that an option which splits the calendars if
there is room and otherwise follows \fIn\fR=2 yields the same results as
\fIn\fR=3.
.RE
.TP
.B \-i
Use ISO 8859-1 standard encoding for the PostScript fonts. If you do
not use this option, the default encoding is used.
.TP
.B \-e
Make the calendar fill the entire page. By default, the calendar is
slightly smaller than the page. This allows days with many reminders
to "expand" as needed. However, if you don't have days which expand,
you can use this option to make all of the boxes slightly bigger.
One caveat: If you do use the \fB\-e\fR option and one day has many
reminders, the calendar may expand off the page, losing some information.
Experiment!
.TP
.B \-m media
Set the page size. If you use the \-m option, you must specify the
media type, which can be one of the
following. (Sizes are approximate.)
.RS
.TP
Letter
8.5 x 11 in.
.TP
Legal
11 x 17 in.
.TP
Ledger
8.5 x 14 in.
.TP
Statement
5.5 x 8.5 in.
.TP
Executive
7.5 x 10 in.
.TP
A3
29.7 x 42 cm.
.TP
A4
21 x 29.7 cm.
.TP
A5
14.8 x 21 cm.
.TP
B4
25.7 x 36.4 cm.
.TP
B5
18.3 x 25.7 cm.
.TP
Folio
8.5 x 13 in.
.TP
Quarto
8.5 x 10.8 in.
.TP
10x14
10 x 14 in.
.PP
Type "rem2ps -m help" for a list of available media. Note that the media
type (and all \fBRem2ps\fR options) are case-sensitive. If you don't use
the \fB\-m\fR option, the media defaults to a compiled-in default - this
is usually Letter for North America and A4 for Europe. The "-m help"
option will display the compiled-in default.
.RE
.TP
\fB\-f\fR[\fBtshed\fR] \fIfont\fR
Set the font for the calendar title,
the small calendars, the day-of-week headings, the calendar
entries, and the day numbers, respectively. \fIFont\fR must be the
name of a valid PostScript font. The default fonts are equivalent to
specifying:
.RS
.PP
.nf
-ftshe Helvetica -fd Helvetica-BoldOblique
.fi
.PP
In other words, the heading, entry and small-calendar fonts are set
to Helvetica, and the font for the day numbers is set to
Helvetica-BoldOblique.
.RE
.TP
\fB\-s\fR[\fBthed\fR] \fIsize\fR
Set the size (in points) of the text for the the calendar title,
day-of-week headings, the calendar entries, and the day numbers,
respectively. \fISize\fR must be a decimal number. The default sizes
are equivalent to specifying:
.RS
.PP
.nf
-sthd 14 -se 8
.fi
.PP
In other words, the heading and day numbers are 14-point fonts, and the
calendar entries are printed in 8-point text.
.RE
.TP
\fB\-b\fR \fIsize\fR
Set the size of the blank white border in each calendar box to \fIsize\fR
points. The default border size is 6 points, or 1/12 in.
.TP
\fB\-t\fR \fIsize\fR
Set the thickness of the black calendar grid lines. The default is 1,
for a line thickness of one point (1/72 in.)
.TP
\fB\-o\fR[\fBlrtb\fR] \fIsize\fR
Set the left, right, top, and/or bottom margins to \fIsize\fR points.
For this option only, \fIsize\fR must be an integer. It represents the
margin size in units of 1/72 in. The default margin sizes are 36, for
half-inch margins. If you wish to punch holes in the calendar page to insert
it into a binder, you may wish to increase the left margin to one inch.
In that case, you should also decrease the heading font size to 12 points
for good output:
.PP
.nf
# This gives good results for putting into a binder
rem2ps -ol 72 -sh 12
.fi
.SH USAGE
To use \fBRem2ps\fR, you should pipe the output of \fBRemind\fR with the \fB\-p\fR
option to \fBRem2ps\fR, and then send the result to a printer. This is most easily
illustrated with examples:
.PP
.nf
remind -p12 /dev/null 1 jan 1994 | rem2ps | lpr -Plaser
.fi
.PP
That example creates a blank calendar for the entire year of 1994, and
sends it the the printer named "laser."
.PP
.nf
remind -p ~/.reminders | rem2ps -l -sd 18 > cal.ps
.fi
.PP
This reminder creates a calendar for the current month, filling in
entries from the reminder file "~/.reminders." The calendar is produced
in landscape mode, with a font size of 18 for the day numbers. The result
is put in the PostScript file "cal.ps."
.PP
.SH VARIABLES AVAILABLE TO USER-SUPPLIED POSTSCRIPT CODE
.PP
The following variables are available to \fBPS\fR and
\fBPSFILE\fR-type reminders. (This material is duplicated
in the \fBRemind\fR manual page.)
.TP
LineWidth
The width of the black grid lines making up the calendar.
.TP
Border
The border between the center of the grid lines and the space used to print
calendar entries. This border is normally blank space.
.TP
BoxWidth and BoxHeight
The width and height of the calendar box, from center-to-center of the
black gridlines.
.TP
InBoxHeight
The height from the center of the bottom black gridline to the top
of the regular calendar entry area. The space from here to the top
of the box is used only to draw the day number.
.TP
/DayFont, /TitleFont, /EntryFont, /SmallFont and /HeadFont
The fonts used to draw the day numbers, the month and year title,
the calendar entries, the small
calendars, and the day-of-week headings, respectively.
.TP
DaySize, TitleSize, EntrySize and HeadSize
The sizes of the above fonts. (The size of the small calendar font
is \fInot\fR defined here.) For example, if you wanted to print
the Hebrew date next to the regular day number in the calendar, use:
.PP
.nf
REM PS Border BoxHeight Border sub DaySize sub moveto \\
/DayFont findfont DaySize scalefont setfont \\
([hebday(today())] [hebmon(today())]) show
.fi
.PP
.RS
Note how /DayFont and DaySize are used.
.RE
.PP
Note that if you supply PostScript code, it is possible to produce invalid
PostScript files. Always test your PostScript thoroughly with a PostScript
viewer before sending it to the printer. You should not use any document
structuring comments in your PostScript code.
.PP
In addition, prior to drawing a calendar page, \fBRem2ps\fR emits
the following PostScript code:
.PP
.nf
save (mon) (yr) PreCal restore
.fi
.PP
where \fImon\fR and \fIyr\fR are the month and year of the calendar
page. The default \fBPreCal\fR procedure simply pops
the arguments and does nothing. However, you can define a \fBPreCal\fR
function in your prologue file to do whatever you want - it can draw a
background for the entire calendar, for instance.
.PP
In the context of the \fBPreCal\fR procedure, the following conditions
hold:
.TP
o
The PostScript origin is at the bottom left-hand corner of the page, and
PostScript units of 1/72" are in effect.
.TP
o
The variables MinX, MinY, MaxX and MaxY define the bounding box within
which the calendar will be drawn.
.TP
o
The font and font-size variables, as well as Border and LineWidth described
previously, are valid.
.PP
For an example, create a file called "myprolog" whose contents are:
.PP
.nf
/PreCal {
/yr exch def
/mon exch def
/xsiz1 MaxX MinX sub def
/ysiz1 MaxY MinY sub def
/xsiz xsiz1 MinX sub MinX sub def
/ysiz ysiz1 MinY sub MinY sub def
xsiz
ysiz
lt
{/len xsiz 1.41 mul def
MinX MinX add ysiz1 xsiz1 sub 2 div MinY add MinY add moveto}
{/len ysiz 1.41 mul def
xsiz1 ysiz1 sub 2 div MinX add MinX add MinY MinY add moveto}
ifelse
/Helvetica-Bold findfont 1 scalefont setfont
mon stringwidth pop
( ) stringwidth pop add
yr stringwidth pop add
len exch div /len exch def
/Helvetica-Bold findfont len scalefont setfont
0.95 setgray
45 rotate
mon show
( ) show
yr show
} bind def
.fi
.PP
Use that file with the \fBRem2ps\fR \fB\-p\fR option to create calendars
with the year and month in large grey letters in the background of the
calendar.
.PP
.SH AUTHOR
David F. Skoll
.SH BUGS
All \fBRem2ps\fR options are case-sensitive, unlike \fBRemind\fR.
Any time you supply
a font name or size, line thickness, or border width, it is treated as a
string and sent straight to the PostScript interpreter. Thus, if you
supply invalid fonts or sizes, \fBRem2ps\fR will not complain, but the
resulting PostScript output will probably not work.
.PP
You should ensure that the values you supply for margin widths are sensible.
If they are too big for the media size, \fBRem2ps\fR will not complain,
but again, the PostScript output will probably not work.
.SH SEE ALSO
\fBRemind\fR

View File

@@ -1,46 +0,0 @@
#!/bin/csh -f
# Shell script to mail all users reminders.
# $Id: remind-all.csh,v 1.1 1996-03-27 03:26:08 dfs Exp $
# Run it AFTER MIDNIGHT so that date is correct!
# On our system, we have the following in our crontab:
# 05 5 * * * /usr/share/lib/remind/remind-all > /dev/null 2>&1
# This script must be run by root. The -u option MUST be supplied
# to Remind, or a severe security hole will exist. Note that Remind
# must be compiled to support the -u option for this script to work.
# Also, the -r and -q options must be used.
# The following line gets a list of users for systems using SUN's
# NIS service:
set USERS = `ypcat passwd | awk -F: '{print $1}'`
# The following line gets a list of users by examining /etc/passwd:
# set USERS = `awk -F: '{print $1}' /etc/passwd`
# If neither of the above methods works, you must come up with some
# way of getting a list of users on the system
# Set the following variables as appropriate for your system
set REMIND = /usr/local/bin/remind
set MAIL = /usr/ucb/mail
set RM = "/usr/bin/rm -f"
set REMFILE = /tmp/RemFile.$$
# Scan each user's directory for a .reminders file
foreach i ($USERS)
if (-r ~$i/.reminders) then
# echo "$i has a .reminders file." DEBUGGING PURPOSES ONLY
$REMIND -u$i -h -r -q -iremind_all=1 ~$i/.reminders < /dev/null > $REMFILE
if (! -z $REMFILE) then
# echo "Sending mail to $i" DEBUGGING PURPOSES ONLY
$MAIL -s "Reminders" $i < $REMFILE
endif
$RM $REMFILE
endif
end

View File

@@ -1,54 +0,0 @@
#!/bin/sh
# Shell script to mail all users reminders.
# This file is part of REMIND
#
# $Id: remind-all.sh,v 1.1 1996-03-27 03:26:08 dfs Exp $
#
# REMIND is Copyright (C) 1992-1996 by David F. Skoll
# This file is Copyright (C) 1990 by Bill Aten
# Thanks to Bill Aten for this script.
# Run it AFTER MIDNIGHT so that date is correct!
# On our system, we have the following in our crontab:
# 02 00 * * * /usr/local/adm/remind-all >/dev/null 2>&1
# This script must be run by root. The -u option MUST be supplied
# to Remind, or a severe security hole will exist. Note that Remind
# must be compiled to support the -u option for this script to work.
# Also, the -r and -q options must be used.
# The following line gets a list of users for systems using SUN's
# NIS service:
# USERS=`ypcat passwd | awk -F: '{print $1}'`
# The following line gets a list of users by examining /etc/passwd:
USERS=`awk -F: '{print $1}' /etc/passwd`
# If neither of the above methods works, you must come up with some
# way of getting a list of users on the system
# Set the following variables as appropriate for your system
REMIND=/usr/local/bin/remind
MAIL=/usr/bin/mail
RM="/bin/rm -f"
REMFILE=/tmp/RemFile.$$
# Scan each user's directory for a .reminders file
for i in $USERS
do
HOME=`grep \^$i: /etc/passwd | awk -F: '{print $6}'`
if [ -r $HOME/.reminders ]; then
# echo "$i has a .reminders file." DEBUGGING PURPOSES ONLY
$REMIND -u$i -h -r -q -iremind_all=1 $HOME/.reminders < /dev/null > $REMFILE
if [ -s $REMFILE ]; then
# echo "Sending mail to $i" DEBUGGING PURPOSES ONLY
$MAIL -s "Reminders" $i < $REMFILE
fi
$RM $REMFILE
fi
done

View File

@@ -1,24 +0,0 @@
Begin3
Title: Remind
Version: 03.00.15
Entered-date: 27 October 1996
Description: Full-featured calendar/reminder program featuring
sophisticated date calculation, moon phases, sunrise/sunset,
Hebrew calendar, alarms, PostScript output, X-Windows
front-end, multilingual messages, and proper handling of
holidays. Available for UNIX, MS-DOS, OS/2, and other
platforms.
Keywords: calendar reminder alarm datebook PostScript
Author: aa775@freenet.carleton.ca (David F. Skoll)
Maintained-by: aa775@freenet.carleton.ca (David F. Skoll)
Primary-site: ftp.doe.carleton.ca /pub/Remind-3.0
215kB remind-3.0.15.tgz
Alternate-site:
Original-site:
Platform: Linux, Solaris, SunOS, HP-UX -- virtually any UN*X-like
system. Wish 4.x required for TCL/Tk front-end, but
this is not essential to use the software.
Copying-policy: An AMENDED version of GPL. The amendments prohibit
porting to MS Windows and use by a certain Canadian
corporation.
End

View File

@@ -1 +0,0 @@
NAME WINDOWCOMPAT NEWFILES

4
scripts/README Normal file
View File

@@ -0,0 +1,4 @@
Files in this directory:
tkremind -- Tcl/Tk graphical calendar using Remind as engine
cm2rem.tcl -- Convert Sun's "cm" calendar manager files to Remind.

358
scripts/cm2rem.tcl Normal file
View File

@@ -0,0 +1,358 @@
#!/bin/sh
# -*-Mode: TCL;-*-
#--------------------------------------------------------------
# cm2rem.tcl
#
# A cheesy Tcl script to convert Sun's "cm" calendar manager
# files (version 3 only) to Remind format.
#
# This file is part of REMIND.
# Copyright (C) 1992-2018 by Dianne Skoll
#
#--------------------------------------------------------------
# the next line restarts using tclsh \
exec tclsh "$0" "$@"
set i 0
foreach month {January February March April May June
July August September October November December} {
incr i
set MonthNum($month) $i
set FullMonth([string range $month 0 2]) $month
}
#***********************************************************************
# %PROCEDURE: convertParens
# %ARGUMENTS:
# line -- a line read from a cm file
# %RETURNS:
# A new line with all ( and ) outside quotes converted to { and }.
# This cheap trick allows us to use Tcl's built-in list manipulation
# functions to munge the line.
#***********************************************************************
proc convertParens { line } {
# Convert all ( and ) to { and } unless they are inside a quoted
# string
set out ""
set len [string length $line]
set inQuotes 0
for {set i 0} {$i < $len} {incr i} {
set char [string range $line $i $i]
if {$char == "\\" && $inQuotes} {
append out $char
incr i
set char [string range $line $i $i]
append out $char
continue
}
if {$char == "(" && !$inQuotes} {
set char \{
}
if {$char == ")" && !$inQuotes} {
set char \}
}
if {$char == "\""} {
set inQuotes [expr !$inQuotes]
}
append out $char
}
return $out
}
#***********************************************************************
# %PROCEDURE: processLine
# %ARGUMENTS:
# line -- a line read from a cm file
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Processes a single line from the file, possibly writing a reminder
# in Remind format to stdout
#***********************************************************************
proc processLine { line } {
global Attributes
global FullMonth
catch {unset Attributes}
# Only convert lines which start with "(add"
if {[string range $line 0 3] != "(add"} {
return
}
set line [convertParens $line]
# Convert it to a list. CAREFUL: Potential security problem if
# $line contains something nasty.
eval set line $line
set Attributes(body) ""
foreach {key val} $line {
switch -exact -- $key {
"add" {
set Attributes(date) $val
}
"what:" {
append Attributes(body) $val
}
"details:" {
append Attributes(body) $val
}
"duration:" {
set Attributes(duration) $val
}
"period:" {
set Attributes(period) $val
}
"ntimes:" {
set Attributes(ntimes) $val
}
"attributes:" {
set Attributes(action) $val
}
}
}
if {[info exists Attributes(action)]} {
# Nuke quotes and commas in action
regsub -all {[,\"]} $Attributes(action) { } Attributes(action)
# Add spaces to pairs
regsub -all \}\{ $Attributes(action) \}\ \{ Attributes(action)
# Add another pair of brackets to make a proper list
set Attributes(action) "{$Attributes(action)}"
# Convert to a real Tcl list
eval set Attributes(action) $Attributes(action)
}
# Split out date into month, day, year, time parts
scan $Attributes(date) "%s%s%s%s%s" wkday month day time year
set time [string range $time 0 4]
set Attributes(wkday) $wkday
set Attributes(month) $FullMonth($month)
set Attributes(day) $day
set Attributes(time) $time
set Attributes(year) $year
# Convert newlines in body to spaces
set body $Attributes(body)
regsub -all "\n" $body " " body
# TODO: Escape BODY to get rid of [] chars.
set Attributes(body) $body
# Convert to Reminder format
convertReminder
}
#***********************************************************************
# %PROCEDURE: convertReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder to Remind format.
#***********************************************************************
proc convertReminder {} {
global Attributes
switch -exact $Attributes(period) {
single { convertSingleReminder }
daily { convertDailyReminder }
weekly { convertWeeklyReminder }
monthly { convertMonthlyReminder }
yearly { convertYearlyReminder }
default {
puts "\# Unable to convert reminder with period $Attributes(period)"
puts "\# Body is: $Attributes(body)"
}
}
}
#***********************************************************************
# %PROCEDURE: convertSingleReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder with "single" period to Remind format.
#***********************************************************************
proc convertSingleReminder {} {
global Attributes
puts "REM $Attributes(day) $Attributes(month) $Attributes(year) [at][duration]MSG $Attributes(body)"
}
#***********************************************************************
# %PROCEDURE: convertDailyReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder with "daily" period to Remind format.
#***********************************************************************
proc convertDailyReminder {} {
global Attributes
set ntimes [expr $Attributes(ntimes) - 1]
if {$ntimes <= 1} {
convertSingleReminder
return
}
set until [getUntilDate $Attributes(day) $Attributes(month) $Attributes(year) $ntimes]
puts "REM $Attributes(day) $Attributes(month) $Attributes(year) *1 [at][duration]UNTIL $until MSG $Attributes(body)"
}
#***********************************************************************
# %PROCEDURE: convertWeeklyReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder with "daily" period to Remind format.
#***********************************************************************
proc convertWeeklyReminder {} {
global Attributes
set ntimes [expr $Attributes(ntimes) - 1]
if {$ntimes <= 1} {
convertSingleReminder
return
}
set until [getUntilDate $Attributes(day) $Attributes(month) $Attributes(year) [expr $ntimes * 7]]
puts "REM $Attributes(day) $Attributes(month) $Attributes(year) *7 [at][duration]UNTIL $until MSG $Attributes(body)"
}
#***********************************************************************
# %PROCEDURE: convertMonthlyReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder with "monthly" period to Remind format.
#***********************************************************************
proc convertMonthlyReminder {} {
global Attributes
set ntimes [expr $Attributes(ntimes) - 1]
if {$ntimes <= 1} {
convertSingleReminder
return
}
# If repetition > 1000, it's infinite
if {$ntimes > 1000} {
puts "REM $Attributes(day) [at][duration]MSG $Attributes(body)"
return
}
### UNTIL date is fudged!
set until [getUntilDate $Attributes(day) $Attributes(month) $Attributes(year) [expr $ntimes * 30]]
puts "REM $Attributes(day) [at][duration]UNTIL $until MSG $Attributes(body)"
}
#***********************************************************************
# %PROCEDURE: convertYearlyReminder
# %ARGUMENTS:
# None -- uses global Attributes variable which must be filled in
# %RETURNS:
# Nothing
# %DESCRIPTION:
# Converts a reminder with "yearly" period to Remind format.
#***********************************************************************
proc convertYearlyReminder {} {
global Attributes
# No special handling of ntimes et al.
puts "REM $Attributes(day) $Attributes(month) [at][duration]MSG $Attributes(body)"
}
#***********************************************************************
# %PROCEDURE: at
# %ARGUMENTS:
# None -- uses Attributes global variable
# %RETURNS:
# A string providing the correct AT clause for a timed reminder.
#***********************************************************************
proc at {} {
global Attributes
if {![info exists Attributes(time)]} {
return ""
}
if {"$Attributes(time)" == ""} {
return ""
}
return "AT $Attributes(time) "
}
#***********************************************************************
# %PROCEDURE: duration
# %ARGUMENTS:
# None -- uses Attributes global variable
# %RETURNS:
# A string providing the correct DURATION clause for a timed reminder.
#***********************************************************************
proc duration {} {
global Attributes
if {![info exists Attributes(duration)]} {
return ""
}
if {"$Attributes(duration)" == ""} {
return ""
}
set h [expr $Attributes(duration) / 3600]
set remainder [expr $Attributes(duration) - $h*3600]
set m [expr $remainder / 60]
return "DURATION [format "%d:%02d " $h $m]"
}
#***********************************************************************
# %PROCEDURE: getUntilDate
# %ARGUMENTS:
# day, month, year -- a date
# days -- number of days to add to date
# %RETURNS:
# The date which is "days" later than supplied date in a correct UNTIL
# format.
#***********************************************************************
proc getUntilDate { day month year days } {
global RemindPipe
global MonthNum
set date "'$year/$MonthNum($month)/$day'"
puts $RemindPipe "MSG \[trigger($date + $days)\]%"
puts $RemindPipe "flush"
flush $RemindPipe
gets $RemindPipe line
return $line
}
catch {wm withdraw .}
# Start a Remind process to issue reminders
if {[catch {set RemindPipe [open "|remind -" "r+"]} err]} {
puts stderr "Error: Cannot run Remind: $err"
exit 1
}
puts $RemindPipe "banner %"
flush $RemindPipe
# Write some blurb
puts "\# Reminder file converted from \"cm\" data by cm2rem.tcl"
puts ""
while {[gets stdin line] >= 0} {
processLine $line
}
exit 0

3705
scripts/tkremind Executable file

File diff suppressed because it is too large Load Diff

View File

@@ -1,94 +0,0 @@
# $Id: smakefile,v 1.3 1996-10-12 02:49:35 dfs Exp $
# Makefile for REMIND, suitable for SAS/C 6.50 under AmigaDOS
# English version
# THIS IS OUT OF DATE!
#-----------------------------------------------------------------------------
# THINGS FOR YOU TO EDIT START BELOW
#-----------------------------------------------------------------------------
# Uncomment the next line if you are running on a SYSV system
# SYSV= -DSYSV
# Uncomment the next line if you are running under UNIX (including SYSV!)
#UNIX= -DUNIX
# Uncomment the next lines if you want to use gcc instead of default compiler
# NOTE: Tempting as it may be, if you use 'cc' for the C compiler, do not
# use 'ld' for the linker. It will probably work much better if you use
# LD= cc rather than LD= ld.
CC= SC
LD= SC
# Put any additional flags for the C compiler or linker here - if you
# are not using gcc, you probably want to remove '-ansi'.
CFLAGS= OPT NOSTKCHK NOSINT MATH=IEEE
CDEFS=
LDFLAGS= LINK
HDRS= config.h err.h expr.h globals.h protos.h types.h version.h \
lang.h english.h german.h dutch.h finnish.h french.h norwgian.h
STDHDRS= config.h types.h protos.h globals.h err.h lang.h
LANGHDRS= english.h german.h dutch.h finnish.h french.h norwgian.h
SRCS= calendar.c dorem.c dosubst.c expr.c files.c funcs.c globals.c hbcal.c \
init.c main.c moon.c omit.c sort.c queue.c token.c trigger.c userfns.c \
utils.c var.c amiga.c
OBJS= calendar.o dorem.o dosubst.o expr.o files.o funcs.o globals.o hbcal.o \
init.o main.o moon.o omit.o sort.o queue.o token.o trigger.o userfns.o \
utils.o var.o amiga.o
MANIFEST= README.UNIX README.DOS COPYRIGHT $(HDRS) $(SRCS) Makefile rem rem.1 \
remind.1 remind-all.csh remind-all.sh test.rem test-rem test.cmp makefile.tc \
makefile.msc lnk.msc lnk.tc MANIFEST.UNX MANIFEST.DOS WHATSNEW.30 kall kall.1 \
defs.rem README.OS2 makefile.os2 rem2ps.c rem2ps.h remind.def rem2ps.1 \
tstlang.rem README.BCC lnk.bcc makefile.bcc os2func.c \
test-rem.bat test-rem.cmd test1.cmp test2.cmp
all: remind rem2ps
.c.o:
$(CC) $(UNIX) $(SYSV) $(CFLAGS) $(CDEFS) $*.c
rem2ps: rem2ps.o
$(LD) MATH=IEEE $(LDFLAGS) PNAME=rem2ps rem2ps.o
remind: $(OBJS)
$(LD) MATH=IEEE $(LDFLAGS) PNAME=remind $(OBJS)
clean:
rm -f *.o *~ core *.bak
clobber:
rm -f *.o *~ remind rem2ps test.out core *.bak
test: remind
sh test-rem
rem2ps.o: rem2ps.c rem2ps.h lang.h config.h
calendar.o: calendar.c $(STDHDRS) expr.h
dorem.o: dorem.c $(STDHDRS) expr.h
dosubst.o: dosubst.c $(STDHDRS) $(LANGHDRS)
expr.o: expr.c $(STDHDRS) expr.h
files.o: files.c $(STDHDRS)
funcs.o: funcs.c $(STDHDRS) expr.h version.h
globals.o: globals.c config.h types.h globals.h err.h lang.h $(LANGHDRS)
hbcal.o: hbcal.c $(STDHDRS)
init.o: init.c $(STDHDRS) expr.h version.h lang.h $(LANGHDRS)
main.o: main.c $(STDHDRS) expr.h
moon.o: moon.c $(STDHDRS)
omit.o: omit.c $(STDHDRS)
sort.o: sort.c $(STDHDRS)
queue.o: queue.c $(STDHDRS)
token.o: token.c $(STDHDRS)
trigger.o: trigger.c $(STDHDRS) expr.h
userfns.o: userfns.c $(STDHDRS) expr.h
utils.o: utils.c $(STDHDRS)
var.o: var.c $(STDHDRS) expr.h
amiga.o: amiga.c
$(CC) OBJNAME=amiga.o $(CFLAGS) amiga.c

95
src/Makefile.in Normal file
View File

@@ -0,0 +1,95 @@
# Makefile.in for REMIND
#
SHELL= /bin/sh
BETA = 1
srcdir=@srcdir@
prefix=@prefix@
exec_prefix=@exec_prefix@
mandir=@mandir@
bindir=@bindir@
datadir=@datadir@
datarootdir=@datarootdir@
VPATH=$(srcdir)
VERSION=@VERSION@
INSTALL=@INSTALL@
INSTALL_PROGRAM=@INSTALL_PROGRAM@
INSTALL_DATA=@INSTALL_DATA@
PROGS= remind rem2ps
SCRIPTS= $(srcdir)/../scripts/tkremind $(srcdir)/../scripts/cm2rem.tcl
MANS= $(srcdir)/../man/rem2ps.1 $(srcdir)/../man/remind.1 \
$(srcdir)/../man/tkremind.1 $(srcdir)/../man/cm2rem.1 \
$(srcdir)/../man/rem.1
.SUFFIXES:
.SUFFIXES: .c .o
REMINDSRCS= calendar.c dynbuf.c dorem.c dosubst.c expr.c files.c funcs.c \
globals.c hbcal.c init.c main.c md5.c moon.c omit.c queue.c \
sort.c token.c trigger.c userfns.c utils.c var.c
REMINDHDRS=config.h custom.h dynbuf.h err.h expr.h globals.h lang.h \
md5.h protos.h rem2ps.h types.h version.h
REMINDOBJS= $(REMINDSRCS:.c=.o)
all: remind rem2ps
test: remind
@sh ../tests/test-rem
.c.o:
@CC@ -c @CPPFLAGS@ @CFLAGS@ @DEFS@ $(CEXTRA) $(LANGDEF) -I. -I$(srcdir) $<
$(REMINDOBJS): $(REMINDHDRS)
rem2ps: rem2ps.o dynbuf.o json.o
@CC@ @LDFLAGS@ $(LDEXTRA) -o rem2ps rem2ps.o dynbuf.o json.o -lm
remind: $(REMINDOBJS)
@CC@ @LDFLAGS@ $(LDEXTRA) -o remind $(REMINDOBJS) @LIBS@
install-nostripped: all
-mkdir -p $(DESTDIR)$(bindir) || true
for prog in $(PROGS) $(SCRIPTS) ; do \
$(INSTALL_PROGRAM) $$prog $(DESTDIR)$(bindir) || exit 1; \
done
rm -f $(DESTDIR)$(bindir)/rem > /dev/null 2>&1 || true
ln -s remind $(DESTDIR)$(bindir)/rem
-mkdir -p $(DESTDIR)$(mandir)/man1 || true
for man in $(MANS) ; do \
$(INSTALL_DATA) $$man $(DESTDIR)$(mandir)/man1 || exit 1; \
done
install: install-nostripped
strip $(DESTDIR)$(bindir)/remind || true
strip $(DESTDIR)$(bindir)/rem2ps || true
clean:
rm -f *.o *~ core *.bak $(PROGS)
clobber:
rm -f *.o *~ remind rem2ps test.out core *.bak
depend:
gccmakedep @DEFS@ $(REMINDSRCS) rem2ps.c json.c
# The next targets are not very useful to you. I use them to build
# distributions, etc.
# Build a tar file based on all files checked into git.
distro:
cd .. && git archive --worktree-attributes --format=tar --prefix=remind-$(VERSION)/ HEAD > src/remind-$(VERSION).tar
gzip -f -v -9 remind-$(VERSION).tar
gpg --detach-sign -u dianne@skoll.ca remind-$(VERSION).tar.gz
beta-tgz:
cd .. && git archive --worktree-attributes --format=tar --prefix=remind-$(VERSION)-BETA-$(BETA)/ HEAD > src/remind-$(VERSION)-BETA-$(BETA).tar
gzip -f -v -9 remind-$(VERSION)-BETA-$(BETA).tar
gpg --detach-sign -u dianne@skoll.ca remind-$(VERSION)-BETA-$(BETA).tar.gz
#---------------- Stuff after this added by "make depend" -----------------

2183
src/calendar.c Normal file

File diff suppressed because it is too large Load Diff

39
src/config.h.in Normal file
View File

@@ -0,0 +1,39 @@
/* Define if utime(file, NULL) sets file's timestamp to the present. */
#undef HAVE_UTIME_NULL
/* Define if you can safely include both <sys/time.h> and <time.h>. */
#undef TIME_WITH_SYS_TIME
/* Define if your <sys/time.h> declares struct tm. */
#undef TM_IN_SYS_TIME
/* Define if you have the <sys/file.h> header file. */
#undef HAVE_SYS_FILE_H
/* Define if you have the <glob.h> header file */
#undef HAVE_GLOB_H
#undef HAVE_WCTYPE_H
#undef HAVE_LOCALE_H
#undef HAVE_GLOB
#undef HAVE_SETENV
#undef HAVE_UNSETENV
#undef HAVE_MBSTOWCS
#undef HAVE_SETLOCALE
/* The number of bytes in a unsigned int. */
#undef SIZEOF_UNSIGNED_INT
/* The number of bytes in a unsigned long. */
#undef SIZEOF_UNSIGNED_LONG
/* The number of bytes in a unsigned short. */
#undef SIZEOF_UNSIGNED_SHORT
#include "custom.h"

View File

@@ -1,27 +1,24 @@
/***************************************************************/
/* */
/* CONFIG.H */
/* CUSTOM.H.IN */
/* */
/* Contains various configuration parameters for Remind. */
/* You may have to edit this file to tweak parameters or take */
/* care of certain system dependencies. */
/* Contains various configuration parameters for Remind */
/* which you can customize. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: config.h,v 1.5 1996-10-12 02:49:32 dfs Exp $ */
/*---------------------------------------------------------------------*/
/* LAT_DEG, LAT_MIN and LAT_SEC: Latitude of your location */
/* LON_DEG, LON_MIN and LON_SEC: Longitude of your location */
/* LOCATION: A string identifying your location. */
/* For latitude, north is positive, south is negative. */
/* For longitude, west is positive, east is negative. */
/* NOTE: For negative numbers, all three of DEG, MIN, SEC should be */
/* negative. To indicate -20deg22'33'' use */
/* DEG=-20, MIN=-22 and SEC=-33. */
/* All latitude and longitude numbers should be positive for the */
/* northern and western hemisphere. If you live in the southern */
/* hemisphere, ALL latitude values should be negative. If you live */
/* in the eastern hemisphere, ALL longitude values should be negative. */
/* */
/* The default values are initially set to Ottawa, Ontario, Canada. */
/*---------------------------------------------------------------------*/
#define LAT_DEG 45
@@ -32,21 +29,6 @@
#define LON_SEC 0
#define LOCATION "Ottawa"
/*---------------------------------------------------------------------*/
/* HAVE_MKTIME: Define this if your C library includes the mktime() */
/* function. Otherwise, will attempt to use the Unix */
/* style time manipulations. */
/*---------------------------------------------------------------------*/
#define HAVE_MKTIME 1
/*---------------------------------------------------------------------*/
/* NEED_TIMEGM: If your C library does not have mktime() and it ALSO */
/* does not have timelocal() or timegm(), uncomment the */
/* next line. If HAVE_MKTIME is defined, NEED_TIMEGM is */
/* ignored. Very few systems should require NEED_TIMEGM. */
/*---------------------------------------------------------------------*/
/* #define NEED_TIMEGM 1 */
/*---------------------------------------------------------------------*/
/* DEFAULT_PAGE: The default page size to use for Rem2PS. */
/* The Letter version is appropriate for North America; the A4 version */
@@ -54,13 +36,13 @@
/*---------------------------------------------------------------------*/
#define DEFAULT_PAGE {"Letter", 612, 792}
/* #define DEFAULT_PAGE {"A4", 595, 842} */
/*---------------------------------------------------------------------*/
/* DATESEP: The default date separator. North American usage is '/'; */
/* others may prefer '-'. */
/* DATESEP: The default date separator. Standard usage is '-'; */
/* others may prefer '/'. */
/*---------------------------------------------------------------------*/
#define DATESEP '/'
/* #define DATESEP '-' */
#define DATESEP '-'
/* #define DATESEP '/' */
/*---------------------------------------------------------------------*/
/* TIMESEP: The default time separator. North American usage is ':'; */
@@ -70,26 +52,64 @@
/* #define TIMESEP '.' */
/*---------------------------------------------------------------------*/
/* ISOLATIN1: uncomment the following line if your system uses the */
/* DATETIMESEP: The default datetime separator. Default is '@'; */
/* others may prefer 'T'. */
/*---------------------------------------------------------------------*/
#define DATETIMESEP '@'
/* #define DATETIMESEP '/' */
/*---------------------------------------------------------------------*/
/* ISOLATIN1: define it to 1 if you use the */
/* ISO 8859-1 character set instead of ASCII. */
/*---------------------------------------------------------------------*/
#define ISOLATIN1 1
/*---------------------------------------------------------------------*/
/* IBMEXTENDED: uncomment the following line if you want to use the */
/* IBM extended character set. NOT ALL LANGUAGE MODULES SUPPORT THIS. */
/* Note that at most one of ISOLATIN1 or IBMEXTENDED should be */
/* defined; if both are defined, the results are unspecified. */
/* ISOLATIN2: define it to 1 if you use the */
/* ISO 8859-2 character set instead of ASCII. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
/* #define IBMEXTENDED 1 */
#define ISOLATIN2 0
/*---------------------------------------------------------------------*/
/* IBMEXTENDED: define as 1 if your system uses the IBM extended */
/* character set. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
#define IBMEXTENDED 0
/*---------------------------------------------------------------------*/
/* IBM852: define as 1 if your system uses the IBM CPI-852 extended */
/* character set. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
#define IBM852 0
/*---------------------------------------------------------------------*/
/* WANT_U_OPTION: Comment out the next define to permanently disable */
/* the -u option. If you do this, however, remind-all.[c]sh will not */
/* work. */
/* the -u option. */
/*---------------------------------------------------------------------*/
#define WANT_U_OPTION 1
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/* You most likely do NOT have to tweak anything after this! */
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/*---------------------------------------------------------------------*/
/* WANT_SHELL_ESCAPING: Define this if you want special shell */
/* characters to be escaped with a backslash for the -k option. */
@@ -98,12 +118,6 @@
#define WANT_SHELL_ESCAPING 1
#endif
/*---------------------------------------------------------------------*/
/* STRSTR: If your system does not have the "strstr" function, */
/* uncomment the following line. */
/*---------------------------------------------------------------------*/
/* #define NO_STRSTR 1 */
/*---------------------------------------------------------------------*/
/* Some implementations have a broken 'putc' and 'putchar'. */
/*---------------------------------------------------------------------*/
@@ -111,20 +125,6 @@
#define BROKEN_PUTC
#endif
/*---------------------------------------------------------------------*/
/* STDLIB: If you don't have the <stdlib.h> header file, comment the */
/* following line. */
/*---------------------------------------------------------------------*/
#define HAVE_STDLIB_H 1
/*---------------------------------------------------------------------*/
/* MALLOC: If you do not have the <malloc.h> header file, */
/* comment out the next 3 lines. */
/*---------------------------------------------------------------------*/
#ifdef UNIX
#define HAVE_MALLOC_H 1
#endif
/*---------------------------------------------------------------------*/
/* BASE: The base year for date calculation. NOTE! January 1 of the */
/* base year MUST be a Monday, else Remind will not work! */
@@ -137,19 +137,16 @@
#define BASE 1990
/*---------------------------------------------------------------------*/
/* YR_RANGE: The range of years allowed. Computers with 16-bit */
/* integers can handle about 89 years worth of reminders; if */
/* you use 32-bit integers, you can handle over 5 867 000 */
/* years. Note that YR_RANGE is set to 88 rather than 89 */
/* because we can range up to the last day of the 88th year. */
/* YR_RANGE: The range of years allowed. With 32-bit signed integers, */
/* the DATETIME type can store 2^31 minutes or about 4074 years. */
/*---------------------------------------------------------------------*/
#define YR_RANGE 88
#define YR_RANGE 4000
/*---------------------------------------------------------------------*/
/* VAR_NAME_LEN: The maximum length of variable names. Don't make it */
/* any less than 12. */
/*---------------------------------------------------------------------*/
#define VAR_NAME_LEN 12
#define VAR_NAME_LEN 64
/*---------------------------------------------------------------------*/
/* MAX_PRT_LEN: The maximum number of characters to print when */
@@ -158,24 +155,25 @@
#define MAX_PRT_LEN 40
/*---------------------------------------------------------------------*/
/* LINELEN: The maximum length of an input line */
/* MAX_STR_LEN: If non-zero, Remind will limit the maximum length */
/* of string values to avoid eating up all of memory... */
/*---------------------------------------------------------------------*/
#define LINELEN 512
#define MAX_STR_LEN 65535
/*---------------------------------------------------------------------*/
/* OP_STACK_SIZE: The size of the operator stack for expr. parsing */
/*---------------------------------------------------------------------*/
#define OP_STACK_SIZE 30
#define OP_STACK_SIZE 100
/*---------------------------------------------------------------------*/
/* VAL_STACK_SIZE: The size of the operand stack for expr. parsing */
/*---------------------------------------------------------------------*/
#define VAL_STACK_SIZE 30
#define VAL_STACK_SIZE 500
/*---------------------------------------------------------------------*/
/* INCLUDE_NEST: How many nested INCLUDES do we handle? */
/*---------------------------------------------------------------------*/
#define INCLUDE_NEST 8
#define INCLUDE_NEST 9
/*---------------------------------------------------------------------*/
/* IF_NEST: How many nested IFs do we handle? Maximum is the number */
@@ -183,68 +181,20 @@
/*---------------------------------------------------------------------*/
#define IF_NEST (4*sizeof(unsigned int))
/*---------------------------------------------------------------------*/
/* Do we handle queued reminders? */
/*---------------------------------------------------------------------*/
#if defined(UNIX) || defined(__OS2__)
#define HAVE_QUEUED 1
#endif
/*---------------------------------------------------------------------*/
/* Does our C compiler have prototypes? Override this test if you */
/* are using a non-ANSI compiler that nevertheless has prototypes. */
/*---------------------------------------------------------------------*/
#if defined(__STDC__) || defined(__TURBOC__) || defined(__BORLANDC__)
#define HAVE_PROTOS 1
#endif
/*---------------------------------------------------------------------*/
/* Do we use the <stdarg.h> scheme for functions with variable number */
/* of parameters? If not, the <varargs.h> scheme is assumed. */
/*---------------------------------------------------------------------*/
#if defined(__STDC__) || defined(__TURBOC__) || defined(__BORLANDC__)
#define HAVE_STDARG 1
#endif
/*---------------------------------------------------------------------*/
/* Does the function argument to the signal() function take an INT */
/* argument? If yes, uncomment the next line. If you get it wrong, */
/* the only bad side effect is a compiler warning, so don't worry too */
/* much about it. */
/*---------------------------------------------------------------------*/
#define SIGHANDLER_INT_ARG 1
/*---------------------------------------------------------------------*/
/* Do we have the <unistd.h> header? If not, use sys/files.h */
/*---------------------------------------------------------------------*/
#ifdef UNIX
#define HAVE_UNISTD 1
#endif
/*---------------------------------------------------------------------*/
/* How many attempts to resolve a weird date spec? */
/*---------------------------------------------------------------------*/
#define TRIG_ATTEMPTS 25
#define TRIG_ATTEMPTS 500
/*---------------------------------------------------------------------*/
/* How many global omits of the form YYYY MM DD do we handle? */
/*---------------------------------------------------------------------*/
#define MAX_FULL_OMITS 75
#define MAX_FULL_OMITS 500
/*---------------------------------------------------------------------*/
/* How many global omits of the form MM DD do we handle? */
/*---------------------------------------------------------------------*/
#define MAX_PARTIAL_OMITS 75
/*---------------------------------------------------------------------*/
/* The size of statically-allocated buffers for tokens. */
/*---------------------------------------------------------------------*/
#define TOKSIZE 128
/*---------------------------------------------------------------------*/
/* The size of the buffer for the shell() function. */
/*---------------------------------------------------------------------*/
#define SHELLSIZE 512
#define MAX_PARTIAL_OMITS 366
/*---------------------------------------------------------------------*/
/* A newline - some systems need "\n\r" */
@@ -259,20 +209,20 @@
/*---------------------------------------------------------------------*/
/* Don't change the next definitions */
/*---------------------------------------------------------------------*/
#define PUBLIC
#define PRIVATE static
#ifdef UNIX
#define _POSIX_SOURCE
#endif
/*---------------------------------------------------------------------*/
/* TAG_LEN: The maximum length of tags. Don't change it */
/*---------------------------------------------------------------------*/
#define TAG_LEN 48
#ifdef SYSV
#define _SVID_SOURCE
#endif
#define PASSTHRU_LEN 32
#define PSBEGIN "# rem2ps begin"
#define PSEND "# rem2ps end"
#define PSBEGIN2 "# rem2ps2 begin"
#define PSEND2 "# rem2ps2 end"
#ifdef BROKEN_PUTC
#define Putc SafePutc
#define PutChar SafePutChar
@@ -280,3 +230,9 @@
#define Putc putc
#define PutChar putchar
#endif
#if defined(HAVE_MBSTOWCS) && defined(HAVE_WCTYPE_H)
#define REM_USE_WCHAR 1
#else
#undef REM_USE_WCHAR
#endif

238
src/custom.h.in Normal file
View File

@@ -0,0 +1,238 @@
/***************************************************************/
/* */
/* CUSTOM.H.IN */
/* */
/* Contains various configuration parameters for Remind */
/* which you can customize. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/*---------------------------------------------------------------------*/
/* LAT_DEG, LAT_MIN and LAT_SEC: Latitude of your location */
/* LON_DEG, LON_MIN and LON_SEC: Longitude of your location */
/* LOCATION: A string identifying your location. */
/* All latitude and longitude numbers should be positive for the */
/* northern and western hemisphere. If you live in the southern */
/* hemisphere, ALL latitude values should be negative. If you live */
/* in the eastern hemisphere, ALL longitude values should be negative. */
/* */
/* The default values are initially set to Ottawa, Ontario, Canada. */
/*---------------------------------------------------------------------*/
#define LAT_DEG 45
#define LAT_MIN 24
#define LAT_SEC 0
#define LON_DEG 75
#define LON_MIN 39
#define LON_SEC 0
#define LOCATION "Ottawa"
/*---------------------------------------------------------------------*/
/* DEFAULT_PAGE: The default page size to use for Rem2PS. */
/* The Letter version is appropriate for North America; the A4 version */
/* is appropriate for Europe. */
/*---------------------------------------------------------------------*/
#define DEFAULT_PAGE {"Letter", 612, 792}
/* #define DEFAULT_PAGE {"A4", 595, 842} */
/*---------------------------------------------------------------------*/
/* DATESEP: The default date separator. Standard usage is '-'; */
/* others may prefer '/'. */
/*---------------------------------------------------------------------*/
#define DATESEP '-'
/* #define DATESEP '/' */
/*---------------------------------------------------------------------*/
/* TIMESEP: The default time separator. North American usage is ':'; */
/* others may prefer '.'. */
/*---------------------------------------------------------------------*/
#define TIMESEP ':'
/* #define TIMESEP '.' */
/*---------------------------------------------------------------------*/
/* DATETIMESEP: The default datetime separator. Default is '@'; */
/* others may prefer 'T'. */
/*---------------------------------------------------------------------*/
#define DATETIMESEP '@'
/* #define DATETIMESEP '/' */
/*---------------------------------------------------------------------*/
/* ISOLATIN1: define it to 1 if you use the */
/* ISO 8859-1 character set instead of ASCII. */
/*---------------------------------------------------------------------*/
#define ISOLATIN1 1
/*---------------------------------------------------------------------*/
/* ISOLATIN2: define it to 1 if you use the */
/* ISO 8859-2 character set instead of ASCII. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
#define ISOLATIN2 0
/*---------------------------------------------------------------------*/
/* IBMEXTENDED: define as 1 if your system uses the IBM extended */
/* character set. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
#define IBMEXTENDED 0
/*---------------------------------------------------------------------*/
/* IBM852: define as 1 if your system uses the IBM CPI-852 extended */
/* character set. */
/* NOT ALL LANGUAGE MODULES SUPPORT THIS. Note that at most one of */
/* ISOLATIN1, ISOLATIN2, IBMEXTENDED and IBM852 should be 1; if more */
/* then one are defined as 1, the results are unspecified. */
/*---------------------------------------------------------------------*/
#define IBM852 0
/*---------------------------------------------------------------------*/
/* WANT_U_OPTION: Comment out the next define to permanently disable */
/* the -u option. */
/*---------------------------------------------------------------------*/
#define WANT_U_OPTION 1
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/* You most likely do NOT have to tweak anything after this! */
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/**********************************************************************/
/*---------------------------------------------------------------------*/
/* WANT_SHELL_ESCAPING: Define this if you want special shell */
/* characters to be escaped with a backslash for the -k option. */
/*---------------------------------------------------------------------*/
#if defined(UNIX)
#define WANT_SHELL_ESCAPING 1
#endif
/*---------------------------------------------------------------------*/
/* Some implementations have a broken 'putc' and 'putchar'. */
/*---------------------------------------------------------------------*/
#ifdef __SASC_60
#define BROKEN_PUTC
#endif
/*---------------------------------------------------------------------*/
/* BASE: The base year for date calculation. NOTE! January 1 of the */
/* base year MUST be a Monday, else Remind will not work! */
/* IMPORTANT NOTE: The Hebrew date routines depend on BASE */
/* being set to 1990. If you change it, you'll have to add the */
/* number of days between 1 Jan <NEWBASE> and 1 Jan 1990 to the */
/* manifest constant CORRECTION in hbcal.c. Also, the year */
/* folding mechanism in main.c depends on BASE<2001. */
/*---------------------------------------------------------------------*/
#define BASE 1990
/*---------------------------------------------------------------------*/
/* YR_RANGE: The range of years allowed. With 32-bit signed integers, */
/* the DATETIME type can store 2^31 minutes or about 4074 years. */
/*---------------------------------------------------------------------*/
#define YR_RANGE 4000
/*---------------------------------------------------------------------*/
/* VAR_NAME_LEN: The maximum length of variable names. Don't make it */
/* any less than 12. */
/*---------------------------------------------------------------------*/
#define VAR_NAME_LEN 64
/*---------------------------------------------------------------------*/
/* MAX_PRT_LEN: The maximum number of characters to print when */
/* displaying a string value for debugging purposes. */
/*---------------------------------------------------------------------*/
#define MAX_PRT_LEN 40
/*---------------------------------------------------------------------*/
/* MAX_STR_LEN: If non-zero, Remind will limit the maximum length */
/* of string values to avoid eating up all of memory... */
/*---------------------------------------------------------------------*/
#define MAX_STR_LEN 65535
/*---------------------------------------------------------------------*/
/* OP_STACK_SIZE: The size of the operator stack for expr. parsing */
/*---------------------------------------------------------------------*/
#define OP_STACK_SIZE 100
/*---------------------------------------------------------------------*/
/* VAL_STACK_SIZE: The size of the operand stack for expr. parsing */
/*---------------------------------------------------------------------*/
#define VAL_STACK_SIZE 500
/*---------------------------------------------------------------------*/
/* INCLUDE_NEST: How many nested INCLUDES do we handle? */
/*---------------------------------------------------------------------*/
#define INCLUDE_NEST 9
/*---------------------------------------------------------------------*/
/* IF_NEST: How many nested IFs do we handle? Maximum is the number */
/* of bits in an int, divided by two. Beware! */
/*---------------------------------------------------------------------*/
#define IF_NEST (4*sizeof(unsigned int))
/*---------------------------------------------------------------------*/
/* How many attempts to resolve a weird date spec? */
/*---------------------------------------------------------------------*/
#define TRIG_ATTEMPTS 500
/*---------------------------------------------------------------------*/
/* How many global omits of the form YYYY MM DD do we handle? */
/*---------------------------------------------------------------------*/
#define MAX_FULL_OMITS 500
/*---------------------------------------------------------------------*/
/* How many global omits of the form MM DD do we handle? */
/*---------------------------------------------------------------------*/
#define MAX_PARTIAL_OMITS 366
/*---------------------------------------------------------------------*/
/* A newline - some systems need "\n\r" */
/*---------------------------------------------------------------------*/
#define NL "\n"
/*---------------------------------------------------------------------*/
/* Minimum number of linefeeds in each calendar "box" */
/*---------------------------------------------------------------------*/
#define CAL_LINES 5
/*---------------------------------------------------------------------*/
/* Don't change the next definitions */
/*---------------------------------------------------------------------*/
/*---------------------------------------------------------------------*/
/* TAG_LEN: The maximum length of tags. Don't change it */
/*---------------------------------------------------------------------*/
#define TAG_LEN 48
#define PASSTHRU_LEN 32
#define PSBEGIN "# rem2ps begin"
#define PSEND "# rem2ps end"
#define PSBEGIN2 "# rem2ps2 begin"
#define PSEND2 "# rem2ps2 end"
#ifdef BROKEN_PUTC
#define Putc SafePutc
#define PutChar SafePutChar
#else
#define Putc putc
#define PutChar putchar
#endif
#if defined(HAVE_MBSTOWCS) && defined(HAVE_WCTYPE_H)
#define REM_USE_WCHAR 1
#else
#undef REM_USE_WCHAR
#endif

1349
src/dorem.c Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -6,29 +6,24 @@
/* reminders are triggered. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: dosubst.c,v 1.3 1996-10-12 02:49:32 dfs Exp $";
#define L_IN_DOSUBST
#include "config.h"
#define L_IN_DOSUBST
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#include "types.h"
#include "globals.h"
#include "err.h"
#include "types.h"
#include "protos.h"
#define UPPER(c) (islower(c) ? toupper(c) : c)
#define UPPER(c) (islower(c) ? toupper(c) : (c))
#define ABS(x) ( (x) < 0 ? -(x) : (x) )
#ifndef NL
#define NL "\n"
@@ -37,6 +32,8 @@ static char const RCSID[] = "$Id: dosubst.c,v 1.3 1996-10-12 02:49:32 dfs Exp $"
static char TODAY[] = L_TODAY;
static char TOMORROW[] = L_TOMORROW;
#define SHIP_OUT(s) if(DBufPuts(dbuf, s) != OK) return E_NO_MEM
/***************************************************************/
/* */
/* DoSubst */
@@ -44,18 +41,10 @@ static char TOMORROW[] = L_TOMORROW;
/* Process the % escapes in the reminder. If */
/* mode==NORMAL_MODE, ignore the %" sequence. If */
/* mode==CAL_MODE, process the %" sequence. */
/* If mode==ADVANCE_MODE, ignore %" but don't add newline */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int DoSubst(ParsePtr p, char *out, Trigger *t, TimeTrig *tt, int jul, int mode)
#else
int DoSubst(p, out, t, tt, jul, mode)
ParsePtr p;
char *out;
Trigger *t;
TimeTrig *tt;
int jul, mode;
#endif
int DoSubst(ParsePtr p, DynamicBuffer *dbuf, Trigger *t, TimeTrig *tt, int jul, int mode)
{
int diff = jul - JulianToday;
int curtime = SystemTime(0) / 60;
@@ -64,12 +53,15 @@ int jul, mode;
int d, m, y;
int tim = tt->ttime;
int h, min, hh, ch, cmin, chh;
char *pm, *cpm;
char const *pm, *cpm;
int tdiff, adiff, mdiff, hdiff;
char *mplu, *hplu, *when, *plu;
char const *mplu, *hplu, *when, *plu;
int has_quote = 0;
char *s = out;
char *ss;
char *os;
char s[256];
int origLen = DBufLen(dbuf);
int altmode;
FromJulian(jul, &y, &m, &d);
@@ -85,14 +77,14 @@ int jul, mode;
mplu = (mdiff == 1 ? "" : L_MPLU);
#endif /* L_MPLU_OVER */
#ifdef L_HPLU_OVER
#ifdef L_HPLU_OVER
L_HPLU_OVER
#else /* L_HPLU_OVER */
hplu = (hdiff == 1 ? "" : L_HPLU);
#endif /* L_HPLU_OVER */
when = (tdiff < 0 ? L_AGO : L_FROMNOW);
h = tim / 60;
min = tim % 60;
@@ -102,7 +94,7 @@ int jul, mode;
pm = (h < 12) ? L_AM : L_PM;
#endif
hh = (h == 12) ? 12 : h % 12;
ch = curtime / 60;
cmin = curtime % 60;
@@ -120,46 +112,64 @@ int jul, mode;
case 1:
case 21:
case 31: plu = "st"; break;
case 2:
case 22: plu = "nd"; break;
case 3:
case 23: plu = "rd"; break;
default: plu = "th"; break;
}
#endif
#endif
while(1) {
c = ParseChar(p, &err, 0);
if (err) return err;
if (err) {
DBufFree(dbuf);
return err;
}
if (c == '\n') continue;
if (!c) {
if (mode != CAL_MODE && t->typ != RUN_TYPE && !MsgCommand)
*s++ = '\n';
*s++ = 0;
if (mode != CAL_MODE && mode != ADVANCE_MODE &&
t->typ != RUN_TYPE && !MsgCommand) {
if (DBufPutc(dbuf, '\n') != OK) return E_NO_MEM;
}
break;
}
if (c != '%') {
*s++ = c;
if (DBufPutc(dbuf, c) != OK) return E_NO_MEM;
continue;
}
altmode = 0;
s[0] = 0;
c = ParseChar(p, &err, 0);
if (err) return err;
if (err) {
DBufFree(dbuf);
return err;
}
if (!c) {
*s++ = 0;
break;
}
os = s;
if (c == '*') {
altmode = c;
c = ParseChar(p, &err, 0);
if (err) {
DBufFree(dbuf);
return err;
}
if (!c) {
break;
}
}
done = 0;
if (diff <= 1) {
switch(UPPER(c)) {
#ifndef L_NOTOMORROW_A
case 'A':
case 'A':
#endif
#ifndef L_NOTOMORROW_B
case 'B':
case 'B':
#endif
#ifndef L_NOTOMORROW_C
case 'C':
@@ -195,125 +205,169 @@ int jul, mode;
case 'V':
#endif
sprintf(s, "%s", (diff ? TOMORROW : TODAY));
s += strlen(s);
SHIP_OUT(s);
done = 1;
break;
default: done = 0;
default: done = 0;
}
}
if (!done) switch(UPPER(c)) {
case 'A':
#ifdef L_A_OVER
L_A_OVER
#else
sprintf(s, "%s %s, %d %s, %d", L_ON, DayName[jul%7], d,
MonthName[m], y);
#else
if (altmode == '*') {
sprintf(s, "%s, %d %s, %d", DayName[jul%7], d,
MonthName[m], y);
} else {
sprintf(s, "%s %s, %d %s, %d", L_ON, DayName[jul%7], d,
MonthName[m], y);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'B':
#ifdef L_B_OVER
L_B_OVER
#else
#else
sprintf(s, L_INXDAYS, diff);
#endif
s += strlen(s);
break;
SHIP_OUT(s);
break;
case 'C':
#ifdef L_C_OVER
L_C_OVER
#else
sprintf(s, "%s %s", L_ON, DayName[jul%7]);
#else
if (altmode == '*') {
sprintf(s, "%s", DayName[jul%7]);
} else {
sprintf(s, "%s %s", L_ON, DayName[jul%7]);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'D':
#ifdef L_D_OVER
L_D_OVER
#else
#else
sprintf(s, "%d", d);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'E':
#ifdef L_E_OVER
L_E_OVER
#else
sprintf(s, "%s %02d%c%02d%c%04d", L_ON, d, DATESEP,
m+1, DATESEP, y);
#else
if (altmode == '*') {
sprintf(s, "%02d%c%02d%c%04d", d, DateSep,
m+1, DateSep, y);
} else {
sprintf(s, "%s %02d%c%02d%c%04d", L_ON, d, DateSep,
m+1, DateSep, y);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'F':
#ifdef L_F_OVER
L_F_OVER
#else
sprintf(s, "%s %02d%c%02d%c%04d", L_ON, m+1, DATESEP, d, DATESEP, y);
#else
if (altmode == '*') {
sprintf(s, "%02d%c%02d%c%04d", m+1, DateSep, d, DateSep, y);
} else {
sprintf(s, "%s %02d%c%02d%c%04d", L_ON, m+1, DateSep, d, DateSep, y);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'G':
#ifdef L_G_OVER
L_G_OVER
#else
sprintf(s, "%s %s, %d %s", L_ON, DayName[jul%7], d, MonthName[m]);
#else
if (altmode == '*') {
sprintf(s, "%s, %d %s", DayName[jul%7], d, MonthName[m]);
} else {
sprintf(s, "%s %s, %d %s", L_ON, DayName[jul%7], d, MonthName[m]);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'H':
#ifdef L_H_OVER
L_H_OVER
#else
sprintf(s, "%s %02d%c%02d", L_ON, d, DATESEP, m+1);
#else
if (altmode == '*') {
sprintf(s, "%02d%c%02d", d, DateSep, m+1);
} else {
sprintf(s, "%s %02d%c%02d", L_ON, d, DateSep, m+1);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'I':
#ifdef L_I_OVER
L_I_OVER
#else
sprintf(s, "%s %02d%c%02d", L_ON, m+1, DATESEP, d);
#else
if (altmode == '*') {
sprintf(s, "%02d%c%02d", m+1, DateSep, d);
} else {
sprintf(s, "%s %02d%c%02d", L_ON, m+1, DateSep, d);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'J':
#ifdef L_J_OVER
L_J_OVER
#else
sprintf(s, "%s %s, %s %d%s, %d", L_ON, DayName[jul%7],
MonthName[m], d, plu, y);
if (altmode == '*') {
sprintf(s, "%s, %s %d%s, %d", DayName[jul%7],
MonthName[m], d, plu, y);
} else {
sprintf(s, "%s %s, %s %d%s, %d", L_ON, DayName[jul%7],
MonthName[m], d, plu, y);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'K':
#ifdef L_K_OVER
L_K_OVER
#else
sprintf(s, "%s %s, %s %d%s", L_ON, DayName[jul%7],
MonthName[m], d, plu);
if (altmode == '*') {
sprintf(s, "%s, %s %d%s", DayName[jul%7],
MonthName[m], d, plu);
} else {
sprintf(s, "%s %s, %s %d%s", L_ON, DayName[jul%7],
MonthName[m], d, plu);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'L':
#ifdef L_L_OVER
L_L_OVER
#else
sprintf(s, "%s %04d%c%02d%c%02d", L_ON, y, DATESEP, m+1, DATESEP, d);
if (altmode == '*') {
sprintf(s, "%04d%c%02d%c%02d", y, DateSep, m+1, DateSep, d);
} else {
sprintf(s, "%s %04d%c%02d%c%02d", L_ON, y, DateSep, m+1, DateSep, d);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'M':
@@ -322,7 +376,7 @@ int jul, mode;
#else
sprintf(s, "%s", MonthName[m]);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'N':
@@ -331,7 +385,7 @@ int jul, mode;
#else
sprintf(s, "%d", m+1);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'O':
@@ -341,25 +395,25 @@ int jul, mode;
if (RealToday == JulianToday) sprintf(s, " (%s)", L_TODAY);
else *s = 0;
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'P':
#ifdef L_P_OVER
L_P_OVER
#else
sprintf(s, (diff == 1 ? "" : L_PLURAL));
sprintf(s, "%s", (diff == 1 ? "" : L_PLURAL));
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'Q':
#ifdef L_Q_OVER
L_Q_OVER
#else
sprintf(s, (diff == 1 ? "'s" : "s'"));
sprintf(s, "%s", (diff == 1 ? "'s" : "s'"));
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'R':
@@ -368,16 +422,16 @@ int jul, mode;
#else
sprintf(s, "%02d", d);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'S':
#ifdef L_S_OVER
L_S_OVER
#else
sprintf(s, plu);
sprintf(s, "%s", plu);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'T':
@@ -386,36 +440,46 @@ int jul, mode;
#else
sprintf(s, "%02d", m+1);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'U':
#ifdef L_U_OVER
L_U_OVER
#else
sprintf(s, "%s %s, %d%s %s, %d", L_ON, DayName[jul%7], d,
plu, MonthName[m], y);
if (altmode == '*') {
sprintf(s, "%s, %d%s %s, %d", DayName[jul%7], d,
plu, MonthName[m], y);
} else {
sprintf(s, "%s %s, %d%s %s, %d", L_ON, DayName[jul%7], d,
plu, MonthName[m], y);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'V':
#ifdef L_V_OVER
L_V_OVER
#else
sprintf(s, "%s %s, %d%s %s", L_ON, DayName[jul%7], d, plu,
MonthName[m]);
if (altmode == '*') {
sprintf(s, "%s, %d%s %s", DayName[jul%7], d, plu,
MonthName[m]);
} else {
sprintf(s, "%s %s, %d%s %s", L_ON, DayName[jul%7], d, plu,
MonthName[m]);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'W':
#ifdef L_W_OVER
L_W_OVER
#else
sprintf(s, DayName[jul%7]);
sprintf(s, "%s", DayName[jul%7]);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'X':
@@ -424,7 +488,7 @@ int jul, mode;
#else
sprintf(s, "%d", diff);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'Y':
@@ -433,7 +497,7 @@ int jul, mode;
#else
sprintf(s, "%d", y);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case 'Z':
@@ -442,16 +506,16 @@ int jul, mode;
#else
sprintf(s, "%d", y % 100);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '1':
#ifdef L_1_OVER
L_1_OVER
#else
if (tdiff == 0)
sprintf(s, L_NOW);
else if (hdiff == 0)
if (tdiff == 0)
sprintf(s, "%s", L_NOW);
else if (hdiff == 0)
sprintf(s, "%d %s%s %s", mdiff, L_MINUTE, mplu, when);
else if (mdiff == 0)
sprintf(s, "%d %s%s %s", hdiff, L_HOUR, hplu, when);
@@ -459,16 +523,20 @@ int jul, mode;
sprintf(s, "%d %s%s %s %d %s%s %s", hdiff, L_HOUR, hplu,
L_AND, mdiff, L_MINUTE, mplu, when);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '2':
#ifdef L_2_OVER
L_2_OVER
#else
sprintf(s, "%s %d%c%02d%s", L_AT, hh, TIMESEP, min, pm);
if (altmode == '*') {
sprintf(s, "%d%c%02d%s", hh, TimeSep, min, pm);
} else {
sprintf(s, "%s %d%c%02d%s", L_AT, hh, TimeSep, min, pm);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '3':
@@ -476,9 +544,13 @@ int jul, mode;
L_3_OVER
#else
sprintf(s, "%s %02d%c%02d", L_AT, h, TIMESEP, min);
if (altmode == '*') {
sprintf(s, "%02d%c%02d", h, TimeSep, min);
} else {
sprintf(s, "%s %02d%c%02d", L_AT, h, TimeSep, min);
}
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '4':
@@ -487,7 +559,7 @@ int jul, mode;
#else
sprintf(s, "%d", tdiff);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '5':
@@ -496,16 +568,16 @@ int jul, mode;
#else
sprintf(s, "%d", adiff);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '6':
#ifdef L_6_OVER
L_6_OVER
#else
sprintf(s, when);
sprintf(s, "%s", when);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '7':
@@ -514,7 +586,7 @@ int jul, mode;
#else
sprintf(s, "%d", hdiff);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '8':
@@ -523,60 +595,61 @@ int jul, mode;
#else
sprintf(s, "%d", mdiff);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '9':
#ifdef L_9_OVER
L_9_OVER
#else
sprintf(s, mplu);
sprintf(s, "%s", mplu);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '0':
#ifdef L_0_OVER
L_0_OVER
#else
sprintf(s, hplu);
sprintf(s, "%s", hplu);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '!':
#ifdef L_BANG_OVER
L_BANG_OVER
#else
sprintf(s, (tdiff >= 0 ? L_IS : L_WAS));
sprintf(s, "%s", (tdiff >= 0 ? L_IS : L_WAS));
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '@':
#ifdef L_AT_OVER
L_AT_OVER
#else
sprintf(s, "%d%c%02d%s", chh, TIMESEP, cmin, cpm);
sprintf(s, "%d%c%02d%s", chh, TimeSep, cmin, cpm);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '#':
#ifdef L_HASH_OVER
L_HASH_OVER
#else
sprintf(s, "%02d%c%02d", ch, TIMESEP, cmin);
sprintf(s, "%02d%c%02d", ch, TimeSep, cmin);
#endif
s += strlen(s);
SHIP_OUT(s);
break;
case '_':
if (mode != CAL_MODE && !MsgCommand)
case '_':
if (PsCal == PSCAL_LEVEL2 || PsCal == PSCAL_LEVEL3 || (mode != CAL_MODE && mode != ADVANCE_MODE && !MsgCommand)) {
sprintf(s, "%s", NL);
else
} else {
sprintf(s, " ");
s += strlen(s);
}
SHIP_OUT(s);
break;
case QUOTE_MARKER:
@@ -584,14 +657,25 @@ int jul, mode;
break;
case '"':
*s++ = QUOTE_MARKER;
has_quote = 1;
if (PsCal != PSCAL_LEVEL3) {
if (DBufPutc(dbuf, QUOTE_MARKER) != OK) return E_NO_MEM;
has_quote = 1;
} else {
if (DBufPutc(dbuf, '%') != OK) return E_NO_MEM;
if (DBufPutc(dbuf, c) != OK) return E_NO_MEM;
}
break;
default:
*s++ = c;
if (DBufPutc(dbuf, c) != OK) return E_NO_MEM;
}
if (isupper(c)) {
os = DBufValue(dbuf);
os += strlen(os) - strlen(s);
if (os >= DBufValue(dbuf)) {
*os = UPPER(*os);
}
}
if (isupper(c)) *os = UPPER(*os);
}
/* We're outside the big while loop. The only way to get here is for c to
@@ -602,38 +686,43 @@ int jul, mode;
/* If there are NO quotes, then: If CAL_MODE && RUN_TYPE, we don't want the
reminder in the calendar. Zero the output buffer and quit. */
if (!has_quote) {
if (mode == CAL_MODE && t->typ == RUN_TYPE) *out = 0;
if ((mode == ADVANCE_MODE || mode == CAL_MODE) && t->typ == RUN_TYPE) {
*DBufValue(dbuf) = 0;
dbuf->len = 0;
}
return OK;
}
/* There ARE quotes. If in CAL_MODE, delete everything before first quote
and after second quote. If in NORMAL_MODE, delete the %" sequences. */
s = out;
os = out;
if (mode == NORMAL_MODE) {
while (*s) {
if (*s != QUOTE_MARKER) *os++ = *s;
s++;
ss = DBufValue(dbuf) + origLen;
os = ss;
if (mode == NORMAL_MODE || mode == ADVANCE_MODE) {
while (*ss) {
if (*ss != QUOTE_MARKER) *os++ = *ss;
ss++;
}
*os = 0;
} else {
/* Skip past the quote marker */
while (*s && (*s != QUOTE_MARKER)) s++;
while (*ss && (*ss != QUOTE_MARKER)) ss++;
/* Security check... actually, *s must == QUOTE_MARKER at this point, but
it doesn't hurt to make it a bit robust. */
if (*s) s++;
if (*ss) ss++;
/* Copy the output until the next QUOTE_MARKER */
while (*s && (*s != QUOTE_MARKER)) *os++ = *s++;
while (*ss && (*ss != QUOTE_MARKER)) *os++ = *ss++;
*os = 0;
}
/* Violating encapsulation here!!!! */
dbuf->len = strlen(dbuf->buffer);
return OK;
}
/***************************************************************/
/* */
@@ -644,15 +733,8 @@ int jul, mode;
/* default triggers and a mode of NORMAL_MODE. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int DoSubstFromString(char *source, char *dest, int jul, int tim)
#else
int DoSubstFromString(source, dest, jul, tim)
char *source;
char *dest;
int jul;
int tim;
#endif
int DoSubstFromString(char const *source, DynamicBuffer *dbuf,
int jul, int tim)
{
Trigger tempTrig;
TimeTrig tempTime;
@@ -665,8 +747,8 @@ int tim;
tempP.allownested = 0;
tempTrig.typ = MSG_TYPE;
tempTime.ttime = tim;
r = DoSubst(&tempP, dest, &tempTrig, &tempTime, jul, NORMAL_MODE);
r = DoSubst(&tempP, dbuf, &tempTrig, &tempTime, jul, NORMAL_MODE);
DestroyParser(&tempP);
return r;
}

178
src/dynbuf.c Normal file
View File

@@ -0,0 +1,178 @@
/***************************************************************/
/* */
/* DYNBUF.C */
/* */
/* Implementation of functions for manipulating dynamic */
/* buffers. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
#include "config.h"
#include "dynbuf.h"
#include "err.h"
#include <string.h>
#include <stdlib.h>
/**********************************************************************
%FUNCTION: DBufMakeRoom
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
n -- size to expand to
%RETURNS:
OK if all went well; E_NO_MEM if out of memory
%DESCRIPTION:
Doubles the size of dynamic buffer until it has room for at least
'n' characters, not including trailing '\0'
**********************************************************************/
static int DBufMakeRoom(DynamicBuffer *dbuf, int n)
{
/* Double size until it's greater than n (strictly > to leave room
for trailing '\0' */
int size = dbuf->allocatedLen;
char *buf;
if (size > n) return OK;
while (size <= n) {
size *= 2;
}
/* Allocate memory */
buf = malloc(size);
if (!buf) return E_NO_MEM;
/* Copy contents */
strcpy(buf, dbuf->buffer);
/* Free contents if necessary */
if (dbuf->buffer != dbuf->staticBuf) free(dbuf->buffer);
dbuf->buffer = buf;
dbuf->allocatedLen = size;
return OK;
}
/**********************************************************************
%FUNCTION: DBufInit
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
%RETURNS:
Nothing
%DESCRIPTION:
Initializes a dynamic buffer
**********************************************************************/
void DBufInit(DynamicBuffer *dbuf)
{
dbuf->buffer = dbuf->staticBuf;
dbuf->len = 0;
dbuf->allocatedLen = DBUF_STATIC_SIZE;
dbuf->buffer[0] = 0;
}
/**********************************************************************
%FUNCTION: DBufPutcFN
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
c -- character to append to buffer
%RETURNS:
OK if all went well; E_NO_MEM if out of memory
%DESCRIPTION:
Appends a character to the buffer.
**********************************************************************/
int DBufPutcFN(DynamicBuffer *dbuf, char c)
{
if (dbuf->allocatedLen == dbuf->len+1) {
if (DBufMakeRoom(dbuf, dbuf->len+1) != OK) return E_NO_MEM;
}
dbuf->buffer[dbuf->len++] = c;
dbuf->buffer[dbuf->len] = 0;
return OK;
}
/**********************************************************************
%FUNCTION: DBufPuts
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
str -- string to append to buffer
%RETURNS:
OK if all went well; E_NO_MEM if out of memory
%DESCRIPTION:
Appends a string to the buffer.
**********************************************************************/
int DBufPuts(DynamicBuffer *dbuf, char const *str)
{
int l = strlen(str);
if (!l) return OK;
if (DBufMakeRoom(dbuf, dbuf->len+l) != OK) return E_NO_MEM;
strcpy((dbuf->buffer+dbuf->len), str);
dbuf->len += l;
return OK;
}
/**********************************************************************
%FUNCTION: DBufFree
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
%RETURNS:
Nothing
%DESCRIPTION:
Frees and reinitializes a dynamic buffer
**********************************************************************/
void DBufFree(DynamicBuffer *dbuf)
{
if (dbuf->buffer != dbuf->staticBuf) free(dbuf->buffer);
DBufInit(dbuf);
}
/**********************************************************************
%FUNCTION: DBufGets
%ARGUMENTS:
dbuf -- pointer to a dynamic buffer
fp -- file to read from
%RETURNS:
OK or E_NO_MEM
%DESCRIPTION:
Reads an entire line from a file and appends to dbuf. Does not include
trailing newline.
**********************************************************************/
int DBufGets(DynamicBuffer *dbuf, FILE *fp)
{
char tmp[256]; /* Safe to hard-code */
int busy = 1;
int l;
DBufFree(dbuf);
/* Try reading the first few bytes right into the buffer --
we can usually save some unnecessary copying */
*(dbuf->buffer) = 0;
if (fgets(dbuf->buffer, dbuf->allocatedLen, fp) == NULL) {
return OK;
}
if (!*(dbuf->buffer)) return OK;
dbuf->len = strlen(dbuf->buffer);
l = dbuf->len - 1;
if (dbuf->buffer[l] == '\n') {
dbuf->buffer[l] = 0;
dbuf->len = l;
return OK;
}
while(busy) {
*tmp = 0;
if (fgets(tmp, 256, fp) == NULL) return OK;
if (!*tmp) return OK;
l = strlen(tmp) - 1;
if (tmp[l] == '\n') {
tmp[l] = 0;
busy = 0;
}
if (DBufPuts(dbuf, tmp) != OK) return E_NO_MEM;
}
return OK;
}

36
src/dynbuf.h Normal file
View File

@@ -0,0 +1,36 @@
/***************************************************************/
/* */
/* DYNBUF.H */
/* */
/* Declaration of functions for manipulating dynamic buffers */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
#ifndef DYNBUF_H
#define DYNBUF_H
#include <stdio.h> /* For FILE */
#define DBUF_STATIC_SIZE 128
typedef struct {
char *buffer;
int len;
int allocatedLen;
char staticBuf[DBUF_STATIC_SIZE];
} DynamicBuffer;
void DBufInit(DynamicBuffer *dbuf);
int DBufPutcFN(DynamicBuffer *dbuf, char c);
int DBufPuts(DynamicBuffer *dbuf, char const *str);
void DBufFree(DynamicBuffer *dbuf);
int DBufGets(DynamicBuffer *dbuf, FILE *fp);
#define DBufValue(bufPtr) ((bufPtr)->buffer)
#define DBufLen(bufPtr) ((bufPtr)->len)
#define DBufPutc(dbuf, c) ( (dbuf)->allocatedLen < (dbuf)->len+1 ) ? (dbuf)->buffer[(dbuf)->len++] = c, (dbuf)->buffer[(dbuf)->len] = 0, OK : DBufPutcFN((dbuf), c)
#endif /* DYNBUF_H */

View File

@@ -5,12 +5,10 @@
/* Error definitions. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: err.h,v 1.2 1996-04-28 02:01:55 dfs Exp $ */
/* Note that not all of the "errors" are really errors - some are just
messages for information purposes. Constants beginning with M_ should
never be returned as error indicators - they should only be used to
@@ -117,7 +115,11 @@
#define M_QUEUED 96
#define E_EXPECTING_NUMBER 97
#define M_BAD_WARN_FUNC 98
#define E_CANT_CONVERT_TZ 99
#define E_NO_MATCHING_REMS 100
#define E_STRING_TOO_LONG 101
#define E_TIME_TWICE 102
#define E_DURATION_NO_AT 103
#ifdef MK_GLOBALS
#undef EXTERN
#define EXTERN
@@ -189,7 +191,7 @@ EXTERN char *ErrMsg[]
"Too many partial OMITs",
"Too many full OMITs",
"Warning: PUSH-OMIT-CONTEXT without matching POP-OMIT-CONTEXT",
"Error reading file",
"Error reading",
"Expecting end-of-line",
"Invalid Hebrew date",
"IIF needs odd number of arguments",
@@ -203,9 +205,9 @@ EXTERN char *ErrMsg[]
"Back value specified twice",
"ONCE keyword used twice. (Hah.)",
"Expecting time after AT",
"UNTIL keyword used twice",
"THROUGH/UNTIL keyword used twice",
"Incomplete date specification",
"SCANFROM keyword used twice",
"FROM/SCANFROM keyword used twice",
"Variable",
"Value",
"*UNDEFINED*",
@@ -229,7 +231,12 @@ EXTERN char *ErrMsg[]
"No reminders.",
"%d reminder(s) queued for later today.\n",
"Expecting number",
"Bad function in WARN clause"
"Bad function in WARN clause",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
}
#endif /* MK_GLOBALS */
;

File diff suppressed because it is too large Load Diff

View File

@@ -5,18 +5,18 @@
/* Contains a few definitions used by expression evaluator. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: expr.h,v 1.1 1996-03-27 03:25:54 dfs Exp $ */
/* Define the types of values */
#define ERR_TYPE 0
#define INT_TYPE 1
#define TIM_TYPE 2
#define DATE_TYPE 3
#define STR_TYPE 4
#define ERR_TYPE 0
#define INT_TYPE 1
#define TIME_TYPE 2
#define DATE_TYPE 3
#define STR_TYPE 4
#define DATETIME_TYPE 5
#define SPECIAL_TYPE 6 /* Only for system variables */
/* Define stuff for parsing expressions */
#define BEG_OF_EXPR '['

875
src/files.c Normal file
View File

@@ -0,0 +1,875 @@
/***************************************************************/
/* */
/* FILES.C */
/* */
/* Controls the opening and closing of files, etc. Also */
/* handles caching of lines and reading of lines from */
/* files. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
#include "config.h"
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <ctype.h>
#include <sys/stat.h>
#ifdef TM_IN_SYS_TIME
#include <sys/time.h>
#else
#include <time.h>
#endif
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
#ifdef HAVE_GLOB_H
#include <glob.h>
#endif
#include "types.h"
#include "protos.h"
#include "globals.h"
#include "err.h"
/* Convenient macro for closing files */
#define FCLOSE(fp) (((fp)&&((fp)!=stdin)) ? (fclose(fp),(fp)=NULL) : ((fp)=NULL))
/* Define the structures needed by the file caching system */
typedef struct cache {
struct cache *next;
char const *text;
int LineNo;
} CachedLine;
typedef struct cheader {
struct cheader *next;
char const *filename;
CachedLine *cache;
int ownedByMe;
} CachedFile;
/* A linked list of filenames if we INCLUDE /some/directory/ */
typedef struct fname_chain {
struct fname_chain *next;
char const *filename;
} FilenameChain;
/* Cache filename chains for directories */
typedef struct directory_fname_chain {
struct directory_fname_chain *next;
FilenameChain *chain;
char const *dirname;
} DirectoryFilenameChain;
/* Define the structures needed by the INCLUDE file system */
typedef struct {
char const *filename;
FilenameChain *chain;
int LineNo;
unsigned int IfFlags;
int NumIfs;
long offset;
CachedLine *CLine;
int ownedByMe;
} IncludeStruct;
static CachedFile *CachedFiles = (CachedFile *) NULL;
static CachedLine *CLine = (CachedLine *) NULL;
static DirectoryFilenameChain *CachedDirectoryChains = NULL;
static FILE *fp;
static IncludeStruct IStack[INCLUDE_NEST];
static int IStackPtr = 0;
static int ReadLineFromFile (void);
static int CacheFile (char const *fname);
static void DestroyCache (CachedFile *cf);
static int CheckSafety (void);
static int PopFile (void);
static void OpenPurgeFile(char const *fname, char const *mode)
{
DynamicBuffer fname_buf;
if (PurgeFP != NULL && PurgeFP != stdout) {
fclose(PurgeFP);
}
PurgeFP = NULL;
/* Do not open a purge file if we're below purge
include depth */
if (IStackPtr-2 >= PurgeIncludeDepth) {
PurgeFP = NULL;
return;
}
DBufInit(&fname_buf);
if (DBufPuts(&fname_buf, fname) != OK) return;
if (DBufPuts(&fname_buf, ".purged") != OK) return;
PurgeFP = fopen(DBufValue(&fname_buf), mode);
if (!PurgeFP) {
fprintf(ErrFp, "Cannot open `%s' for writing: %s\n", DBufValue(&fname_buf), strerror(errno));
}
DBufFree(&fname_buf);
}
static void FreeChainItem(FilenameChain *chain)
{
if (chain->filename) free((void *) chain->filename);
free(chain);
}
static void FreeChain(FilenameChain *chain)
{
FilenameChain *next;
while(chain) {
next = chain->next;
FreeChainItem(chain);
chain = next;
}
}
/***************************************************************/
/* */
/* ReadLine */
/* */
/* Read a line from the file or cache. */
/* */
/***************************************************************/
int ReadLine(void)
{
int r;
/* If we're at the end of a file, pop */
while (!CLine && !fp) {
r = PopFile();
if (r) return r;
}
/* If it's cached, read line from the cache */
if (CLine) {
CurLine = CLine->text;
LineNo = CLine->LineNo;
CLine = CLine->next;
FreshLine = 1;
if (DebugFlag & DB_ECHO_LINE) OutputLine(ErrFp);
return OK;
}
/* Not cached. Read from the file. */
return ReadLineFromFile();
}
/***************************************************************/
/* */
/* ReadLineFromFile */
/* */
/* Read a line from the file pointed to by fp. */
/* */
/***************************************************************/
static int ReadLineFromFile(void)
{
int l;
char copy_buffer[4096];
size_t n;
DynamicBuffer buf;
DBufInit(&buf);
DBufFree(&LineBuffer);
while(fp) {
if (DBufGets(&buf, fp) != OK) {
DBufFree(&LineBuffer);
return E_NO_MEM;
}
LineNo++;
if (ferror(fp)) {
DBufFree(&buf);
DBufFree(&LineBuffer);
return E_IO_ERR;
}
if (feof(fp)) {
FCLOSE(fp);
if ((DBufLen(&buf) == 0) &&
(DBufLen(&LineBuffer) == 0) && PurgeMode) {
if (PurgeFP != NULL && PurgeFP != stdout) fclose(PurgeFP);
PurgeFP = NULL;
}
}
l = DBufLen(&buf);
if (l && (DBufValue(&buf)[l-1] == '\\')) {
if (PurgeMode) {
if (DBufPuts(&LineBuffer, DBufValue(&buf)) != OK) {
DBufFree(&buf);
DBufFree(&LineBuffer);
return E_NO_MEM;
}
if (DBufPutc(&LineBuffer, '\n') != OK) {
DBufFree(&buf);
DBufFree(&LineBuffer);
return E_NO_MEM;
}
} else {
DBufValue(&buf)[l-1] = '\n';
if (DBufPuts(&LineBuffer, DBufValue(&buf)) != OK) {
DBufFree(&buf);
DBufFree(&LineBuffer);
return E_NO_MEM;
}
}
continue;
}
if (DBufPuts(&LineBuffer, DBufValue(&buf)) != OK) {
DBufFree(&buf);
DBufFree(&LineBuffer);
return E_NO_MEM;
}
DBufFree(&buf);
/* If the line is: __EOF__ treat it as end-of-file */
CurLine = DBufValue(&LineBuffer);
if (!strcmp(CurLine, "__EOF__")) {
if (PurgeMode && PurgeFP) {
PurgeEchoLine("%s\n", "__EOF__");
while ((n = fread(copy_buffer, 1, sizeof(copy_buffer), fp)) != 0) {
fwrite(copy_buffer, 1, n, PurgeFP);
}
if (PurgeFP != stdout) fclose(PurgeFP);
PurgeFP = NULL;
}
FCLOSE(fp);
DBufFree(&LineBuffer);
CurLine = DBufValue(&LineBuffer);
}
FreshLine = 1;
if (DebugFlag & DB_ECHO_LINE) OutputLine(ErrFp);
return OK;
}
CurLine = DBufValue(&LineBuffer);
return OK;
}
/***************************************************************/
/* */
/* OpenFile */
/* */
/* Open a file for reading. If it's in the cache, set */
/* CLine. Otherwise, open it on disk and set fp. If */
/* ShouldCache is 1, cache the file */
/* */
/***************************************************************/
int OpenFile(char const *fname)
{
CachedFile *h = CachedFiles;
int r;
if (PurgeMode) {
if (PurgeFP != NULL && PurgeFP != stdout) {
fclose(PurgeFP);
}
PurgeFP = NULL;
}
/* Assume we own the file for now */
RunDisabled &= ~RUN_NOTOWNER;
/* If it's in the cache, get it from there. */
while (h) {
if (!strcmp(fname, h->filename)) {
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Reading `%s': Found in cache\n", fname);
}
CLine = h->cache;
STRSET(FileName, fname);
LineNo = 0;
if (!h->ownedByMe) {
RunDisabled |= RUN_NOTOWNER;
}
if (FileName) return OK; else return E_NO_MEM;
}
h = h->next;
}
/* If it's a dash, then it's stdin */
if (!strcmp(fname, "-")) {
fp = stdin;
if (PurgeMode) {
PurgeFP = stdout;
}
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Reading `-': Reading stdin\n");
}
} else {
fp = fopen(fname, "r");
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Reading `%s': Opening file on disk\n", fname);
}
if (PurgeMode) {
OpenPurgeFile(fname, "w");
}
}
if (!fp || !CheckSafety()) return E_CANT_OPEN;
CLine = NULL;
if (ShouldCache) {
LineNo = 0;
r = CacheFile(fname);
if (r == OK) {
fp = NULL;
CLine = CachedFiles->cache;
} else {
if (strcmp(fname, "-")) {
fp = fopen(fname, "r");
if (!fp || !CheckSafety()) return E_CANT_OPEN;
if (PurgeMode) OpenPurgeFile(fname, "w");
} else {
fp = stdin;
if (PurgeMode) PurgeFP = stdout;
}
}
}
STRSET(FileName, fname);
LineNo = 0;
if (FileName) return OK; else return E_NO_MEM;
}
/***************************************************************/
/* */
/* CacheFile */
/* */
/* Cache a file in memory. If we fail, set ShouldCache to 0 */
/* Returns an indication of success or failure. */
/* */
/***************************************************************/
static int CacheFile(char const *fname)
{
int r;
CachedFile *cf;
CachedLine *cl;
char const *s;
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Caching file `%s' in memory\n", fname);
}
cl = NULL;
/* Create a file header */
cf = NEW(CachedFile);
if (!cf) {
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
cf->cache = NULL;
cf->filename = StrDup(fname);
if (!cf->filename) {
ShouldCache = 0;
FCLOSE(fp);
free(cf);
return E_NO_MEM;
}
if (RunDisabled & RUN_NOTOWNER) {
cf->ownedByMe = 0;
} else {
cf->ownedByMe = 1;
}
/* Read the file */
while(fp) {
r = ReadLineFromFile();
if (r) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return r;
}
/* Skip blank chars */
s = DBufValue(&LineBuffer);
while (isempty(*s)) s++;
if (*s && *s!=';' && *s!='#') {
/* Add the line to the cache */
if (!cl) {
cf->cache = NEW(CachedLine);
if (!cf->cache) {
DBufFree(&LineBuffer);
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
cl = cf->cache;
} else {
cl->next = NEW(CachedLine);
if (!cl->next) {
DBufFree(&LineBuffer);
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
cl = cl->next;
}
cl->next = NULL;
cl->LineNo = LineNo;
cl->text = StrDup(s);
DBufFree(&LineBuffer);
if (!cl->text) {
DestroyCache(cf);
ShouldCache = 0;
FCLOSE(fp);
return E_NO_MEM;
}
}
}
/* Put the cached file at the head of the queue */
cf->next = CachedFiles;
CachedFiles = cf;
return OK;
}
/***************************************************************/
/* */
/* NextChainedFile - move to the next chained file in a glob */
/* list. */
/* */
/***************************************************************/
static int NextChainedFile(IncludeStruct *i)
{
while(i->chain) {
FilenameChain *cur = i->chain;
i->chain = i->chain->next;
if (OpenFile(cur->filename) == OK) {
return OK;
} else {
Eprint("%s: %s", ErrMsg[E_CANT_OPEN], cur->filename);
}
}
return E_EOF;
}
/***************************************************************/
/* */
/* PopFile - we've reached the end. Pop up to the previous */
/* file, or return E_EOF */
/* */
/***************************************************************/
static int PopFile(void)
{
IncludeStruct *i;
/* Assume we own the file for now */
RunDisabled &= ~RUN_NOTOWNER;
if (!Hush && NumIfs) Eprint("%s", ErrMsg[E_MISS_ENDIF]);
if (!IStackPtr) return E_EOF;
i = &IStack[IStackPtr-1];
if (i->chain) {
int oldRunDisabled = RunDisabled;
if (NextChainedFile(i) == OK) {
return OK;
}
RunDisabled = oldRunDisabled;
}
if (IStackPtr <= 1) {
return E_EOF;
}
IStackPtr--;
LineNo = i->LineNo;
IfFlags = i->IfFlags;
NumIfs = i->NumIfs;
CLine = i->CLine;
fp = NULL;
STRSET(FileName, i->filename);
if (!i->ownedByMe) {
RunDisabled |= RUN_NOTOWNER;
}
if (!CLine && (i->offset != -1L)) {
/* We must open the file, then seek to specified position */
if (strcmp(i->filename, "-")) {
fp = fopen(i->filename, "r");
if (!fp || !CheckSafety()) return E_CANT_OPEN;
if (PurgeMode) OpenPurgeFile(i->filename, "a");
} else {
fp = stdin;
if (PurgeMode) PurgeFP = stdout;
}
if (fp != stdin)
(void) fseek(fp, i->offset, 0); /* Trust that it works... */
}
free((char *) i->filename);
return OK;
}
/***************************************************************/
/* */
/* DoInclude */
/* */
/* The INCLUDE command. */
/* */
/***************************************************************/
int DoInclude(ParsePtr p)
{
DynamicBuffer buf;
int r, e;
DBufInit(&buf);
if ( (r=ParseToken(p, &buf)) ) return r;
e = VerifyEoln(p);
if (e) Eprint("%s", ErrMsg[e]);
if ( (r=IncludeFile(DBufValue(&buf))) ) {
DBufFree(&buf);
return r;
}
DBufFree(&buf);
NumIfs = 0;
IfFlags = 0;
return OK;
}
#ifdef HAVE_GLOB
static int SetupGlobChain(char const *dirname, IncludeStruct *i)
{
DynamicBuffer pattern;
char *dir;
size_t l;
int r;
glob_t glob_buf;
DirectoryFilenameChain *dc = CachedDirectoryChains;
i->chain = NULL;
if (!*dirname) return E_CANT_OPEN;
dir = StrDup(dirname);
if (!dir) return E_NO_MEM;
/* Strip trailing slashes off directory */
l = strlen(dir);
while(l) {
if (*(dir+l-1) == '/') {
l--;
*(dir+l) = 0;
} else {
break;
}
}
/* Repair root directory :-) */
if (!l) {
*dir = '/';
}
/* Check the cache */
while(dc) {
if (!strcmp(dc->dirname, dir)) {
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Found cached directory listing for `%s'\n",
dir);
}
free(dir);
i->chain = dc->chain;
return OK;
}
dc = dc->next;
}
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Scanning directory `%s' for *.rem files\n", dir);
}
if (ShouldCache) {
dc = malloc(sizeof(DirectoryFilenameChain));
if (dc) {
dc->dirname = StrDup(dir);
if (!dc->dirname) {
free(dc);
dc = NULL;
}
}
if (dc) {
if (DebugFlag & DB_TRACE_FILES) {
fprintf(ErrFp, "Caching directory `%s' listing\n", dir);
}
dc->chain = NULL;
dc->next = CachedDirectoryChains;
CachedDirectoryChains = dc;
}
}
DBufInit(&pattern);
DBufPuts(&pattern, dir);
DBufPuts(&pattern, "/*.rem");
free(dir);
r = glob(DBufValue(&pattern), 0, NULL, &glob_buf);
DBufFree(&pattern);
if (r == GLOB_NOMATCH) {
globfree(&glob_buf);
return OK;
}
if (r != 0) {
globfree(&glob_buf);
return -1;
}
/* Add the files to the chain backwards to preserve sort order */
for (r=glob_buf.gl_pathc-1; r>=0; r--) {
FilenameChain *ch = malloc(sizeof(FilenameChain));
if (!ch) {
globfree(&glob_buf);
FreeChain(i->chain);
i->chain = NULL;
return E_NO_MEM;
}
/* TODO: stat the file and only add if it's a plain file and
readable by us */
ch->filename = StrDup(glob_buf.gl_pathv[r]);
if (!ch->filename) {
globfree(&glob_buf);
FreeChain(i->chain);
i->chain = NULL;
free(ch);
return E_NO_MEM;
}
ch->next = i->chain;
i->chain = ch;
}
if (dc) {
dc->chain = i->chain;
}
globfree(&glob_buf);
return OK;
}
#endif
/***************************************************************/
/* */
/* IncludeFile */
/* */
/* Process the INCLUDE command - actually do the file */
/* inclusion. */
/* */
/***************************************************************/
int IncludeFile(char const *fname)
{
IncludeStruct *i;
int oldRunDisabled;
struct stat statbuf;
FreshLine = 1;
if (IStackPtr+1 >= INCLUDE_NEST) return E_NESTED_INCLUDE;
i = &IStack[IStackPtr];
if (FileName) {
i->filename = StrDup(FileName);
if (!i->filename) return E_NO_MEM;
} else {
i->filename = NULL;
}
i->LineNo = LineNo;
i->NumIfs = NumIfs;
i->IfFlags = IfFlags;
i->CLine = CLine;
i->offset = -1L;
i->chain = NULL;
if (RunDisabled & RUN_NOTOWNER) {
i->ownedByMe = 0;
} else {
i->ownedByMe = 1;
}
if (fp) {
i->offset = ftell(fp);
FCLOSE(fp);
}
IStackPtr++;
#ifdef HAVE_GLOB
/* If it's a directory, set up the glob chain here. */
if (stat(fname, &statbuf) == 0) {
FilenameChain *fc;
if (S_ISDIR(statbuf.st_mode)) {
if (SetupGlobChain(fname, i) == OK) { /* Glob succeeded */
if (!i->chain) { /* Oops... no matching files */
if (!Hush) {
Eprint("%s: %s", fname, ErrMsg[E_NO_MATCHING_REMS]);
}
PopFile();
return E_NO_MATCHING_REMS;
}
while(i->chain) {
fc = i->chain;
i->chain = i->chain->next;
/* Munch first file */
oldRunDisabled = RunDisabled;
if (!OpenFile(fc->filename)) {
return OK;
}
Eprint("%s: %s", ErrMsg[E_CANT_OPEN], fc->filename);
RunDisabled = oldRunDisabled;
}
/* Couldn't open anything... bail */
return PopFile();
} else {
if (!Hush) {
Eprint("%s: %s", fname, ErrMsg[E_NO_MATCHING_REMS]);
}
}
return E_NO_MATCHING_REMS;
}
}
#endif
oldRunDisabled = RunDisabled;
/* Try to open the new file */
if (!OpenFile(fname)) {
return OK;
}
RunDisabled = oldRunDisabled;
Eprint("%s: %s", ErrMsg[E_CANT_OPEN], fname);
/* Ugh! We failed! */
PopFile();
return E_CANT_OPEN;
}
/***************************************************************/
/* */
/* GetAccessDate - get the access date of a file. */
/* */
/***************************************************************/
int GetAccessDate(char const *file)
{
struct stat statbuf;
struct tm *t1;
if (stat(file, &statbuf)) return -1;
t1 = localtime(&(statbuf.st_atime));
if (t1->tm_year + 1900 < BASE)
return 0;
else
return Julian(t1->tm_year+1900, t1->tm_mon, t1->tm_mday);
}
/***************************************************************/
/* */
/* DestroyCache */
/* */
/* Free all the memory used by a cached file. */
/* */
/***************************************************************/
static void DestroyCache(CachedFile *cf)
{
CachedLine *cl, *cnext;
CachedFile *temp;
if (cf->filename) free((char *) cf->filename);
cl = cf->cache;
while (cl) {
if (cl->text) free ((char *) cl->text);
cnext = cl->next;
free(cl);
cl = cnext;
}
if (CachedFiles == cf) CachedFiles = cf->next;
else {
temp = CachedFiles;
while(temp) {
if (temp->next == cf) {
temp->next = cf->next;
break;
}
temp = temp->next;
}
}
free(cf);
}
/***************************************************************/
/* */
/* TopLevel */
/* */
/* Returns 1 if current file is top level, 0 otherwise. */
/* */
/***************************************************************/
int TopLevel(void)
{
return IStackPtr <= 1;
}
/***************************************************************/
/* */
/* CheckSafety */
/* */
/* Returns 1 if current file is safe to read; 0 otherwise. */
/* Currently only meaningful for UNIX. If we are running as */
/* root, we refuse to open files not owned by root. */
/* We also reject world-writable files, no matter */
/* who we're running as. */
/* As a side effect, if we don't own the file, we disable RUN */
/***************************************************************/
static int CheckSafety(void)
{
struct stat statbuf;
if (fp == stdin) {
return 1;
}
if (fstat(fileno(fp), &statbuf)) {
fclose(fp);
fp = NULL;
return 0;
}
/* Under UNIX, take extra precautions if running as root */
if (!geteuid()) {
/* Reject files not owned by root or group/world writable */
if (statbuf.st_uid != 0) {
fprintf(ErrFp, "SECURITY: Won't read non-root-owned file when running as root!\n");
fclose(fp);
fp = NULL;
return 0;
}
}
/* Sigh... /dev/null is usually world-writable, so ignore devices,
FIFOs, sockets, etc. */
if (!S_ISREG(statbuf.st_mode)) {
return 1;
}
if ((statbuf.st_mode & S_IWOTH)) {
fprintf(ErrFp, "SECURITY: Won't read world-writable file!\n");
fclose(fp);
fp = NULL;
return 0;
}
/* If file is not owned by me, disable RUN command */
if (statbuf.st_uid != geteuid()) {
RunDisabled |= RUN_NOTOWNER;
}
return 1;
}

2937
src/funcs.c Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -8,15 +8,15 @@
/* globals.h and err.h */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: globals.c,v 1.1 1996-03-27 03:25:57 dfs Exp $";
#include "config.h"
#include <stdio.h> /* For defintion of FILE - sigh! */
#include "types.h"
#include "custom.h"
#define MK_GLOBALS
#include "globals.h"
#include "err.h"

View File

@@ -7,12 +7,10 @@
/* MK_GLOBALS. Also contains useful macro definitions. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: globals.h,v 1.1 1996-03-27 03:25:57 dfs Exp $ */
#ifdef MK_GLOBALS
#undef EXTERN
#define EXTERN
@@ -23,6 +21,8 @@
#define INIT(var, val) var
#endif
#define MINUTES_PER_DAY 1440
#define DaysInYear(y) (((y) % 4) ? 365 : ((!((y) % 100) && ((y) % 400)) ? 365 : 366 ))
#define IsLeapYear(y) (((y) % 4) ? 0 : ((!((y) % 100) && ((y) % 400)) ? 0 : 1 ))
#define DaysInMonth(m, y) ((m) != 1 ? MonthDays[m] : 28 + IsLeapYear(y))
@@ -36,32 +36,33 @@ EXTERN int CurMon;
EXTERN int CurYear;
EXTERN int LineNo;
EXTERN int FreshLine;
EXTERN char LineBuffer[LINELEN];
EXTERN char SubstBuffer[LINELEN];
EXTERN char TokBuffer[TOKSIZE+1];
EXTERN INIT( char *MsgCommand, NULL);
EXTERN INIT( char const *MsgCommand, NULL);
EXTERN INIT( int ShowAllErrors, 0);
EXTERN INIT( int DebugFlag, 0);
EXTERN INIT( int DoCalendar, 0);
EXTERN INIT( int DoSimpleCalendar, 0);
EXTERN INIT( int DoSimpleCalDelta, 0);
EXTERN INIT( int DoPrefixLineNo, 0);
EXTERN INIT( int MondayFirst, 0);
EXTERN INIT( int Iterations, 1);
EXTERN INIT( int PsCal, 0);
EXTERN INIT( int CalWidth, 80);
EXTERN INIT( int CalWidth, -1);
EXTERN INIT( int CalWeeks, 0);
EXTERN INIT( int CalMonths, 0);
EXTERN INIT( int Hush, 0);
EXTERN INIT( int NextMode, 0);
EXTERN INIT( int InfiniteDelta, 0);
EXTERN INIT( int DeltaOffset, 0);
EXTERN INIT( int RunDisabled, 0);
EXTERN INIT( int IgnoreOnce, 0);
EXTERN INIT( int SortByTime, 0);
EXTERN INIT( int SortByDate, 0);
EXTERN INIT( int SortByPrio, 0);
EXTERN INIT( int UntimedBeforeTimed, 0);
EXTERN INIT( int DefaultPrio, NO_PRIORITY);
EXTERN INIT( long SysTime, -1L);
EXTERN char *InitialFile;
EXTERN char const *InitialFile;
EXTERN int FileAccessDate;
EXTERN INIT( int DontFork, 0);
@@ -69,25 +70,42 @@ EXTERN INIT( int DontQueue, 0);
EXTERN INIT( int NumQueued, 0);
EXTERN INIT( int DontIssueAts, 0);
EXTERN INIT( int Daemon, 0);
EXTERN INIT( char DateSep, DATESEP);
EXTERN INIT( char TimeSep, TIMESEP);
EXTERN INIT( char DateTimeSep, DATETIMESEP);
EXTERN INIT( int DefaultColorR, -1);
EXTERN INIT( int DefaultColorB, -1);
EXTERN INIT( int DefaultColorG, -1);
EXTERN INIT( int SynthesizeTags, 0);
EXTERN INIT( int ScFormat, SC_AMPM);
EXTERN INIT( int MaxSatIter, 150);
EXTERN INIT( int MaxStringLen, MAX_STR_LEN);
EXTERN INIT( char *FileName, NULL);
EXTERN INIT( int UseStdin, 0);
EXTERN INIT( int PurgeMode, 0);
EXTERN INIT( int PurgeIncludeDepth, 0);
EXTERN FILE *ErrFp;
EXTERN INIT( FILE *PurgeFP, NULL);
EXTERN INIT( int NumIfs, 0);
EXTERN INIT( unsigned int IfFlags, 0);
EXTERN INIT( int LastTriggerDate, 0);
EXTERN INIT( int LastTrigValid, 0);
EXTERN Trigger LastTrigger;
EXTERN TimeTrig LastTimeTrig;
EXTERN INIT( int LastTriggerDate, 0);
EXTERN INIT( int LastTriggerTime, 0);
EXTERN INIT( int ShouldCache, 0);
EXTERN char *CurLine;
EXTERN char const *CurLine;
EXTERN INIT( int NumTriggered, 0);
EXTERN int ArgC;
EXTERN char **ArgV;
EXTERN char const **ArgV;
EXTERN INIT( int CalLines, CAL_LINES);
EXTERN INIT( int CalPad, 1);
EXTERN INIT( int UseVTChars, 0);
EXTERN INIT( int UseUTF8Chars, 0);
EXTERN INIT( int UseVTColors, 0);
EXTERN INIT( int Use256Colors, 0);
EXTERN INIT( int UseTrueColors, 0);
EXTERN INIT( int TerminalBackground, TERMINAL_BACKGROUND_UNKNOWN);
/* Latitude and longitude */
EXTERN INIT( int LatDeg, LAT_DEG);
@@ -113,9 +131,11 @@ EXTERN INIT( char *EndSentIg, "\"')]}>");
/* We need the language stuff here... */
#include "lang.h"
#include "dynbuf.h"
EXTERN INIT( char Banner[LINELEN], L_BANNER);
EXTERN DynamicBuffer Banner;
EXTERN DynamicBuffer LineBuffer;
EXTERN DynamicBuffer ExprBuf;
/* List of months */
EXTERN char *EnglishMonthName[]
#ifdef MK_GLOBALS
@@ -171,12 +191,3 @@ EXTERN int MonthIndex[2][12]
#endif
;
#if defined(__OS2__)
#if defined(_MSC_VER) || defined(__EMX__)
#define OS2MODE (_osmode == OS2_MODE)
#define DOSMODE (_osmode == DOS_MODE)
#else
#define OS2MODE 1
#define DOSMODE 0
#endif
#endif

View File

@@ -5,17 +5,16 @@
/* Support for the Hebrew calendar */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/* Derived from code written by Amos Shapir in 1978; revised */
/* 1985. */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: hbcal.c,v 1.1 1996-03-27 03:25:58 dfs Exp $";
#include "config.h"
#include <stdio.h> /* For FILE used by protos.h - sigh. */
#include "config.h"
#include "types.h"
#include "protos.h"
#include "globals.h"
@@ -55,7 +54,7 @@ static char const RCSID[] = "$Id: hbcal.c,v 1.1 1996-03-27 03:25:58 dfs Exp $";
#define ADAR2ADARA 1
#define ADAR2BOTH 2
static char *HebMonthNames[] = {
static char const *HebMonthNames[] = {
"Tishrey", "Heshvan", "Kislev", "Tevet", "Shvat", "Adar A", "Adar B",
"Nisan", "Iyar", "Sivan", "Tamuz", "Av", "Elul", "Adar"};
@@ -63,7 +62,7 @@ static char MaxMonLen[] = {
30, 30, 30, 29, 30, 30, 29, 30, 29, 30, 29, 30, 29, 29};
static char HebIsLeap[] = {0,0,1,0,0,1,0,1,0,0,1,0,0,1,0,0,1,0,1};
/***************************************************************/
/* */
/* RoshHashana */
@@ -72,12 +71,7 @@ static char HebIsLeap[] = {0,0,1,0,0,1,0,1,0,0,1,0,0,1,0,0,1,0,1};
/* Hebrew year. (ie, 5751, not 1990) */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int RoshHashana(int i)
#else
int RoshHashana(i)
int i;
#endif
int RoshHashana(int i)
{
long j;
j = DaysToHebYear(i-3744) - CORRECTION;
@@ -92,12 +86,7 @@ int i;
/* from new moon before Tishrey 1 5701. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC long DaysToHebYear(int y)
#else
long DaysToHebYear(y)
int y;
#endif
long DaysToHebYear(int y)
{
long m, nm, dw, s, l;
@@ -130,12 +119,7 @@ int y;
/* */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int DaysInHebYear(int y)
#else
int DaysInHebYear(y)
int y;
#endif
int DaysInHebYear(int y)
{
long thisyear, nextyear;
@@ -152,15 +136,10 @@ int y;
/* given the LENGTH of the Hebrew year. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC char *DaysInHebMonths(int ylen)
#else
char *DaysInHebMonths(ylen)
int ylen;
#endif
char const *DaysInHebMonths(int ylen)
{
static char monlen[13] =
{30, 29, 30, 29, 30, 0, 29, 30, 29, 30, 29, 30, 29};
static char monlen[14] =
{30, 29, 30, 29, 30, 0, 29, 30, 29, 30, 29, 30, 29, 29};
if (ylen > 355) {
@@ -183,15 +162,10 @@ int ylen;
/* non-leap-years. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int HebToJul(int hy, int hm, int hd)
#else
int HebToJul(hy, hm, hd)
int hy, hm, hd;
#endif
int HebToJul(int hy, int hm, int hd)
{
int ylen;
char *monlens;
char const *monlens;
int rh;
int m;
@@ -221,17 +195,12 @@ int hy, hm, hd;
/* non-leap-years. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC void JulToHeb(int jul, int *hy, int *hm, int *hd)
#else
void JulToHeb(jul, hy, hm, hd)
int jul, *hy, *hm, *hd;
#endif
void JulToHeb(int jul, int *hy, int *hm, int *hd)
{
int y, m, d;
int rh;
int ylen;
char *monlen;
char const *monlen;
/* Get the common year */
FromJulian(jul, &y, &m, &d);
y += 3763; /* Over-estimate a bit to be on the safe side below... */
@@ -262,12 +231,7 @@ int jul, *hy, *hm, *hd;
/* year. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int HebNameToNum(const char *mname)
#else
int HebNameToNum(mname)
char *mname;
#endif
int HebNameToNum(char const *mname)
{
int i;
int m=-1;
@@ -289,12 +253,7 @@ char *mname;
/* year. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC char *HebMonthName(int m, int y)
#else
char *HebMonthName(m, y)
int m, y;
#endif
char const *HebMonthName(int m, int y)
{
if (m != ADARA && m != ADARB) return HebMonthNames[m];
@@ -330,15 +289,10 @@ int m, y;
/* Change 30 Adar A to 30 Shvat in nonleap */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int GetValidHebDate(int yin, int min, int din, int adarbehave,
int GetValidHebDate(int yin, int min, int din, int adarbehave,
int *mout, int *dout, int jahr)
#else
int GetValidHebDate(yin, min, din, adarbehave, mout, dout, jahr)
int yin, min, din, adarbehave, *mout, *dout, jahr;
#endif
{
char *monlen;
char const *monlen;
int ylen;
*mout = min;
@@ -435,13 +389,8 @@ int yin, min, din, adarbehave, *mout, *dout, jahr;
/* Returns 0 for success, non-zero for failure. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int GetNextHebrewDate(int julstart, int hm, int hd,
int GetNextHebrewDate(int julstart, int hm, int hd,
int jahr, int adarbehave, int *ans)
#else
int GetNextHebrewDate(julstart, hm, hd, jahr, adarbehave, ans)
int julstart, hm, hd, jahr, adarbehave, *ans;
#endif
{
int r, yout, mout, dout, jul=1;
int adarflag = adarbehave;
@@ -496,14 +445,9 @@ int julstart, hm, hd, jahr, adarbehave, *ans;
/* Given a date of death, compute the value to use for jahr. */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC int ComputeJahr(int y, int m, int d, int *ans)
#else
int ComputeJahr(y, m, d, ans)
int y, m, d, *ans;
#endif
int ComputeJahr(int y, int m, int d, int *ans)
{
char *monlen;
char const *monlen;
int len;
*ans = JAHR_NONE;

View File

@@ -7,35 +7,28 @@
/* in normal mode. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
static char const RCSID[] = "$Id: init.c,v 1.3 1996-10-27 21:28:03 dfs Exp $";
#include "version.h"
#include "config.h"
#define L_IN_INIT 1
#include "config.h"
#include <stdio.h>
#include <string.h>
#ifdef HAVE_STDLIB_H
#include <ctype.h>
#include <stdlib.h>
#endif
#ifdef HAVE_MALLOC_H
#include <malloc.h>
#endif
#ifdef UNIX
#include <sys/types.h>
#include <pwd.h>
#ifdef HAVE_UNISTD
#include <unistd.h>
#endif
#endif
#include <ctype.h>
#include <sys/ioctl.h>
#include "types.h"
#include "protos.h"
#include "expr.h"
#include "err.h"
#include "version.h"
#include "globals.h"
/***************************************************************
@@ -46,9 +39,12 @@ static char const RCSID[] = "$Id: init.c,v 1.3 1996-10-27 21:28:03 dfs Exp $";
* simple calendar format.
* -r = Disallow RUN mode
* -c[n] = Produce a calendar for n months (default = 1)
* -@[n,m] = Colorize n=0 VT100 n=1 85 n=2 True m=0 dark terminal m=1 light
* -w[n,n,n] = Specify output device width, padding and spacing
* -s[n] = Produce calendar in "simple calendar" format
* -p[n] = Produce calendar in format compatible with rem2ps
* -l = Prefix simple calendar lines with a comment containing
* their trigger line numbers and filenames
* -v = Verbose mode
* -o = Ignore ONCE directives
* -a = Don't issue timed reminders which will be queued
@@ -57,13 +53,14 @@ static char const RCSID[] = "$Id: init.c,v 1.3 1996-10-27 21:28:03 dfs Exp $";
* -h = Hush mode
* -f = Do not fork
* -dchars = Debugging mode: Chars are:
* f = Trace file openings
* e = Echo input lines
* x = Display expression evaluation
* t = Display trigger dates
* v = Dump variables at end
* l = Display entire line in error messages
* -e = Send messages normally sent to stderr to stdout instead
* -z[n] = Daemon mode waking up every n (def 5) minutes.
* -z[n] = Daemon mode waking up every n (def 1) minutes.
* -bn = Time format for cal (0, 1, or 2)
* -xn = Max. number of iterations for SATISFY
* -uname = Run as user 'name' - only valid when run by root. If run
@@ -71,9 +68,13 @@ static char const RCSID[] = "$Id: init.c,v 1.3 1996-10-27 21:28:03 dfs Exp $";
* -kcmd = Run 'cmd' for MSG-type reminders instead of printing to stdout
* -iVAR=EXPR = Initialize and preserve VAR.
* -m = Start calendar with Monday instead of Sunday.
* -j[n] = Purge all junk from reminder files (n = INCLUDE depth)
* A minus sign alone indicates to take input from stdin
*
**************************************************************/
#if defined(__APPLE__) || defined(__CYGWIN__)
static void rkrphgvba(int x);
#endif
/* For parsing an integer */
#define PARSENUM(var, s) \
@@ -84,13 +85,41 @@ while (isdigit(*(s))) { \
s++; \
}
#ifdef UNIX
PRIVATE void ChgUser ARGS((char *uname));
#endif
static void ChgUser(char const *u);
static void InitializeVar(char const *str);
PRIVATE void InitializeVar ARGS ((char *str));
static char const *BadDate = "Illegal date on command line\n";
static char *BadDate = "Illegal date on command line\n";
static DynamicBuffer default_filename_buf;
/***************************************************************/
/* */
/* DefaultFilename */
/* */
/* If we're invoked as "rem" rather than "remind", use a */
/* default filename. Use $DOTREMINDERS or $HOME/.reminders */
/* */
/***************************************************************/
static char const *DefaultFilename(void)
{
char const *s;
DBufInit(&default_filename_buf);
s = getenv("DOTREMINDERS");
if (s) {
return s;
}
s = getenv("HOME");
if (!s) {
fprintf(stderr, "HOME environment variable not set. Unable to determine reminder file.\n");
exit(1);
}
DBufPuts(&default_filename_buf, s);
DBufPuts(&default_filename_buf, "/.reminders");
return DBufValue(&default_filename_buf);
}
/***************************************************************/
/* */
@@ -99,18 +128,52 @@ static char *BadDate = "Illegal date on command line\n";
/* Initialize the system - called only once at beginning! */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PUBLIC void InitRemind(int argc, char *argv[])
#else
void InitRemind(argc, argv)
int argc;
char *argv[];
#endif
void InitRemind(int argc, char const *argv[])
{
char *arg;
char const *arg;
int i;
int y, m, d, rep;
Token tok;
int InvokedAsRem = 0;
char const *s;
int weeks;
int x;
int jul;
#if defined(__APPLE__)
rkrphgvba(0);
#elif defined(__CYGWIN__)
rkrphgvba(1);
#endif
jul = NO_DATE;
/* If stdout is a terminal, initialize $FormWidth to terminal width-8,
but clamp to [20, 500] */
if (isatty(STDOUT_FILENO)) {
struct winsize w;
if (ioctl(STDOUT_FILENO, TIOCGWINSZ, &w) == 0) {
FormWidth = w.ws_col - 8;
if (FormWidth < 20) FormWidth = 20;
if (FormWidth > 500) FormWidth = 500;
}
}
/* Initialize global dynamic buffers */
DBufInit(&Banner);
DBufInit(&LineBuffer);
DBufInit(&ExprBuf);
DBufPuts(&Banner, L_BANNER);
PurgeFP = NULL;
/* Make sure remind is not installed set-uid or set-gid */
if (getgid() != getegid() ||
getuid() != geteuid()) {
fprintf(ErrFp, "\nRemind should not be installed set-uid or set-gid.\nCHECK YOUR SYSTEM SECURITY.\n");
exit(1);
}
y = NO_YR;
m = NO_MON;
@@ -125,21 +188,22 @@ char *argv[];
JulianToday = RealToday;
FromJulian(JulianToday, &CurYear, &CurMon, &CurDay);
#if !defined(HAVE_QUEUED)
DontFork = 1;
DontQueue = 1;
NumQueued = 0;
DontIssueAts = 0;
Daemon = 0;
#elif defined(_MSC_VER) || defined(__BORLANDC__)
DontFork = 1;
#elif defined(__OS2__) && defined (__MSDOS__)
if (DOSMODE)
DontFork = 1;
#endif
/* See if we were invoked as "rem" rather than "remind" */
if (argv[0]) {
s = strrchr(argv[0], '/');
if (!s) {
s = argv[0];
} else {
s++;
}
if (!strcmp(s, "rem")) {
InvokedAsRem = 1;
}
}
/* Parse the command-line options */
i = 1;
while (i < argc) {
arg = argv[i];
if (*arg != '-') break; /* Exit the loop if it's not an option */
@@ -154,24 +218,50 @@ char *argv[];
while (*arg) {
switch(*arg++) {
case '@':
UseVTColors = 1;
if (*arg) {
PARSENUM(x, arg);
if (x == 1) {
Use256Colors = 1;
} else if (x == 2) {
UseTrueColors = 1;
}
}
if (*arg == ',') {
arg++;
PARSENUM(x, arg);
if (x == 0) {
TerminalBackground = TERMINAL_BACKGROUND_DARK;
} else if (x == 1) {
TerminalBackground = TERMINAL_BACKGROUND_LIGHT;
}
}
break;
case 'j':
case 'J':
PurgeMode = 1;
if (*arg) {
PARSENUM(PurgeIncludeDepth, arg);
}
break;
case 'i':
case 'I':
InitializeVar(arg);
while(*arg) arg++;
break;
case 'n':
case 'N':
NextMode = 1;
#ifdef HAVE_QUEUED
DontQueue = 1;
Daemon = 0;
#endif
break;
case 'r':
case 'R':
RunDisabled = 1;
RunDisabled = RUN_CMDLINE;
break;
case 'm':
@@ -184,11 +274,22 @@ char *argv[];
IgnoreOnce = 1;
break;
case 't':
case 'T':
InfiniteDelta = 1;
case 'y':
case 'Y':
SynthesizeTags = 1;
break;
case 't':
case 'T':
if (!*arg) {
InfiniteDelta = 1;
} else {
PARSENUM(DeltaOffset, arg);
if (DeltaOffset < 0) {
DeltaOffset = 0;
}
}
break;
case 'e':
case 'E':
ErrFp = stdout;
@@ -204,6 +305,7 @@ char *argv[];
SortByDate = SORT_ASCEND;
SortByTime = SORT_ASCEND;
SortByPrio = SORT_ASCEND;
UntimedBeforeTimed = 0;
if (*arg) {
if (*arg == 'D' || *arg == 'd')
SortByDate = SORT_DESCEND;
@@ -219,28 +321,37 @@ char *argv[];
SortByPrio = SORT_DESCEND;
arg++;
}
if (*arg) {
if (*arg == 'D' || *arg == 'd')
UntimedBeforeTimed = 1;
arg++;
}
break;
#if defined(UNIX) && defined(WANT_U_OPTION)
case 'u':
case 'U':
ChgUser(arg);
RunDisabled = RUN_CMDLINE;
while (*arg) arg++;
break;
#endif
#ifdef HAVE_QUEUED
case 'z':
case 'Z':
DontFork = 1;
PARSENUM(Daemon, arg);
if (Daemon<5) Daemon=5;
else if (Daemon>60) Daemon=60;
if (*arg == '0') {
PARSENUM(Daemon, arg);
if (Daemon == 0) Daemon = -1;
else if (Daemon < 1) Daemon = 1;
else if (Daemon > 60) Daemon = 60;
} else {
PARSENUM(Daemon, arg);
if (Daemon<1) Daemon=1;
else if (Daemon>60) Daemon=60;
}
break;
case 'a':
case 'A':
DontIssueAts = 1;
DontIssueAts++;
break;
case 'q':
@@ -252,12 +363,41 @@ char *argv[];
case 'F':
DontFork = 1;
break;
#endif
case 'c':
case 'C':
DoCalendar = 1;
if (*arg == '+') {
arg++;
weeks = 0;
/* Parse the flags */
while(*arg) {
if (*arg == 'a' ||
*arg == 'A') {
DoSimpleCalDelta = 1;
arg++;
continue;
}
if (*arg == '+') {
weeks = 1;
arg++;
continue;
}
if (*arg == 'l' || *arg == 'L') {
UseVTChars = 1;
arg++;
continue;
}
if (*arg == 'u' || *arg == 'U') {
UseUTF8Chars = 1;
arg++;
continue;
}
if (*arg == 'c' || *arg == 'C') {
UseVTColors = 1;
arg++;
continue;
}
break;
}
if (weeks) {
PARSENUM(CalWeeks, arg);
if (!CalWeeks) CalWeeks = 1;
} else {
@@ -269,8 +409,21 @@ char *argv[];
case 's':
case 'S':
DoSimpleCalendar = 1;
if (*arg == '+') {
arg++;
weeks = 0;
while(*arg) {
if (*arg == 'a' || *arg == 'A') {
DoSimpleCalDelta = 1;
arg++;
continue;
}
if (*arg == '+') {
arg++;
weeks = 1;
continue;
}
break;
}
if (weeks) {
PARSENUM(CalWeeks, arg);
if (!CalWeeks) CalWeeks = 1;
} else {
@@ -282,16 +435,40 @@ char *argv[];
case 'p':
case 'P':
DoSimpleCalendar = 1;
PsCal = 1;
PsCal = PSCAL_LEVEL1;
while (*arg == 'a' || *arg == 'A' ||
*arg == 'p' || *arg == 'P') {
if (*arg == 'a' || *arg == 'A') {
DoSimpleCalDelta = 1;
} else if (*arg == 'p' || *arg == 'P') {
/* JSON interchange formats always include
file and line number info */
DoPrefixLineNo = 1;
if (PsCal == PSCAL_LEVEL1) {
PsCal = PSCAL_LEVEL2;
} else {
PsCal = PSCAL_LEVEL3;
}
}
arg++;
}
PARSENUM(CalMonths, arg);
if (!CalMonths) CalMonths = 1;
break;
case 'l':
case 'L':
DoPrefixLineNo = 1;
break;
case 'w':
case 'W':
if (*arg != ',') {
PARSENUM(CalWidth, arg);
if (CalWidth < 80) CalWidth = 80;
if (CalWidth != 0 && CalWidth < 71) CalWidth = 71;
if (CalWidth == 0) {
CalWidth = -1;
}
}
if (*arg == ',') {
arg++;
@@ -311,11 +488,12 @@ char *argv[];
case 'D':
while (*arg) {
switch(*arg++) {
case 'e': case 'E': DebugFlag |= DB_ECHO_LINE; break;
case 'x': case 'X': DebugFlag |= DB_PRTEXPR; break;
case 't': case 'T': DebugFlag |= DB_PRTTRIG; break;
case 'v': case 'V': DebugFlag |= DB_DUMP_VARS; break;
case 'l': case 'L': DebugFlag |= DB_PRTLINE; break;
case 'e': case 'E': DebugFlag |= DB_ECHO_LINE; break;
case 'x': case 'X': DebugFlag |= DB_PRTEXPR; break;
case 't': case 'T': DebugFlag |= DB_PRTTRIG; break;
case 'v': case 'V': DebugFlag |= DB_DUMP_VARS; break;
case 'l': case 'L': DebugFlag |= DB_PRTLINE; break;
case 'f': case 'F': DebugFlag |= DB_TRACE_FILES; break;
default:
fprintf(ErrFp, ErrMsg[M_BAD_DB_FLAG], *(arg-1));
}
@@ -354,11 +532,15 @@ char *argv[];
}
/* Get the filename. */
if (i >= argc) {
Usage();
exit(1);
if (!InvokedAsRem) {
if (i >= argc) {
Usage();
exit(1);
}
InitialFile = argv[i++];
} else {
InitialFile = DefaultFilename();
}
InitialFile = argv[i++];
/* Get the date, if any */
if (i < argc) {
@@ -370,25 +552,37 @@ char *argv[];
if (SysTime != -1L) Usage();
else {
SysTime = (long) tok.val * 60L;
#ifdef HAVE_QUEUED
DontQueue = 1;
Daemon = 0;
#endif
}
break;
case T_DateTime:
if (SysTime != -1L) Usage();
if (m != NO_MON || d != NO_DAY || y != NO_YR || jul != NO_DATE) Usage();
SysTime = (tok.val % MINUTES_PER_DAY) * 60;
DontQueue = 1;
Daemon = 0;
jul = tok.val / MINUTES_PER_DAY;
break;
case T_Date:
if (m != NO_MON || d != NO_DAY || y != NO_YR || jul != NO_DATE) Usage();
jul = tok.val;
break;
case T_Month:
if (m != NO_MON) Usage();
if (m != NO_MON || jul != NO_DATE) Usage();
else m = tok.val;
break;
case T_Day:
if (d != NO_DAY) Usage();
if (d != NO_DAY || jul != NO_DATE) Usage();
else d = tok.val;
break;
case T_Year:
if (y != NO_YR) Usage();
if (y != NO_YR || jul != NO_DATE) Usage();
else y = tok.val;
break;
@@ -397,7 +591,8 @@ char *argv[];
else rep = tok.val;
break;
default: Usage();
default:
Usage();
}
}
@@ -407,6 +602,9 @@ char *argv[];
Daemon = 0;
}
if (jul != NO_DATE) {
FromJulian(jul, &y, &m, &d);
}
/* Must supply date in the form: day, mon, yr OR mon, yr */
if (m != NO_MON || y != NO_YR || d != NO_DAY) {
if (m == NO_MON || y == NO_YR) {
@@ -420,12 +618,12 @@ char *argv[];
}
if (d == NO_DAY) d=1;
if (d > DaysInMonth(m, y)) {
fprintf(ErrFp, BadDate);
fprintf(ErrFp, "%s", BadDate);
Usage();
}
JulianToday = Julian(y, m, d);
if (JulianToday == -1) {
fprintf(ErrFp, BadDate);
fprintf(ErrFp, "%s", BadDate);
Usage();
}
CurYear = y;
@@ -437,7 +635,7 @@ char *argv[];
}
/* Figure out the offset from UTC */
if (CalculateUTC)
(void) CalcMinsFromUTC(JulianToday, SystemTime(1)/60,
(void) CalcMinsFromUTC(JulianToday, SystemTime(0)/60,
&MinsFromUTC, NULL);
}
@@ -449,13 +647,9 @@ char *argv[];
/* */
/***************************************************************/
#ifndef L_USAGE_OVERRIDE
#ifdef HAVE_PROTOS
PUBLIC void Usage(void)
#else
void Usage()
#endif /* HAVE_PROTOS */
void Usage(void)
{
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-1996 by David F. Skoll\n", VERSION, L_LANGNAME);
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-2020 Dianne Skoll\n", VERSION, L_LANGNAME);
#ifdef BETA
fprintf(ErrFp, ">>>> BETA VERSION <<<<\n");
#endif
@@ -463,29 +657,31 @@ void Usage()
fprintf(ErrFp, "Options:\n");
fprintf(ErrFp, " -n Output next occurrence of reminders in simple format\n");
fprintf(ErrFp, " -r Disable RUN directives\n");
fprintf(ErrFp, " -c[n] Produce a calendar for n (default 1) months\n");
fprintf(ErrFp, " -c+[n] Produce a calendar for n (default 1) weeks\n");
fprintf(ErrFp, " -@[n,m] Colorize COLOR reminders\n");
fprintf(ErrFp, " -c[a][n] Produce a calendar for n (default 1) months\n");
fprintf(ErrFp, " -c[a]+[n] Produce a calendar for n (default 1) weeks\n");
fprintf(ErrFp, " -w[n[,p[,s]]] Specify width, padding and spacing of calendar\n");
fprintf(ErrFp, " -s[+][n] Produce `simple calendar' for n (1) months (weeks)\n");
fprintf(ErrFp, " -p[n] Same as -s, but input compatible with rem2ps\n");
fprintf(ErrFp, " -s[a][+][n] Produce `simple calendar' for n (1) months (weeks)\n");
fprintf(ErrFp, " -p[a][n] Same as -s, but input compatible with rem2ps\n");
fprintf(ErrFp, " -l Prefix each simple calendar line with line number and filename comment\n");
fprintf(ErrFp, " -v Verbose mode\n");
fprintf(ErrFp, " -o Ignore ONCE directives\n");
fprintf(ErrFp, " -t Trigger all future reminders regardless of delta\n");
fprintf(ErrFp, " -t[n] Trigger all future (or those within `n' days)\n");
fprintf(ErrFp, " -h `Hush' mode - be very quiet\n");
#ifdef HAVE_QUEUED
fprintf(ErrFp, " -a Don't trigger timed reminders immediately - just queue them\n");
fprintf(ErrFp, " -q Don't queue timed reminders\n");
fprintf(ErrFp, " -f Trigger timed reminders by staying in foreground\n");
fprintf(ErrFp, " -z[n] Enter daemon mode, waking every n (5) minutes.\n");
#endif
fprintf(ErrFp, " -d... Debug: e=echo x=expr-eval t=trig v=dumpvars l=showline\n");
fprintf(ErrFp, " -z[n] Enter daemon mode, waking every n (1) minutes.\n");
fprintf(ErrFp, " -d... Debug: e=echo x=expr-eval t=trig v=dumpvars l=showline f=tracefiles\n");
fprintf(ErrFp, " -e Divert messages normally sent to stderr to stdout\n");
fprintf(ErrFp, " -b[n] Time format for cal: 0=am/pm, 1=24hr, 2=none\n");
fprintf(ErrFp, " -x[n] Iteration limit for SATISFY clause (def=150)\n");
fprintf(ErrFp, " -kcmd Run `cmd' for MSG-type reminders\n");
fprintf(ErrFp, " -g[ddd] Sort reminders by date, time and priority before issuing\n");
fprintf(ErrFp, " -g[dddd] Sort reminders by date, time, priority, and 'timedness'\n");
fprintf(ErrFp, " -ivar=val Initialize var to val and preserve var\n");
fprintf(ErrFp, " -m Start calendar with Monday rather than Sunday\n");
fprintf(ErrFp, " -y Synthesize tags for tagless reminders\n");
fprintf(ErrFp, " -j[n] Run in 'purge' mode. [n = INCLUDE depth]\n");
exit(1);
}
#endif /* L_USAGE_OVERRIDE */
@@ -499,23 +695,15 @@ void Usage()
/* USER environment variables. */
/* */
/***************************************************************/
#if defined(UNIX) && defined(WANT_U_OPTION)
#ifdef HAVE_PROTOS
PRIVATE void ChgUser(char *user)
#else
static void ChgUser(user)
char *user;
#endif /* HAVE_PROTOS */
static void ChgUser(char const *user)
{
#ifdef SYSV
/* uid_t myuid; This seems to mess up on XENIX, so forget it... */
int myuid;
#else
int myuid;
#endif
uid_t myuid;
struct passwd *pwent;
static char *home, *shell, *username, *logname;
static char *home;
static char *shell;
static char *username;
static char *logname;
myuid = getuid();
@@ -538,7 +726,7 @@ char *user;
home = malloc(strlen(pwent->pw_dir) + 6);
if (!home) {
fprintf(ErrFp, ErrMsg[M_NOMEM_ENV]);
fprintf(ErrFp, "%s", ErrMsg[M_NOMEM_ENV]);
exit(1);
}
sprintf(home, "HOME=%s", pwent->pw_dir);
@@ -546,7 +734,7 @@ char *user;
shell = malloc(strlen(pwent->pw_shell) + 7);
if (!shell) {
fprintf(ErrFp, ErrMsg[M_NOMEM_ENV]);
fprintf(ErrFp, "%s", ErrMsg[M_NOMEM_ENV]);
exit(1);
}
sprintf(shell, "SHELL=%s", pwent->pw_shell);
@@ -555,22 +743,34 @@ char *user;
if (pwent->pw_uid) {
username = malloc(strlen(pwent->pw_name) + 6);
if (!username) {
fprintf(ErrFp, ErrMsg[M_NOMEM_ENV]);
fprintf(ErrFp, "%s", ErrMsg[M_NOMEM_ENV]);
exit(1);
}
sprintf(username, "USER=%s", pwent->pw_name);
putenv(username);
logname= malloc(strlen(pwent->pw_name) + 9);
if (!logname) {
fprintf(ErrFp, ErrMsg[M_NOMEM_ENV]);
fprintf(ErrFp, "%s", ErrMsg[M_NOMEM_ENV]);
exit(1);
}
sprintf(logname, "LOGNAME=%s", pwent->pw_name);
putenv(logname);
}
}
#endif /* UNIX && WANT_U_OPTION */
static void
DefineFunction(char const *str)
{
Parser p;
int r;
CreateParser(str, &p);
r = DoFset(&p);
DestroyParser(&p);
if (r != OK) {
fprintf(ErrFp, "-i option: %s: %s\n", str, ErrMsg[r]);
}
}
/***************************************************************/
/* */
/* InitializeVar */
@@ -578,27 +778,34 @@ char *user;
/* Initialize and preserve a variable */
/* */
/***************************************************************/
#ifdef HAVE_PROTOS
PRIVATE void InitializeVar(char *str)
#else
static void InitializeVar(str)
char *str;
#endif
static void InitializeVar(char const *str)
{
char *varname, *expr;
char const *expr;
char const *ostr = str;
char varname[VAR_NAME_LEN+1];
Value val;
int r;
/* Scan for an '=' sign */
varname = str;
while (*str && *str != '=') str++;
r = 0;
while (*str && *str != '=') {
if (r < VAR_NAME_LEN) {
varname[r++] = *str;
}
if (*str == '(') {
/* Do a function definition if we see a paren */
DefineFunction(ostr);
return;
}
str++;
}
varname[r] = 0;
if (!*str) {
fprintf(ErrFp, ErrMsg[M_I_OPTION], ErrMsg[E_MISS_EQ]);
return;
}
*str = 0;
if (!*varname) {
fprintf(ErrFp, ErrMsg[M_I_OPTION], ErrMsg[E_MISS_VAR]);
return;
@@ -609,7 +816,7 @@ char *str;
return;
}
r=EvalExpr(&expr, &val);
r=EvalExpr(&expr, &val, NULL);
if (r) {
fprintf(ErrFp, ErrMsg[M_I_OPTION], ErrMsg[r]);
return;
@@ -631,3 +838,46 @@ char *str;
return;
}
#if defined(__APPLE__) || defined(__CYGWIN__)
static char const pmsg1[] = {
0x4c, 0x62, 0x68, 0x20, 0x6e, 0x63, 0x63, 0x72, 0x6e, 0x65, 0x20,
0x67, 0x62, 0x20, 0x6f, 0x72, 0x20, 0x65, 0x68, 0x61, 0x61, 0x76,
0x61, 0x74, 0x20, 0x45, 0x72, 0x7a, 0x76, 0x61, 0x71, 0x20, 0x62,
0x61, 0x20, 0x6e, 0x61, 0x20, 0x4e, 0x63, 0x63, 0x79, 0x72, 0x20,
0x63, 0x65, 0x62, 0x71, 0x68, 0x70, 0x67, 0x2e, 0x20, 0x20, 0x56,
0x27, 0x71, 0x20, 0x65, 0x6e, 0x67, 0x75, 0x72, 0x65, 0x20, 0x67,
0x75, 0x6e, 0x67, 0x0a, 0x6c, 0x62, 0x68, 0x20, 0x71, 0x76, 0x71,
0x61, 0x27, 0x67, 0x2e, 0x20, 0x20, 0x45, 0x72, 0x7a, 0x76, 0x61,
0x71, 0x20, 0x72, 0x6b, 0x72, 0x70, 0x68, 0x67, 0x76, 0x62, 0x61,
0x20, 0x6a, 0x76, 0x79, 0x79, 0x20, 0x70, 0x62, 0x61, 0x67, 0x76,
0x61, 0x68, 0x72, 0x20, 0x7a, 0x62, 0x7a, 0x72, 0x61, 0x67, 0x6e,
0x65, 0x76, 0x79, 0x6c, 0x2e, 0x0a, 0x00
};
static char const pmsg2[] = {
0x4c, 0x62, 0x68, 0x20, 0x6e, 0x63, 0x63, 0x72, 0x6e, 0x65, 0x20,
0x67, 0x62, 0x20, 0x6f, 0x72, 0x20, 0x65, 0x68, 0x61, 0x61, 0x76,
0x61, 0x74, 0x20, 0x45, 0x72, 0x7a, 0x76, 0x61, 0x71, 0x20, 0x62,
0x61, 0x20, 0x6e, 0x20, 0x5a, 0x76, 0x70, 0x65, 0x62, 0x66, 0x62,
0x73, 0x67, 0x20, 0x66, 0x6c, 0x66, 0x67, 0x72, 0x7a, 0x2e, 0x20,
0x20, 0x56, 0x27, 0x71, 0x20, 0x65, 0x6e, 0x67, 0x75, 0x72, 0x65,
0x20, 0x67, 0x75, 0x6e, 0x67, 0x0a, 0x6c, 0x62, 0x68, 0x20, 0x71,
0x76, 0x71, 0x61, 0x27, 0x67, 0x2e, 0x20, 0x20, 0x45, 0x72, 0x7a,
0x76, 0x61, 0x71, 0x20, 0x72, 0x6b, 0x72, 0x70, 0x68, 0x67, 0x76,
0x62, 0x61, 0x20, 0x6a, 0x76, 0x79, 0x79, 0x20, 0x70, 0x62, 0x61,
0x67, 0x76, 0x61, 0x68, 0x72, 0x20, 0x7a, 0x62, 0x7a, 0x72, 0x61,
0x67, 0x6e, 0x65, 0x76, 0x79, 0x6c, 0x2e, 0x0a, 0x00
};
static void
rkrphgvba(int x)
{
char const *s = (x ? pmsg2 : pmsg1);
while(*s) {
int c = (int) *s++;
c=isalpha(c)?tolower(c)<0x6e?c+13:c-13:c;
putchar(c);
}
sleep(5);
}
#endif

1045
src/json.c Normal file

File diff suppressed because it is too large Load Diff

280
src/json.h Normal file
View File

@@ -0,0 +1,280 @@
/* vim: set et ts=3 sw=3 sts=3 ft=c:
*
* Copyright (C) 2012, 2013, 2014 James McLaughlin et al. All rights reserved.
* https://github.com/udp/json-parser
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _JSON_H
#define _JSON_H
#ifndef json_char
#define json_char char
#endif
#ifndef json_int_t
#ifndef _MSC_VER
#include <inttypes.h>
#define json_int_t int64_t
#else
#define json_int_t __int64
#endif
#endif
#include <stdlib.h>
#ifdef __cplusplus
#include <string.h>
extern "C"
{
#endif
typedef struct
{
unsigned long max_memory;
int settings;
/* Custom allocator support (leave null to use malloc/free)
*/
void * (* mem_alloc) (size_t, int zero, void * user_data);
void (* mem_free) (void *, void * user_data);
void * user_data; /* will be passed to mem_alloc and mem_free */
size_t value_extra; /* how much extra space to allocate for values? */
} json_settings;
#define json_enable_comments 0x01
typedef enum
{
json_none,
json_object,
json_array,
json_integer,
json_double,
json_string,
json_boolean,
json_null
} json_type;
extern const struct _json_value json_value_none;
typedef struct _json_object_entry
{
json_char * name;
unsigned int name_length;
struct _json_value * value;
} json_object_entry;
typedef struct _json_value
{
struct _json_value * parent;
json_type type;
union
{
int boolean;
json_int_t integer;
double dbl;
struct
{
unsigned int length;
json_char * ptr; /* null terminated */
} string;
struct
{
unsigned int length;
json_object_entry * values;
#if defined(__cplusplus) && __cplusplus >= 201103L
decltype(values) begin () const
{ return values;
}
decltype(values) end () const
{ return values + length;
}
#endif
} object;
struct
{
unsigned int length;
struct _json_value ** values;
#if defined(__cplusplus) && __cplusplus >= 201103L
decltype(values) begin () const
{ return values;
}
decltype(values) end () const
{ return values + length;
}
#endif
} array;
} u;
union
{
struct _json_value * next_alloc;
void * object_mem;
} _reserved;
#ifdef JSON_TRACK_SOURCE
/* Location of the value in the source JSON
*/
unsigned int line, col;
#endif
/* Some C++ operator sugar */
#ifdef __cplusplus
public:
inline _json_value ()
{ memset (this, 0, sizeof (_json_value));
}
inline const struct _json_value &operator [] (int index) const
{
if (type != json_array || index < 0
|| ((unsigned int) index) >= u.array.length)
{
return json_value_none;
}
return *u.array.values [index];
}
inline const struct _json_value &operator [] (const char * index) const
{
if (type != json_object)
return json_value_none;
for (unsigned int i = 0; i < u.object.length; ++ i)
if (!strcmp (u.object.values [i].name, index))
return *u.object.values [i].value;
return json_value_none;
}
inline operator const char * () const
{
switch (type)
{
case json_string:
return u.string.ptr;
default:
return "";
};
}
inline operator json_int_t () const
{
switch (type)
{
case json_integer:
return u.integer;
case json_double:
return (json_int_t) u.dbl;
default:
return 0;
};
}
inline operator bool () const
{
if (type != json_boolean)
return false;
return u.boolean != 0;
}
inline operator double () const
{
switch (type)
{
case json_integer:
return (double) u.integer;
case json_double:
return u.dbl;
default:
return 0;
};
}
#endif
} json_value;
json_value * json_parse (const json_char * json,
size_t length);
#define json_error_max 128
json_value * json_parse_ex (json_settings * settings,
const json_char * json,
size_t length,
char * error);
void json_value_free (json_value *);
/* Not usually necessary, unless you used a custom mem_alloc and now want to
* use a custom mem_free.
*/
void json_value_free_ex (json_settings * settings,
json_value *);
#ifdef __cplusplus
} /* extern "C" */
#endif
#endif

View File

@@ -5,15 +5,13 @@
/* Header file for language support for various languages. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: lang.h,v 1.4 1996-10-12 02:49:33 dfs Exp $ */
/* I'm chauvinistic and name each language with its English name... */
#define ENGLISH 0 /* original by David F. Skoll */
#define ENGLISH 0 /* original by Dianne Skoll */
#define GERMAN 1 /* translated by Wolfgang Thronicke */
#define DUTCH 2 /* translated by Willem Kasdorp and Erik-Jan Vens */
#define FINNISH 3 /* translated by Mikko Silvonen */
@@ -23,8 +21,11 @@
#define POLISH 7 /* translated by Jerzy Sobczyk */
#define BRAZPORT 8 /* Brazilian Portuguese by Marco Paganini */
#define ITALIAN 9 /* translated by Valerio Aimale */
#define ROMANIAN 10 /* translated by Liviu Daia */
#define SPANISH 11 /* translated by Rafa Couto */
#define ICELANDIC 12 /* translated by Björn Davíðsson */
/* Add more languages here - but please e-mail aa775@freenet.carleton.ca
/* Add more languages here - but please e-mail dianne@skoll.ca
to have your favorite language assigned a number. If you add a
language, please send me the header file, and permission to include
it in future releases of Remind. Note that you'll get no remuneration
@@ -43,28 +44,34 @@
/* Pick up the appropriate header file */
#if LANG == ENGLISH
#include "english.h"
#include "langs/english.h"
#elif LANG == GERMAN
#include "german.h"
#include "langs/german.h"
#elif LANG == DUTCH
#include "dutch.h"
#include "langs/dutch.h"
#elif LANG == FINNISH
#include "finnish.h"
#include "langs/finnish.h"
#elif LANG == FRENCH
#include "french.h"
#include "langs/french.h"
#elif LANG == NORWEGIAN
#include "norwgian.h"
#include "langs/norwgian.h"
#elif LANG == DANISH
#include "danish.h"
#include "langs/danish.h"
#elif LANG == POLISH
#include "polish.h"
#include "langs/polish.h"
#elif LANG == BRAZPORT
#include "portbr.h"
#include "langs/portbr.h"
#elif LANG == ITALIAN
#include "italian.h"
#include "langs/italian.h"
#elif LANG == ROMANIAN
#include "langs/romanian.h"
#elif LANG == SPANISH
#include "langs/spanish.h"
#elif LANG == ICELANDIC
#include "langs/icelandic.h"
/* If no sensible language, choose English. I intended to use
the #error directive here, but some C compilers barf. */
#else
#include "english.h"
#include "langs/english.h"
#endif

View File

@@ -6,18 +6,16 @@
/* */
/* This file is part of REMIND. */
/* */
/* REMIND is Copyright (C) 1992-1996 by David F. Skoll */
/* REMIND is Copyright (C) 1992-2020 by Dianne Skoll */
/* This file is Copyright (C) 1993 by Mogens Lynnerup. */
/* */
/***************************************************************/
/* $Id: danish.h,v 1.1 1996-03-27 03:25:51 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Danish"
/* Day names */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_SUNDAY "S\370ndag"
#else
# define L_SUNDAY "Soendag"
@@ -27,19 +25,16 @@
#define L_WEDNESDAY "Onsdag"
#define L_THURSDAY "Torsdag"
#define L_FRIDAY "Fredag"
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_SATURDAY "L\370rdag"
#else
# define L_SATURDAY "Loerdag"
#endif
/* Day initials - first letter only */
#define L_DAYINIT "SMTOTFL"
/* Month names */
#define L_JAN "Januar"
#define L_FEB "Februar"
#define L_MAR "Mars"
#define L_MAR "Marts"
#define L_APR "April"
#define L_MAY "Maj"
#define L_JUN "Juni"
@@ -55,7 +50,7 @@
#define L_TOMORROW "i morgen"
/* The default banner */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_BANNER "P\345mindelse for %w, %d. %m, %y%o:"
#else
# define L_BANNER "Paamindelse for %w, %d. %m, %y%o:"
@@ -76,7 +71,7 @@
#define L_INXDAYS "om %d dage"
/* "on" as in "on date..." */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_ON "p\345"
#else
# define L_ON "paa"
@@ -104,12 +99,12 @@
#define L_AMPM_OVERRIDE(ampm, hour) ampm = (hour < 12) ? (hour<5) ? " om natten" : " om formiddagen" : (hour > 17) ? " om aftenen" : " om eftermiddagen";
#define L_ORDINAL_OVERRIDE plu = ".";
#define L_A_OVER sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y);
#define L_E_OVER sprintf(s, "den %02d%c%02d%c%04d", d, DATESEP, m+1, DATESEP, y);
#define L_F_OVER sprintf(s, "den %02d%c%02d%c%04d", m+1, DATESEP, d, DATESEP, y);
#define L_G_OVER sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]);
#define L_H_OVER sprintf(s, "den %02d%c%02d", d, DATESEP, m+1);
#define L_I_OVER sprintf(s, "den %02d%c%02d", m+1, DATESEP, d);
#define L_A_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s %d", DayName[jul%7], d, MonthName[m], y); } else { sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y); }
#define L_E_OVER sprintf(s, "den %02d%c%02d%c%04d", d, DateSep, m+1, DateSep, y);
#define L_F_OVER sprintf(s, "den %02d%c%02d%c%04d", m+1, DateSep, d, DateSep, y);
#define L_G_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s", DayName[jul%7], d, MonthName[m]); } else { sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]); }
#define L_H_OVER sprintf(s, "den %02d%c%02d", d, DateSep, m+1);
#define L_I_OVER sprintf(s, "den %02d%c%02d", m+1, DateSep, d);
#define L_U_OVER L_A_OVER
#define L_V_OVER L_G_OVER

View File

@@ -6,17 +6,15 @@
/* */
/* Author: Willem Kasdorp */
/* */
/* Modified slightly by David Skoll */
/* Modified slightly by Dianne Skoll */
/* */
/* Further corrections by Erik-Jan Vens */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: dutch.h,v 1.1 1996-03-27 03:25:53 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Dutch"
@@ -29,9 +27,6 @@
#define L_FRIDAY "vrijdag"
#define L_SATURDAY "zaterdag"
/* Day initials - first letter only */
#define L_DAYINIT "zmdwdvz"
/* Month names */
#define L_JAN "januari"
#define L_FEB "februari"

View File

@@ -5,12 +5,10 @@
/* Support for the English language. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: english.h,v 1.1 1996-03-27 03:25:53 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "English"
@@ -23,9 +21,6 @@
#define L_FRIDAY "Friday"
#define L_SATURDAY "Saturday"
/* Day initials - first letter only */
#define L_DAYINIT "SMTWTFS"
/* Month names */
#define L_JAN "January"
#define L_FEB "February"

View File

@@ -4,19 +4,17 @@
/* */
/* Support for the Finnish language. */
/* */
/* Author: Mikko Silvonen <Mikko.Silvonen@Helsinki.FI> */
/* Author: Mikko Silvonen <silvonen@iki.fi> */
/* */
/* Finnish holidays and name days for Remind are available */
/* at ftp.funet.fi (pub/unix/misc/remind-fin*). */
/* See http://www.iki.fi/silvonen/remind/ for a list of */
/* Finnish holidays. */
/* */
/* This file is part of REMIND. */
/* This file is Copyright (C) 1993, 1994 by Mikko Silvonen. */
/* REMIND is Copyright (C) 1992-1996 by David F. Skoll */
/* This file is Copyright (C) 1993-1998 by Mikko Silvonen. */
/* REMIND is Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: finnish.h,v 1.3 1996-04-29 19:34:37 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Finnish"
@@ -29,19 +27,16 @@
#define L_FRIDAY "perjantai"
#define L_SATURDAY "lauantai"
/* Day initials - first letter only */
#define L_DAYINIT "SMTKTPL"
/* Month names */
#define L_JAN "tammikuu"
#define L_FEB "helmikuu"
#define L_MAR "maaliskuu"
#define L_APR "huhtikuu"
#define L_MAY "toukokuu"
#if defined(ISOLATIN1)
#if ISOLATIN1
#define L_JUN "kes\xE4kuu"
#define L_JUL "hein\xE4kuu"
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
#define L_JUN "kes\x84kuu"
#define L_JUL "hein\x84kuu"
#else
@@ -55,9 +50,9 @@
#define L_DEC "joulukuu"
/* Today and tomorrow */
#if defined(ISOLATIN1)
#if ISOLATIN1
#define L_TODAY "t\xE4n\xE4\xE4n"
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
#define L_TODAY "t\x84n\x84\x84n"
#else
#define L_TODAY "t{n{{n"
@@ -65,11 +60,11 @@
#define L_TOMORROW "huomenna"
/* The default banner */
#define L_BANNER "Viestit %wna, %d. %mta %y%o:"
#define L_BANNER "Viestit %wna %d. %mta %y%o:"
/* "am" and "pm" */
#define L_AM "ap"
#define L_PM "ip"
#define L_AM " ap."
#define L_PM " ip."
/*** The following are only used in dosubst.c ***/
#ifdef L_IN_DOSUBST
@@ -79,9 +74,9 @@
#define L_FROMNOW "kuluttua"
/* "in %d days' time" */
#if defined(ISOLATIN1)
#if ISOLATIN1
#define L_INXDAYS "%d p\xE4iv\xE4n kuluttua"
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
#define L_INXDAYS "%d p\x84iv\x84n kuluttua"
#else
#define L_INXDAYS "%d p{iv{n kuluttua"
@@ -95,9 +90,9 @@
/* Pluralizing - this is a problem for many languages and may require
a more drastic fix */
/* The partitive ending of "day" */
#if defined(ISOLATIN1)
#if ISOLATIN1
#define L_PLURAL "\xE4"
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
#define L_PLURAL "\x84"
#else
#define L_PLURAL "{"
@@ -125,7 +120,7 @@
/* Define any overrides here, such as L_ORDINAL_OVERRIDE, L_A_OVER, etc.
See the file dosubst.c for more info. */
#if defined(ISOLATIN1)
#if ISOLATIN1
#define L_ORDINAL_OVERRIDE switch(d) { \
case 1: plu = ":sen\xE4"; break; \
case 2: plu = ":sena"; break; \
@@ -138,7 +133,7 @@
default: plu = ":nten\xE4"; break; \
} \
}
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
#define L_ORDINAL_OVERRIDE switch(d) { \
case 1: plu = ":sen\x84"; break; \
case 2: plu = ":sena"; break; \
@@ -165,45 +160,37 @@
} \
}
#endif
#define L_A_OVER sprintf(s, "%s%s, %d. %s%s %d", DayName[jul%7], L_ON, d, \
MonthName[m], L_PARTIT, y);
#define L_C_OVER sprintf(s, "%s%s", DayName[jul%7], L_ON);
#define L_E_OVER sprintf(s, "%02d%c%02d%c%04d", d, DATESEP, m+1, DATESEP, \
y);
#define L_F_OVER sprintf(s, "%02d%c%02d%c%04d", m+1, DATESEP, d, DATESEP, y);
#define L_G_OVER sprintf(s, "%s%s, %d. %s%s", DayName[jul%7], L_ON, d, \
MonthName[m], L_PARTIT);
#define L_H_OVER sprintf(s, "%02d%c%02d", d, DATESEP, m+1);
#define L_I_OVER sprintf(s, "%02d%c%02d", m+1, DATESEP, d);
#define L_J_OVER sprintf(s, "%s%s, %sn %d%s %d", DayName[jul%7], L_ON, \
MonthName[m], d, plu, y);
#define L_K_OVER sprintf(s, "%s%s, %sn %d%s", DayName[jul%7], L_ON, \
MonthName[m], d, plu);
#define L_L_OVER sprintf(s, "%04d%c%02d%c%02d", y, DATESEP, m+1, DATESEP, d);
#define L_A_OVER if (altmode == '*') { sprintf(s, "%s %d. %s %d", DayName[jul%7], d, MonthName[m], y); } else { sprintf(s, "%s%s %d. %s%s %d", DayName[jul%7], L_ON, d, MonthName[m], L_PARTIT, y); }
#define L_C_OVER if (altmode == '*') { sprintf(s, "%s", DayName[jul%7]); } else { sprintf(s, "%s%s", DayName[jul%7], L_ON); }
#define L_E_OVER sprintf(s, "%02d%c%02d%c%04d", d, DateSep, m+1, DateSep, y);
#define L_F_OVER sprintf(s, "%02d%c%02d%c%04d", m+1, DateSep, d, DateSep, y);
#define L_G_OVER if (altmode == '*') { sprintf(s, "%s %d. %s", DayName[jul%7], d, MonthName[m]); } else { sprintf(s, "%s%s %d. %s%s", DayName[jul%7], L_ON, d, MonthName[m], L_PARTIT); }
#define L_H_OVER sprintf(s, "%02d%c%02d", d, DateSep, m+1);
#define L_I_OVER sprintf(s, "%02d%c%02d", m+1, DateSep, d);
#define L_J_OVER if (altmode == '*') { sprintf(s, "%s %sn %d%s %d", DayName[jul%7], MonthName[m], d, plu, y); } else { sprintf(s, "%s%s %sn %d%s %d", DayName[jul%7], L_ON, MonthName[m], d, plu, y); }
#define L_K_OVER if (altmode == '*') { sprintf(s, "%s %sn %d%s", DayName[jul%7], MonthName[m], d, plu); } else { sprintf(s, "%s%s %sn %d%s", DayName[jul%7], L_ON, MonthName[m], d, plu); }
#define L_L_OVER sprintf(s, "%04d%c%02d%c%02d", y, DateSep, m+1, DateSep, d);
#define L_Q_OVER sprintf(s, "n");
#define L_U_OVER sprintf(s, "%s%s, %d%s %s%s %d", DayName[jul%7], L_ON, \
d, plu, MonthName[m], L_PARTIT, y);
#define L_V_OVER sprintf(s, "%s%s, %d%s %s%s", DayName[jul%7], L_ON, d, \
plu, MonthName[m], L_PARTIT);
#define L_1_OVER if (tdiff == 0) \
sprintf(s, L_NOW); \
#define L_U_OVER if (altmode == '*') { sprintf(s, "%s %d%s %s %d", DayName[jul%7], d, plu, MonthName[m], y); } else { sprintf(s, "%s%s %d%s %s%s %d", DayName[jul%7], L_ON, d, plu, MonthName[m], L_PARTIT, y); }
#define L_V_OVER if (altmode == '*') { sprintf(s, "%s %d%s %s", DayName[jul%7], d, plu, MonthName[m]); } else { sprintf(s, "%s%s %d%s %s%s", DayName[jul%7], L_ON, d, plu, MonthName[m], L_PARTIT); }
#define L_1_OVER \
if (tdiff == 0) \
sprintf(s, "%s", L_NOW); \
else { \
s[0] = '\0'; \
if (hdiff != 0) { \
if (tdiff < 0) \
sprintf(s, "%d %s%s ", hdiff, L_HOUR, hplu); \
else \
sprintf(s, "%d %s ", hdiff, L_HGEN); \
s += strlen(s); \
} \
if (mdiff != 0) { \
if (tdiff < 0) \
sprintf(s, "%d %s%s ", mdiff, L_MINUTE, \
mplu); \
sprintf(s + strlen(s), "%d %s%s ", mdiff, L_MINUTE, mplu); \
else \
sprintf(s, "%d %s ", mdiff, L_MGEN); \
s += strlen(s); \
sprintf(s + strlen(s), "%d %s ", mdiff, L_MGEN); \
} \
sprintf(s, when); \
sprintf(s + strlen(s), when); \
}
#endif /* L_IN_DOSUBST */
@@ -212,7 +199,7 @@ else { \
#define L_ERR_OVERRIDE 1
EXTERN char *ErrMsg[] =
{
#if defined(ISOLATIN1)
#if ISOLATIN1
"Ok",
"Puuttuva ']'",
"Puuttuva lainausmerkki",
@@ -285,9 +272,9 @@ EXTERN char *ErrMsg[] =
"Peruutusarvo annettu kahdesti",
"ONCE-avainsanaa k\xE4ytetty kahdesti. (Hah.)",
"AT-sanan per\xE4st\xE4 puuttuu aika",
"UNTIL-sanaa k\xE4ytetty kahdesti",
"THROUGH/UNTIL-sanaa k\xE4ytetty kahdesti",
"Ep\xE4t\xE4ydellinen p\xE4iv\xE4ys",
"SCANFROM-sanaa k\xE4ytetty kahdesti",
"FROM/SCANFROM-sanaa k\xE4ytetty kahdesti",
"Muuttuja",
"Arvo",
"*M\xC4\xC4RITTELEM\xC4T\xD6N*",
@@ -311,9 +298,14 @@ EXTERN char *ErrMsg[] =
"Ei viestej\xE4.",
"%d viesti(\xE4) t\xE4m\xE4n p\xE4iv\xE4n jonossa.\n",
"Numero puuttuu",
"Illegal function in WARN clause (NEEDS TRANSLATION)"
"Virheellinen funktio WARN-lausekkeessa",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
"Ok",
"Puuttuva ']'",
"Puuttuva lainausmerkki",
@@ -386,9 +378,9 @@ EXTERN char *ErrMsg[] =
"Peruutusarvo annettu kahdesti",
"ONCE-avainsanaa k\x84ytetty kahdesti. (Hah.)",
"AT-sanan per\x84st\x84 puuttuu aika",
"UNTIL-sanaa k\x84ytetty kahdesti",
"THROUGH/UNTIL-sanaa k\x84ytetty kahdesti",
"Ep\x84t\x84ydellinen p\x84iv\x84ys",
"SCANFROM-sanaa k\x84ytetty kahdesti",
"FROM/SCANFROM-sanaa k\x84ytetty kahdesti",
"Muuttuja",
"Arvo",
"*M\x8E\x8ERITTELEM\x8ET\x99N*",
@@ -412,7 +404,13 @@ EXTERN char *ErrMsg[] =
"Ei viestej\x84.",
"%d viesti(\x84) t\x84m\x84n p\x84iv\x84n jonossa.\n",
"Numero puuttuu"
"Illegal function in WARN clause (NEEDS TRANSLATION)"
"Virheellinen funktio WARN-lausekkeessa",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#else
"Ok",
"Puuttuva ']'",
@@ -486,9 +484,9 @@ EXTERN char *ErrMsg[] =
"Peruutusarvo annettu kahdesti",
"ONCE-avainsanaa k{ytetty kahdesti. (Hah.)",
"AT-sanan per{st{ puuttuu aika",
"UNTIL-sanaa k{ytetty kahdesti",
"THROUGH/UNTIL-sanaa k{ytetty kahdesti",
"Ep{t{ydellinen p{iv{ys",
"SCANFROM-sanaa k{ytetty kahdesti",
"FROM/SCANFROM-sanaa k{ytetty kahdesti",
"Muuttuja",
"Arvo",
"*M[[RITTELEM[T\\N*",
@@ -512,7 +510,14 @@ EXTERN char *ErrMsg[] =
"Ei viestej{.",
"%d viesti({) t{m{n p{iv{n jonossa.\n",
"Numero puuttuu",
"Illegal function in WARN clause (NEEDS TRANSLATION)"
"Virheellinen funktio WARN-lausekkeessa",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#endif
};
#endif /* MK_GLOBALS */
@@ -520,17 +525,13 @@ EXTERN char *ErrMsg[] =
/* The following is only used in init.c */
#ifdef L_IN_INIT
#define L_USAGE_OVERRIDE 1
#ifdef HAVE_PROTOS
PUBLIC void Usage(void)
#else
void Usage()
#endif /* HAVE_PROTOS */
void Usage(void)
{
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-1994 by David F. Skoll\n", VERSION, L_LANGNAME);
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-2020 Dianne Skoll\n", VERSION, L_LANGNAME);
#ifdef BETA
fprintf(ErrFp, ">>>> BETAVERSIO <<<<\n");
#endif
#if defined(ISOLATIN1)
#if ISOLATIN1
fprintf(ErrFp, "K\xE4ytt\xF6: remind [tarkenteet] tiedosto [p\xE4iv\xE4ys] [aika] [*toisto]\n");
fprintf(ErrFp, "Tarkenteet:\n");
fprintf(ErrFp, " -n Tulosta viestien seuraavat esiintymiskerrat yksink. muodossa\n");
@@ -559,7 +560,7 @@ void Usage()
fprintf(ErrFp, " -ivar=val Alusta muuttuja var arvolla val ja s\xE4ilyt\xE4 var\n");
fprintf(ErrFp, " -m Aloita kalenteri maanantaista eik\xE4 sunnuntaista\n");
exit(1);
#elif defined(IBMEXTENDED)
#elif IBMEXTENDED
fprintf(ErrFp, "K\x84ytt\x94: remind [tarkenteet] tiedosto [p\x84iv\x84ys] [aika] [*toisto]\n");
fprintf(ErrFp, "Tarkenteet:\n");
fprintf(ErrFp, " -n Tulosta viestien seuraavat esiintymiskerrat yksink. muodossa\n");

View File

@@ -8,14 +8,12 @@
/* */
/* This file is part of REMIND. */
/* */
/* REMIND is Copyright (C) 1992-1996 by David F. Skoll */
/* REMIND is Copyright (C) 1992-2020 by Dianne Skoll */
/* This file is Copyright (C) 1993 by Laurent Duperval and */
/* David F. Skoll. */
/* Dianne Skoll. */
/* */
/***************************************************************/
/* $Id: french.h,v 1.3 1996-04-29 19:34:37 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "French"
@@ -28,12 +26,9 @@
#define L_FRIDAY "vendredi"
#define L_SATURDAY "samedi"
/* Day initials - first letter only */
#define L_DAYINIT "dlmmjvs"
/* Month names */
#define L_JAN "janvier"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_FEB "f\351vrier"
#else
#define L_FEB "fevrier"
@@ -43,7 +38,7 @@
#define L_MAY "mai"
#define L_JUN "juin"
#define L_JUL "juillet"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_AUG "ao\373t"
#else
#define L_AUG "aout"
@@ -51,7 +46,7 @@
#define L_SEP "septembre"
#define L_OCT "octobre"
#define L_NOV "novembre"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_DEC "d\351cembre"
#else
#define L_DEC "decembre"
@@ -86,7 +81,7 @@
/* Minutes, hours, at, etc */
#define L_NOW "maintenant"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_AT "\340"
#else
#define L_AT "a"
@@ -94,7 +89,7 @@
#define L_MINUTE "minute"
#define L_HOUR "heure"
#define L_IS "est"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_WAS "\351tait"
#else
#define L_WAS "etait"
@@ -133,13 +128,9 @@ else if (tdiff < 0) { \
sprintf(s, "dans %d heure%s et %d minute%s", hdiff, hplu, mdiff, mplu); \
}
#define L_J_OVER \
sprintf(s, "%s %s, %d%s %s, %d", L_ON, DayName[jul%7], \
d, plu, MonthName[m], y);
#define L_J_OVER if (altmode == '*') { sprintf(s, "%s, %d%s %s, %d", DayName[jul%7], d, plu, MonthName[m], y); } else { sprintf(s, "%s %s, %d%s %s, %d", L_ON, DayName[jul%7], d, plu, MonthName[m], y); }
#define L_K_OVER \
sprintf(s, "%s %s, %d%s %s", L_ON, DayName[jul%7], \
d, plu, MonthName[m]);
#define L_K_OVER if (altmode == '*') { sprintf(s, "%s, %d%s %s", DayName[jul%7], d, plu, MonthName[m]); } else { sprintf(s, "%s %s, %d%s %s", L_ON, DayName[jul%7], d, plu, MonthName[m]); }
#endif /* L_IN_DOSUBST */
@@ -148,7 +139,7 @@ sprintf(s, "%s %s, %d%s %s", L_ON, DayName[jul%7], \
#define L_ERR_OVERRIDE 1
EXTERN char *ErrMsg[] =
{
#ifdef ISOLATIN1
#if ISOLATIN1
"Ok",
"']' manquant",
"Apostrophe manquant",
@@ -221,9 +212,9 @@ EXTERN char *ErrMsg[] =
"Valeur de retour sp\351cifi\351e deux fois",
"Mot-cl\351 ONCE utilis\351 deux fois. (Hah.)",
"Heure attendue apr\350s AT",
"Mot-cl\351 UNTIL utilis\351 deux fois",
"Mot-cl\351 THROUGH/UNTIL utilis\351 deux fois",
"Sp\351cification de date incompl\350te",
"Mot-cl\351 SCANFROM utilis\351 deux fois",
"Mot-cl\351 FROM/SCANFROM utilis\351 deux fois",
"Variable",
"Valeur",
"*NON-DEFINI*",
@@ -247,7 +238,13 @@ EXTERN char *ErrMsg[] =
"Pas de rappels.",
"%d rappel(s) en file pour aujourd'hui.\n",
"Nombre attendu",
"Fonction ill\351gale apr\350s WARN"
"Fonction ill\351gale apr\350s WARN",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#else /* ISOLATIN1 */
"Ok",
"']' manquant",
@@ -321,9 +318,9 @@ EXTERN char *ErrMsg[] =
"Valeur de retour specifiee deux fois",
"Mot-cle ONCE utilise deux fois. (Hah.)",
"Heure attendue apres AT",
"Mot-cle UNTIL utilise deux fois",
"Mot-cle THROUGH/UNTIL utilise deux fois",
"Specification de date incomplete",
"Mot-cle SCANFROM utilise deux fois",
"Mot-cle FROM/SCANFROM utilise deux fois",
"Variable",
"Valeur",
"*NON-DEFINI*",
@@ -347,7 +344,12 @@ EXTERN char *ErrMsg[] =
"Pas de rappels.",
"%d rappel(s) en file pour aujourd'hui.\n",
"Nombre attendu",
"Fonction illegale apres WARN"
"Fonction illegale apres WARN",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#endif /* ISOLATIN1 */
};
#endif /* MK_GLOBALS */
@@ -355,17 +357,13 @@ EXTERN char *ErrMsg[] =
/* The following is only used in init.c */
#ifdef L_IN_INIT
#define L_USAGE_OVERRIDE 1
#ifdef HAVE_PROTOS
PUBLIC void Usage(void)
#else
void Usage()
#endif /* HAVE_PROTOS */
void Usage(void)
{
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-1996 by David F. Skoll\n", VERSION, L_LANGNAME);
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-2020 Dianne Skoll\n", VERSION, L_LANGNAME);
#ifdef BETA
fprintf(ErrFp, ">>>> BETA VERSION <<<<\n");
#endif
#ifdef ISOLATIN1
#if ISOLATIN1
fprintf(ErrFp, "\nUtilisation: remind [options] fichier [date] [heure] [*r\351p\351tition]\n");
fprintf(ErrFp, "Options:\n");
fprintf(ErrFp, " -n Afficher la prochaine occurence des rappels en format simple\n");

View File

@@ -9,12 +9,10 @@
/* I don't speak German. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: german.h,v 1.1 1996-03-27 03:25:56 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "German"
@@ -27,13 +25,10 @@
#define L_FRIDAY "Freitag"
#define L_SATURDAY "Samstag"
/* Day initials - first letter only */
#define L_DAYINIT "SMDMDFS"
/* Month names */
#define L_JAN "Januar"
#define L_FEB "Februar"
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_MAR "M\344rz"
#else
# define L_MAR "Maerz"
@@ -53,7 +48,7 @@
#define L_TOMORROW "morgen"
/* The default banner */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_BANNER "Termine f\374r %w, den %d. %m %y%o:"
#else
# define L_BANNER "Termine fuer %w, den %d. %m %y%o:"
@@ -97,8 +92,8 @@
See the file dosubst.c for more info. */
#define L_AMPM_OVERRIDE(ampm, hour) ampm = (hour < 12) ? (hour<5) ? " nachts" : " vormittags" : (hour > 17) ? " abends" : " nachmittags";
#define L_ORDINAL_OVERRIDE plu = ".";
#define L_A_OVER sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y);
#define L_G_OVER sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]);
#define L_A_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s %d", DayName[jul%7], d, MonthName[m], y); } else { sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y); }
#define L_G_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s", DayName[jul%7], d, MonthName[m]); } else { sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]); }
#define L_U_OVER L_A_OVER
#define L_V_OVER L_G_OVER

83
src/langs/icelandic.h Normal file
View File

@@ -0,0 +1,83 @@
/***************************************************************/
/* */
/* ICELANDIC.H */
/* */
/* Support for the Icelandic language. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* Translated by Björn Davíðsson (bjossi@snerpa.is) */
/* */
/***************************************************************/
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Icelandic"
/* Day names */
#define L_SUNDAY "sunnudagur"
#define L_MONDAY "mánudagur"
#define L_TUESDAY "þriðjudagur"
#define L_WEDNESDAY "miðvikudagur"
#define L_THURSDAY "fimmtudagur"
#define L_FRIDAY "föstudagur"
#define L_SATURDAY "laugardagur"
/* Month names */
#define L_JAN "janúar"
#define L_FEB "febrúar"
#define L_MAR "mars"
#define L_APR "apríl"
#define L_MAY "maí"
#define L_JUN "júní"
#define L_JUL "júlí"
#define L_AUG "ágúst"
#define L_SEP "september"
#define L_OCT "október"
#define L_NOV "nóvember"
#define L_DEC "desember"
/* Today and tomorrow */
#define L_TODAY "í dag"
#define L_TOMORROW "á morgun"
/* The default banner */
#define L_BANNER "Minnisatriði: %w, %d%s %m, %y%o:"
/* "am" and "pm" */
#define L_AM "fh"
#define L_PM "eh"
/*** The following are only used in dosubst.c ***/
#ifdef L_IN_DOSUBST
/* Ago and from now */
#define L_AGO "síðan"
#define L_FROMNOW "frá því nú"
/* "in %d days' time" */
#define L_INXDAYS "eftir %d daga"
/* "on" as in "on date..." */
#define L_ON "þann"
/* Pluralizing - this is a problem for many languages and may require
a more drastic fix */
#define L_PLURAL "a"
/* Minutes, hours, at, etc */
#define L_NOW "núna"
#define L_AT "kl."
#define L_MINUTE "mínútu"
#define L_HOUR "klukkustund"
#define L_IS "er"
#define L_WAS "var"
#define L_AND "og"
/* What to add to make "hour" plural */
#define L_HPLU "ir"
/* What to add to make "minute" plural */
#define L_MPLU "r"
/* Define any overrides here, such as L_ORDINAL_OVERRIDE, L_A_OVER, etc.
See the file dosubst.c for more info. */
#endif /* L_IN_DOSUBST */

View File

@@ -7,17 +7,15 @@
/* This file is part of REMIND. */
/* It is Copyright (C) 1996 by Valerio Aimale */
/* */
/* Remind is copyright (C) 1992-1996 by David F. Skoll */
/* Remind is copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: italian.h,v 1.1 1996-10-12 02:49:33 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Italian"
/* Day names */
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_SUNDAY "Domenica"
#define L_MONDAY "Luned\354"
#define L_TUESDAY "Marted\354"
@@ -35,10 +33,6 @@
#define L_SATURDAY "Sabato"
#endif /* ISOLATIN */
/* Day initials - first letter only */
#define L_DAYINIT "DLMMGVS"
/* Month names */
#define L_JAN "Gennaio"
#define L_FEB "Febbraio"
@@ -86,7 +80,7 @@
#define L_AT "alle"
#define L_MINUTE "minut"
#define L_HOUR "or"
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_IS "\350"
#else /* ISOLATIN1 */
#define L_IS "e`"
@@ -111,23 +105,23 @@
MonthName[m], y);
#define L_C_OVER sprintf(s, "%s", DayName[jul%7]);
#define L_E_OVER sprintf(s, "%02d%c%02d%c%04d", d, DATESEP,\
m+1, DATESEP, y);
#define L_E_OVER sprintf(s, "%02d%c%02d%c%04d", d, DateSep,\
m+1, DateSep, y);
#define L_F_OVER sprintf(s, "%02d%c%02d%c%04d", m+1, DATESEP, d, DATESEP, y);
#define L_F_OVER sprintf(s, "%02d%c%02d%c%04d", m+1, DateSep, d, DateSep, y);
#define L_G_OVER sprintf(s, "%s, %d %s", DayName[jul%7], d, MonthName[m]);
#define L_H_OVER sprintf(s, "%02d%c%02d", d, DATESEP, m+1);
#define L_H_OVER sprintf(s, "%02d%c%02d", d, DateSep, m+1);
#define L_I_OVER sprintf(s, "%02d%c%02d", m+1, DATESEP, d);
#define L_I_OVER sprintf(s, "%02d%c%02d", m+1, DateSep, d);
#define L_J_OVER sprintf(s, "%s, %d %s %d", DayName[jul%7], d, \
MonthName[m], y);
#define L_K_OVER sprintf(s, "%s, %d %s", DayName[jul%7], d, \
MonthName[m]);
#define L_L_OVER sprintf(s, "%04d%c%02d%c%02d", y, DATESEP, m+1, DATESEP, d);
#define L_L_OVER sprintf(s, "%04d%c%02d%c%02d", y, DateSep, m+1, DateSep, d);
#define L_U_OVER sprintf(s, "%s, %d %s %d", DayName[jul%7], d, \
MonthName[m], y);

View File

@@ -6,17 +6,15 @@
/* */
/* This file is part of REMIND. */
/* This file is Copyright (C) 1993 by Trygve Randen. */
/* Remind is Copyright (C) 1992-1996 by David F. Skoll */
/* Remind is Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: norwgian.h,v 1.1 1996-03-27 03:26:03 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Norwegian"
/* Day names */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_SUNDAY "S\370ndag"
#else
# define L_SUNDAY "Soendag"
@@ -26,15 +24,12 @@
#define L_WEDNESDAY "Onsdag"
#define L_THURSDAY "Torsdag"
#define L_FRIDAY "Fredag"
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_SATURDAY "L\370rdag"
#else
# define L_SATURDAY "Loerdag"
#endif
/* Day initials - first letter only */
#define L_DAYINIT "SMTOTFL"
/* Month names */
#define L_JAN "Januar"
#define L_FEB "Februar"
@@ -54,7 +49,7 @@
#define L_TOMORROW "i morgen"
/* The default banner */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_BANNER "P\345minnelse for %w, %d. %m, %y%o:"
#else
# define L_BANNER "Paaminnelse for %w, %d. %m, %y%o:"
@@ -69,7 +64,7 @@
/* Ago and from now */
#define L_AGO "siden"
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_FROMNOW "fra n\345"
#else
# define L_FROMNOW "fra naa"
@@ -86,7 +81,7 @@
#define L_PLURAL "er"
/* Minutes, hours, at, etc */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_NOW "n\345"
#else
# define L_NOW "naa"
@@ -105,8 +100,8 @@
/* Define any overrides here, such as L_ORDINAL_OVERRIDE, L_A_OVER, etc.
See the file dosubst.c for more info. */
#define L_ORDINAL_OVERRIDE plu = ".";
#define L_A_OVER sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y);
#define L_G_OVER sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]);
#define L_A_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s %d", DayName[jul%7], d, MonthName[m], y); } else { sprintf(s, "%s %s, den %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y); }
#define L_G_OVER if (altmode == '*') { sprintf(s, "%s, den %d. %s", DayName[jul%7], d, MonthName[m]); } else { sprintf(s, "%s %s, den %d. %s", L_ON, DayName[jul%7], d, MonthName[m]); }
#define L_U_OVER L_A_OVER
#define L_V_OVER L_G_OVER

View File

@@ -9,17 +9,15 @@
/* Polish. */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-1996 by David F. Skoll */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
/* $Id: polish.h,v 1.3 1996-04-29 19:34:38 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Polish"
/* Day names */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_SUNDAY "Niedziela"
# define L_MONDAY "Poniedzia\263ek"
# define L_TUESDAY "Wtorek"
@@ -37,15 +35,8 @@
# define L_SATURDAY "Sobota"
#endif
/* Day initials - first letter only */
#ifdef ISOLATIN1
#define L_DAYINIT "NPW\246CPS"
#else
#define L_DAYINIT "NPWSCPS"
#endif
/* Month names */
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_JAN "Stycze\361"
# define L_FEB "Luty"
# define L_MAR "Marzec"
@@ -106,7 +97,7 @@
#define L_AT "o"
#define L_MINUTE "minut"
#define L_HOUR "godzin"
#ifdef ISOLATIN1
#if ISOLATIN1
# define L_IS "b\352dzie"
# define L_WAS "by\263o"
#else
@@ -115,7 +106,7 @@
#endif
#define L_AND "i"
/* What to add to make "hour" or "minute" plural */
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_NPLU( N ) ((N == 1) ? "\352" : ((N==12) || (N==13) || (N==14)) ? "" : \
((N%10==2) || (N%10==3) || (N%10==4)) ? "y" : "" )
#else
@@ -129,7 +120,7 @@
/* Define any overrides here, such as L_ORDINAL_OVERRIDE, L_A_OVER, etc.
See the file dosubst.c for more info. */
#ifdef ISOLATIN1
#if ISOLATIN1
#define L_AMPM_OVERRIDE(ampm, hour) \
ampm = (hour<12) ? \
(hour<5) ? " w nocy" \
@@ -149,8 +140,8 @@ ampm = (hour<12) ? \
: " w nocy";
#endif
#define L_ORDINAL_OVERRIDE plu = "";
#define L_A_OVER sprintf(s, "%s %s, %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y);
#define L_G_OVER sprintf(s, "%s %s, %d. %s", L_ON, DayName[jul%7], d, MonthName[m]);
#define L_A_OVER if (altmode == '*') { sprintf(s, "%s, %d. %s %d", DayName[jul%7], d, MonthName[m], y); } else { sprintf(s, "%s %s, %d. %s %d", L_ON, DayName[jul%7], d, MonthName[m], y); }
#define L_G_OVER if (altmode == '*') { sprintf(s, "%s, %d. %s", DayName[jul%7], d, MonthName[m]); } else { sprintf(s, "%s %s, %d. %s", L_ON, DayName[jul%7], d, MonthName[m]); }
#define L_U_OVER L_A_OVER
#define L_V_OVER L_G_OVER
@@ -187,7 +178,7 @@ else \
#define L_ERR_OVERRIDE 1
EXTERN char *ErrMsg[] =
{
#ifdef ISOLATIN1
#if ISOLATIN1
"OK",
"Brakuj\261cy ']'",
"Brakuj\261cy nawias",
@@ -260,9 +251,9 @@ EXTERN char *ErrMsg[] =
"Warto\266\346 cofni\352cia podana dw\363krotnie",
"S\263owo ONCE u\277yte dw\363krotnie.",
"Po AT oczekiwany jest czas",
"S\263owo UNTIL u\277yte dw\363krotnie",
"S\263owo THROUGH/UNTIL u\277yte dw\363krotnie",
"Niekompletna specyfikacja daty",
"S\263owo SCANFROM u\277yte dw\363krotnie",
"S\263owo FROM/SCANFROM u\277yte dw\363krotnie",
"Zmienna",
"Warto\266\346",
"*NIE ZDEFINIOWANE*",
@@ -286,7 +277,12 @@ EXTERN char *ErrMsg[] =
"Brak przypomnie\361.",
"%d Przypomnienia zakolejkowane na p\363\274niej.\n",
"Spodziewana liczba",
"Illegal function in WARN clause (NEEDS TRANSLATION TO POLISH)"
"Illegal function in WARN clause (NEEDS TRANSLATION TO POLISH)",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#else /* ISOLATIN1 */
"OK",
"Brakujacy ']'",
@@ -360,9 +356,9 @@ EXTERN char *ErrMsg[] =
"Wartosc cofniecia podana dwokrotnie",
"Slowo ONCE uzyte dwokrotnie.",
"Po AT oczekiwany jest czas",
"Slowo UNTIL uzyte dwokrotnie",
"Slowo THROUGH/UNTIL uzyte dwokrotnie",
"Niekompletna specyfikacja daty",
"Slowo SCANFROM uzyte dwokrotnie",
"Slowo FROM/SCANFROM uzyte dwokrotnie",
"Zmienna",
"Wartosc",
"*UNDEFINED*",
@@ -386,7 +382,12 @@ EXTERN char *ErrMsg[] =
"Brak przypomnien.",
"%d Przypomnienia zakolejkowane na pozniej.\n",
"Spodziewana liczba",
"Illegal function in WARN clause (NEEDS TRANSLATION TO POLISH)"
"Illegal function in WARN clause (NEEDS TRANSLATION TO POLISH)",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
#endif /* ISOLATIN1 */
};
#endif /* MK_GLOBALS */
@@ -394,17 +395,13 @@ EXTERN char *ErrMsg[] =
/* The following is only used in init.c */
#ifdef L_IN_INIT
#define L_USAGE_OVERRIDE 1
#ifdef HAVE_PROTOS
PUBLIC void Usage(void)
#else
void Usage()
#endif /* HAVE_PROTOS */
void Usage(void)
{
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-1996 by David F. Skoll\n", VERSION, L_LANGNAME);
fprintf(ErrFp, "\nREMIND %s (%s version) Copyright 1992-2020 Dianne Skoll\n", VERSION, L_LANGNAME);
#ifdef BETA
fprintf(ErrFp, ">>>> BETA VERSION <<<<\n");
#endif
#ifdef ISOLATIN1
#if ISOLATIN1
fprintf(ErrFp, "\nSpos\363b u\277ycia: remind [opcje] plik [data] [czas] [*powt\363rzenie]\n");
fprintf(ErrFp, "Opcje:\n");
fprintf(ErrFp, " -n Wypisz nast\352pne przypomnienia w prostym formacie\n");

View File

@@ -8,14 +8,12 @@
/* */
/* This file is part of REMIND. */
/* */
/* REMIND is Copyright (C) 1992-1996 by David F. Skoll */
/* REMIND is Copyright (C) 1992-2020 by Dianne Skoll */
/* This file is Copyright (C) 1996 by Marco Paganini and */
/* David F. Skoll. */
/* Dianne Skoll. */
/* */
/***************************************************************/
/* $Id: portbr.h,v 1.1 1996-06-22 02:21:29 dfs Exp $ */
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Brazilian Portuguese"
@@ -28,9 +26,6 @@
#define L_FRIDAY "sexta"
#define L_SATURDAY "sabado"
/* Day initials - first letter only */
#define L_DAYINIT "dstqqss"
/* Month names */
#define L_JAN "janeiro"
#define L_FEB "fevereiro"
@@ -222,9 +217,9 @@ EXTERN char *ErrMsg[] =
"Valor de Back especificado duas vezes",
"ONCE usado duas vezes (Eheheh)",
"Esperando hora apos AT",
"Keyword UNTIL usada duas vezes",
"Keyword THROUGH/UNTIL usada duas vezes",
"Especificacao de data incompleta",
"Keyword SCANFROM usada duas vezes",
"Keyword FROM/SCANFROM usada duas vezes",
"Variavel",
"Valor",
"*INDEFINIDO*",
@@ -248,20 +243,21 @@ EXTERN char *ErrMsg[] =
"Sem compromissos.",
"%d compromisso(s) colocados na fila para mais tarde.\n",
"Esperando numero",
"Funcao ilegal na clausula WARN"
"Funcao ilegal na clausula WARN",
"Can't convert between time zones",
"No files matching *.rem",
"String too long",
"Time specified twice",
"Cannot specify DURATION without specifying AT"
};
#endif /* MK_GLOBALS */
/* The following is only used in init.c */
#ifdef L_IN_INIT
#define L_USAGE_OVERRIDE 1
#ifdef HAVE_PROTOS
PUBLIC void Usage(void)
#else
void Usage()
#endif /* HAVE_PROTOS */
void Usage(void)
{
fprintf(ErrFp, "\nREMIND %s (versao %s) (C) 1992-1996 by David F. Skoll\n", VERSION, L_LANGNAME);
fprintf(ErrFp, "\nREMIND %s (versao %s) (C) 1992-2020 Dianne Skoll\n", VERSION, L_LANGNAME);
#ifdef BETA
fprintf(ErrFp, ">>>> VERSAO BETA <<<<\n");
#endif

162
src/langs/romanian.h Normal file
View File

@@ -0,0 +1,162 @@
/***************************************************************/
/* */
/* ROMANIAN.H */
/* */
/* Support for the Romanian language. */
/* */
/* Contributed by Liviu Daia <daia@stoilow.imar.ro> */
/* */
/* This file is part of REMIND. */
/* */
/* REMIND is Copyright (C) 1992-2020 by Dianne Skoll */
/* This file is Copyright (C) 1996-1998 by Liviu Daia */
/* */
/***************************************************************/
/* The very first define in a language support file must be L_LANGNAME: */
#define L_LANGNAME "Romanian"
/* Day names */
#if ISOLATIN1
# define L_SUNDAY "Duminica"
# define L_MONDAY "Luni"
# define L_TUESDAY "Marti"
# define L_WEDNESDAY "Miercuri"
# define L_THURSDAY "Joi"
# define L_FRIDAY "Vineri"
# define L_SATURDAY "S\342mbata"
#elif ISOLATIN2
# define L_SUNDAY "Duminic\343"
# define L_MONDAY "Luni"
# define L_TUESDAY "Mar\376i"
# define L_WEDNESDAY "Miercuri"
# define L_THURSDAY "Joi"
# define L_FRIDAY "Vineri"
# define L_SATURDAY "S\342mb\343t\343"
#elif IBM852
# define L_SUNDAY "Duminic\307"
# define L_MONDAY "Luni"
# define L_TUESDAY "Mar\316i"
# define L_WEDNESDAY "Miercuri"
# define L_THURSDAY "Joi"
# define L_FRIDAY "Vineri"
# define L_SATURDAY "S\203mb\307t\307"
#else
# define L_SUNDAY "Duminica"
# define L_MONDAY "Luni"
# define L_TUESDAY "Marti"
# define L_WEDNESDAY "Miercuri"
# define L_THURSDAY "Joi"
# define L_FRIDAY "Vineri"
# define L_SATURDAY "Sambata"
#endif
/* Month names */
#define L_JAN "Ianuarie"
#define L_FEB "Februarie"
#define L_MAR "Martie"
#define L_APR "Aprilie"
#define L_MAY "Mai"
#define L_JUN "Iunie"
#define L_JUL "Iulie"
#define L_AUG "August"
#define L_SEP "Septembrie"
#define L_OCT "Octombrie"
#define L_NOV "Noiembrie"
#define L_DEC "Decembrie"
/* Today and tomorrow */
#if ISOLATIN1
# define L_TODAY "astazi"
# define L_TOMORROW "m\342ine"
#elif ISOLATIN2
# define L_TODAY "ast\343zi"
# define L_TOMORROW "m\342ine"
#elif IBM852
# define L_TODAY "ast\307zi"
# define L_TOMORROW "m\203ine"
#else
# define L_TODAY "astazi"
# define L_TOMORROW "maine"
#endif
/* The default banner */
#define L_BANNER "Reamintiri pentru %w, %d %m %y%o:"
/* "am" and "pm" */
#define L_AM "am"
#define L_PM "pm"
#ifdef L_IN_DOSUBST
/*** The following are only used in dosubst.c ***/
/* Ago and from now */
#define L_AGO "acum"
#define L_FROMNOW "peste"
/* "in %d days' time" */
#define L_INXDAYS "peste %d zile"
/* "on" as in "on date..." */
#define L_ON "pe"
/* Pluralizing - this is a problem for many languages and may require
a more drastic fix */
#define L_PLURAL "le"
/* Minutes, hours, at, etc */
#define L_NOW "acum"
#define L_AT "la ora"
#define L_MINUTE "minut"
#define L_HOUR "or"
#define L_IS "este"
#define L_WAS "a fost"
/* What to add to make "minute" plural */
#define L_MPLU "e"
#if ISOLATIN2
/* What to add to make "hour" plural */
# define L_HPLU_OVER hplu = (hdiff == 1 ? "\343" : "e");
# define L_AND "\272i"
#elif IBM852
/* What to add to make "hour" plural */
# define L_HPLU_OVER hplu = (hdiff == 1 ? "\307" : "e");
# define L_AND "\255i"
#else
/* What to add to make "hour" plural */
# define L_HPLU_OVER hplu = (hdiff == 1 ? "a" : "e");
# define L_AND "si"
#endif
/* Define any overrides here, such as L_ORDINAL_OVERRIDE, L_A_OVER, etc.
See the file dosubst.c for more info. */
#if ISOLATIN2
# define L_AMPM_OVERRIDE(ampm, hour) ampm = (hour < 12) ? (hour<4) ? " noaptea" : " diminea\376a" : (hour > 17) ? " seara" : " dup\343-amiaza";
#elif IBM852
# define L_AMPM_OVERRIDE(ampm, hour) ampm = (hour < 12) ? (hour<4) ? " noaptea" : " diminea\316a" : (hour > 17) ? " seara" : " dup\307-amiaza";
#else
# define L_AMPM_OVERRIDE(ampm, hour) ampm = (hour < 12) ? (hour<4) ? " noaptea" : " dimineata" : (hour > 17) ? " seara" : " dupa-amiaza";
#endif
#define L_ORDINAL_OVERRIDE plu = "";
#define L_A_OVER sprintf(s, "%s, %d %s %d", DayName[jul%7], d, MonthName[m], y);
#define L_C_OVER sprintf(s, "%s", DayName[jul%7]);
#define L_G_OVER sprintf(s, "%s, %d %s", DayName[jul%7], d, MonthName[m]);
#define L_J_OVER sprintf(s, "%s, %s %d, %d", DayName[jul%7], MonthName[m], d, y);
#define L_K_OVER sprintf(s, "%s, %s %d", DayName[jul%7], MonthName[m], d);
#define L_S_OVER
#define L_U_OVER sprintf(s, "%s, %d %s %d", DayName[jul%7], d, MonthName[m], y);
#define L_V_OVER sprintf(s, "%s, %d %s", DayName[jul%7], d, MonthName[m]);
#define L_1_OVER \
if (tdiff == 0) \
sprintf(s, L_NOW); \
else if (hdiff == 0) \
sprintf(s, "%s %d %s%s", when, mdiff, L_MINUTE, mplu); \
else if (mdiff == 0) \
sprintf(s, "%s %d %s%s", when, hdiff, L_HOUR, hplu); \
else \
sprintf(s, "%s %d %s%s %s %d %s%s", when, hdiff, \
L_HOUR, hplu, L_AND, mdiff, L_MINUTE, mplu);
#endif /* L_IN_DOSUBST */

96
src/langs/spanish.h Normal file
View File

@@ -0,0 +1,96 @@
/***************************************************************/
/* */
/* SPANISH.H */
/* */
/* Support for the Spanish language. */
/* */
/* Author: Rafa Couto <rafacouto@biogate.com> */
/* */
/* This file is part of REMIND. */
/* Copyright (C) 1992-2020 by Dianne Skoll */
/* */
/***************************************************************/
#define L_LANGNAME "Spanish"
/* Nombres de los di'as de la semana */
#define L_SUNDAY "Domingo"
#define L_MONDAY "Lunes"
#define L_TUESDAY "Martes"
#if ISOLATIN1
#define L_WEDNESDAY "Mi\351rcoles"
#else
#define L_WEDNESDAY "Miercoles"
#endif
#define L_THURSDAY "Jueves"
#define L_FRIDAY "Viernes"
#if ISOLATIN1
#define L_SATURDAY "S\341bado"
#else
#define L_SATURDAY "Sabado"
#endif
/* Nombres de los meses */
#define L_JAN "Enero"
#define L_FEB "Febrero"
#define L_MAR "Marzo"
#define L_APR "Abril"
#define L_MAY "Mayo"
#define L_JUN "Junio"
#define L_JUL "Julio"
#define L_AUG "Agosto"
#define L_SEP "Septiembre"
#define L_OCT "Octubre"
#define L_NOV "Noviembre"
#define L_DEC "Diciembre"
/* Hoy y man~ana */
#define L_TODAY "hoy"
#if ISOLATIN1
#define L_TOMORROW "ma\361ana"
#else
#define L_TOMORROW "manana"
#endif
/* El titular habitual */
#define L_BANNER "Agenda para el %w, %d%s %m, %y%o:"
/* "am" and "pm" */
#define L_AM "am"
#define L_PM "pm"
/*** The following are only used in dosubst.c ***/
#ifdef L_IN_DOSUBST
/* Hace y desde hoy */
#define L_AGO "hace"
#define L_FROMNOW "desde hoy"
/* "dentro de %d di'as" */
#if ISOLATIN1
#define L_INXDAYS "dentro de %d d\355as"
#define L_ON "el d\355a"
#else
#define L_INXDAYS "dentro de %d di'as"
#define L_ON "el di'a"
#endif
/* "el di'a..." */
/* plurales */
#define L_PLURAL "s"
/* Minutos, horas, a las, etc */
#define L_NOW "ahora"
#define L_AT "a las"
#define L_MINUTE "minuto"
#define L_HOUR "hora"
#define L_IS "es"
#define L_WAS "fue"
#define L_AND "y"
#define L_HPLU "s"
#define L_MPLU "s"
#endif /* L_IN_DOSUBST */

File diff suppressed because it is too large Load Diff

249
src/md5.c Normal file
View File

@@ -0,0 +1,249 @@
/*
* This code implements the MD5 message-digest algorithm.
* The algorithm is due to Ron Rivest. This code was
* written by Colin Plumb in 1993, no copyright is claimed.
* This code is in the public domain; do with it what you wish.
*
* Equivalent code is available from RSA Data Security, Inc.
* This code has been tested against that, and is equivalent,
* except that you don't need to include two pages of legalese
* with every copy.
*
* LIC: GPL
*
* To compute the message digest of a chunk of bytes, declare an
* MD5Context structure, pass it to MD5Init, call MD5Update as
* needed on buffers full of bytes, and then call MD5Final, which
* will fill a supplied 16-byte array with the digest.
*/
#include <string.h> /* for memcpy() */
#include "md5.h"
static void byteReverse(unsigned char *buf, unsigned longs);
/*
* Note: this code is harmless on little-endian machines.
*/
static void
byteReverse(unsigned char *buf, unsigned longs)
{
uint32 t;
do {
t = (uint32) ((unsigned) buf[3] << 8 | buf[2]) << 16 |
((unsigned) buf[1] << 8 | buf[0]);
*(uint32 *) buf = t;
buf += 4;
} while (--longs);
}
/*
* Start MD5 accumulation. Set bit count to 0 and buffer to mysterious
* initialization constants.
*/
void MD5Init(struct MD5Context *ctx)
{
ctx->buf[0] = 0x67452301;
ctx->buf[1] = 0xefcdab89;
ctx->buf[2] = 0x98badcfe;
ctx->buf[3] = 0x10325476;
ctx->bits[0] = 0;
ctx->bits[1] = 0;
}
/*
* Update context to reflect the concatenation of another buffer full
* of bytes.
*/
void MD5Update(struct MD5Context *ctx, unsigned char const *buf, unsigned len)
{
uint32 t;
/* Update bitcount */
t = ctx->bits[0];
if ((ctx->bits[0] = t + ((uint32) len << 3)) < t)
ctx->bits[1]++; /* Carry from low to high */
ctx->bits[1] += len >> 29;
t = (t >> 3) & 0x3f; /* Bytes already in shsInfo->data */
/* Handle any leading odd-sized chunks */
if (t) {
unsigned char *p = (unsigned char *) ctx->in + t;
t = 64 - t;
if (len < t) {
memcpy(p, buf, len);
return;
}
memcpy(p, buf, t);
byteReverse(ctx->in, 16);
MD5Transform(ctx->buf, (uint32 *) ctx->in);
buf += t;
len -= t;
}
/* Process data in 64-byte chunks */
while (len >= 64) {
memcpy(ctx->in, buf, 64);
byteReverse(ctx->in, 16);
MD5Transform(ctx->buf, (uint32 *) ctx->in);
buf += 64;
len -= 64;
}
/* Handle any remaining bytes of data. */
memcpy(ctx->in, buf, len);
}
/*
* Final wrapup - pad to 64-byte boundary with the bit pattern
* 1 0* (64-bit count of bits processed, MSB-first)
*/
void MD5Final(unsigned char digest[16], struct MD5Context *ctx)
{
unsigned count;
unsigned char *p;
/* Compute number of bytes mod 64 */
count = (ctx->bits[0] >> 3) & 0x3F;
/* Set the first char of padding to 0x80. This is safe since there is
always at least one byte free */
p = ctx->in + count;
*p++ = 0x80;
/* Bytes of padding needed to make 64 bytes */
count = 64 - 1 - count;
/* Pad out to 56 mod 64 */
if (count < 8) {
/* Two lots of padding: Pad the first block to 64 bytes */
memset(p, 0, count);
byteReverse(ctx->in, 16);
MD5Transform(ctx->buf, (uint32 *) ctx->in);
/* Now fill the next block with 56 bytes */
memset(ctx->in, 0, 56);
} else {
/* Pad block to 56 bytes */
memset(p, 0, count - 8);
}
byteReverse(ctx->in, 14);
/* Append length in bits and transform */
((uint32 *) ctx->in)[14] = ctx->bits[0];
((uint32 *) ctx->in)[15] = ctx->bits[1];
MD5Transform(ctx->buf, (uint32 *) ctx->in);
byteReverse((unsigned char *) ctx->buf, 4);
memcpy(digest, ctx->buf, 16);
memset(ctx, 0, sizeof(*ctx)); /* In case it's sensitive */
}
#ifndef ASM_MD5
/* The four core functions - F1 is optimized somewhat */
/* #define F1(x, y, z) (x & y | ~x & z) */
#define F1(x, y, z) (z ^ (x & (y ^ z)))
#define F2(x, y, z) F1(z, x, y)
#define F3(x, y, z) (x ^ y ^ z)
#define F4(x, y, z) (y ^ (x | ~z))
/* This is the central step in the MD5 algorithm. */
#define MD5STEP(f, w, x, y, z, data, s) \
( w += f(x, y, z) + data, w = w<<s | w>>(32-s), w += x )
/*
* The core of the MD5 algorithm, this alters an existing MD5 hash to
* reflect the addition of 16 longwords of new data. MD5Update blocks
* the data and converts bytes into longwords for this routine.
*/
void MD5Transform(uint32 buf[4], uint32 const in[16])
{
register uint32 a, b, c, d;
a = buf[0];
b = buf[1];
c = buf[2];
d = buf[3];
MD5STEP(F1, a, b, c, d, in[0] + 0xd76aa478, 7);
MD5STEP(F1, d, a, b, c, in[1] + 0xe8c7b756, 12);
MD5STEP(F1, c, d, a, b, in[2] + 0x242070db, 17);
MD5STEP(F1, b, c, d, a, in[3] + 0xc1bdceee, 22);
MD5STEP(F1, a, b, c, d, in[4] + 0xf57c0faf, 7);
MD5STEP(F1, d, a, b, c, in[5] + 0x4787c62a, 12);
MD5STEP(F1, c, d, a, b, in[6] + 0xa8304613, 17);
MD5STEP(F1, b, c, d, a, in[7] + 0xfd469501, 22);
MD5STEP(F1, a, b, c, d, in[8] + 0x698098d8, 7);
MD5STEP(F1, d, a, b, c, in[9] + 0x8b44f7af, 12);
MD5STEP(F1, c, d, a, b, in[10] + 0xffff5bb1, 17);
MD5STEP(F1, b, c, d, a, in[11] + 0x895cd7be, 22);
MD5STEP(F1, a, b, c, d, in[12] + 0x6b901122, 7);
MD5STEP(F1, d, a, b, c, in[13] + 0xfd987193, 12);
MD5STEP(F1, c, d, a, b, in[14] + 0xa679438e, 17);
MD5STEP(F1, b, c, d, a, in[15] + 0x49b40821, 22);
MD5STEP(F2, a, b, c, d, in[1] + 0xf61e2562, 5);
MD5STEP(F2, d, a, b, c, in[6] + 0xc040b340, 9);
MD5STEP(F2, c, d, a, b, in[11] + 0x265e5a51, 14);
MD5STEP(F2, b, c, d, a, in[0] + 0xe9b6c7aa, 20);
MD5STEP(F2, a, b, c, d, in[5] + 0xd62f105d, 5);
MD5STEP(F2, d, a, b, c, in[10] + 0x02441453, 9);
MD5STEP(F2, c, d, a, b, in[15] + 0xd8a1e681, 14);
MD5STEP(F2, b, c, d, a, in[4] + 0xe7d3fbc8, 20);
MD5STEP(F2, a, b, c, d, in[9] + 0x21e1cde6, 5);
MD5STEP(F2, d, a, b, c, in[14] + 0xc33707d6, 9);
MD5STEP(F2, c, d, a, b, in[3] + 0xf4d50d87, 14);
MD5STEP(F2, b, c, d, a, in[8] + 0x455a14ed, 20);
MD5STEP(F2, a, b, c, d, in[13] + 0xa9e3e905, 5);
MD5STEP(F2, d, a, b, c, in[2] + 0xfcefa3f8, 9);
MD5STEP(F2, c, d, a, b, in[7] + 0x676f02d9, 14);
MD5STEP(F2, b, c, d, a, in[12] + 0x8d2a4c8a, 20);
MD5STEP(F3, a, b, c, d, in[5] + 0xfffa3942, 4);
MD5STEP(F3, d, a, b, c, in[8] + 0x8771f681, 11);
MD5STEP(F3, c, d, a, b, in[11] + 0x6d9d6122, 16);
MD5STEP(F3, b, c, d, a, in[14] + 0xfde5380c, 23);
MD5STEP(F3, a, b, c, d, in[1] + 0xa4beea44, 4);
MD5STEP(F3, d, a, b, c, in[4] + 0x4bdecfa9, 11);
MD5STEP(F3, c, d, a, b, in[7] + 0xf6bb4b60, 16);
MD5STEP(F3, b, c, d, a, in[10] + 0xbebfbc70, 23);
MD5STEP(F3, a, b, c, d, in[13] + 0x289b7ec6, 4);
MD5STEP(F3, d, a, b, c, in[0] + 0xeaa127fa, 11);
MD5STEP(F3, c, d, a, b, in[3] + 0xd4ef3085, 16);
MD5STEP(F3, b, c, d, a, in[6] + 0x04881d05, 23);
MD5STEP(F3, a, b, c, d, in[9] + 0xd9d4d039, 4);
MD5STEP(F3, d, a, b, c, in[12] + 0xe6db99e5, 11);
MD5STEP(F3, c, d, a, b, in[15] + 0x1fa27cf8, 16);
MD5STEP(F3, b, c, d, a, in[2] + 0xc4ac5665, 23);
MD5STEP(F4, a, b, c, d, in[0] + 0xf4292244, 6);
MD5STEP(F4, d, a, b, c, in[7] + 0x432aff97, 10);
MD5STEP(F4, c, d, a, b, in[14] + 0xab9423a7, 15);
MD5STEP(F4, b, c, d, a, in[5] + 0xfc93a039, 21);
MD5STEP(F4, a, b, c, d, in[12] + 0x655b59c3, 6);
MD5STEP(F4, d, a, b, c, in[3] + 0x8f0ccc92, 10);
MD5STEP(F4, c, d, a, b, in[10] + 0xffeff47d, 15);
MD5STEP(F4, b, c, d, a, in[1] + 0x85845dd1, 21);
MD5STEP(F4, a, b, c, d, in[8] + 0x6fa87e4f, 6);
MD5STEP(F4, d, a, b, c, in[15] + 0xfe2ce6e0, 10);
MD5STEP(F4, c, d, a, b, in[6] + 0xa3014314, 15);
MD5STEP(F4, b, c, d, a, in[13] + 0x4e0811a1, 21);
MD5STEP(F4, a, b, c, d, in[4] + 0xf7537e82, 6);
MD5STEP(F4, d, a, b, c, in[11] + 0xbd3af235, 10);
MD5STEP(F4, c, d, a, b, in[2] + 0x2ad7d2bb, 15);
MD5STEP(F4, b, c, d, a, in[9] + 0xeb86d391, 21);
buf[0] += a;
buf[1] += b;
buf[2] += c;
buf[3] += d;
}
#endif

34
src/md5.h Normal file
View File

@@ -0,0 +1,34 @@
#ifndef MD5_H
#define MD5_H
/*
* LIC: GPL
*/
#include "config.h"
#if SIZEOF_UNSIGNED_INT == 4
typedef unsigned int uint32;
#elif SIZEOF_UNSIGNED_LONG == 4
typedef unsigned long uint32;
#else
# error Could not find a 32-bit integer type
#endif
struct MD5Context {
uint32 buf[4];
uint32 bits[2];
unsigned char in[64];
};
void MD5Init(struct MD5Context *context);
void MD5Update(struct MD5Context *context, unsigned char const *buf,
unsigned len);
void MD5Final(unsigned char digest[16], struct MD5Context *context);
void MD5Transform(uint32 buf[4], uint32 const in[16]);
/*
* This is needed to make RSAREF happy on some MS-DOS compilers.
*/
typedef struct MD5Context MD5_CTX;
#endif /* !MD5_H */

Some files were not shown because too many files have changed in this diff Show More