1 /* ---------------------------------------------------------------------------
2 
3    pcaldefs.h
4 
5    Notes:
6 
7       This file contains various definitions and declarations of items used
8       throughout the application.
9 
10    Revision history:
11 
12 	4.11.0
13 		B.Marr		2007-12-15
14 
15 		Add support for new '-W' option, to specify horizontal
16 		alignment of the "Month/Year" title on monthly-format
17 		calendars, thanks to a patch from Todd Foster.
18 
19 		Add support for building on Amiga, thanks to a patch from
20 		Stefan Haubenthal.
21 
22 		Add support for new "on" preposition, thanks to a request from
23 		and in part to a patch from Erkki Petsalo.
24 
25 		Enhance some comments.
26 
27 		Rename some variables, structures, and/or routines to be
28 		clearer about their purpose and/or to allow easier searching
29 		with fewer "false positives".
30 
31 	4.10.0
32 		B.Marr		2006-07-19
33 
34 		Provide a definition of the 'pcal' website URL so that it can
35 		be added to the PostScript output.
36 
37 		Change the date/time stamp format in the PostScript output.
38 
39 		Provide support for the DOS+DJGPP build environment, adding
40 		'%%For: xxx' in the PostScript output.
41 
42 		Reformatted comments and code to match my standards.
43 
44 		B.Marr		2006-07-12
45 
46 		Provide explicit casting in several spots to avoid warnings in
47 		a "gcc 3.4.2 on Solaris 8" environment, based on a report from
48 		David Mathog <mathog at mendel.bio.caltech.edu>.
49 
50 		Increase the value of the defined constant 'MAXWORD' from 100
51 		to 300.  This prevents a crash in the rare case when the
52 		number of 'words' on a single line in the calendar
53 		configuration file exceeds 100.
54 
55 		Get rid of all the '#ifdef PROTOS' checks, which are pretty
56 		much obsolete these days and just needlessly clutter up the
57 		code.
58 
59 		Drop support for obsolete platforms (Amiga, VMS, OS/2).
60 
61 		Merged 'pcalpapr.h' code into this file.
62 
63 	4.9.0
64 		B.Marr		2005-08-02
65 
66 		Add enumeration for new 'delete' keyword, from Bill Bogstad's
67 		'event deletion' patch.
68 
69 		B.Marr		2005-01-04
70 
71 		Provide 12 new character encodings (KOI8-R and several 'ISO
72 		8859-*' encodings) to correspond to new PostScript encoding
73 		vectors in order to support a wider diversity of languages.
74 
75 	4.8.0
76 		B.Marr		2004-12-05
77 
78 		Fix misleading references to "holiday" to instead refer to
79 		"predefined event" (i.e. not all pre-defined events are
80 		'holidays').  Create and support concept of 'input' language
81 		versus 'output' language.  Support specification of paper size
82 		via run-time option (command-line, etc).  Remove spaces
83 		embedded within tab fields. Perform various other cosmetic
84 		and/or comment cleanups.
85 
86 		B.Marr		2004-11-13
87 
88 		Use new KOI8U mapping for newly-added Ukrainian language
89 		support.  Provide support for "Friday the 13th" events, based
90 		on a patch from Don Laursen (donrl at users dot sourceforge
91 		dot net).
92 
93 	4.7	AWR	01/25/2000	add SEARCH_PCAL_DIR to control whether
94 					or not Pcal looks for the calendar
95 					file in the same directory where Pcal
96 					itself lives (not desirable if an
97 					executable named 'calendar' has been
98 					installed there)
99 
100 			04/19/1999	add DIVIDE_BLANK_SPACE (cf. writefil.c)
101 					to control style of blank date boxes
102 					beginning and end of HTML calendars
103 
104 			06/19/1998	add support for generating full-year
105 					HTML calendars
106 
107 			03/08/1998	add alternate scaling and translation
108 					factors for A4 size paper (-DA4PAPER);
109 					express all such factors as numbers
110 					instead of character strings (cf.
111 					pcal.c, pcalglob.h, pcallang.h,
112 					writefil.c); reposition Y origin as
113 					top of calendar boxes
114 
115 			12/21/1997	add OS/2 definitions (as suggested by
116 					Alexander Mai)
117 
118 			07/27/1997	add support for -H flag (HTML-specific
119 					macro definitions); delete obsolete FPR
120 					and PRT macros
121 
122 	4.6	AWR	05/14/1997	replace CENTURY with TM_YEAR (cf.
123 					<time.h>)
124 
125 			09/13/1996	support "nearest_before" and
126 					"nearest_after" keywords
127 
128 			04/30/1996	define NOBODY pseudo-account (Un*x
129 					only) to suppress various inapplicable
130 					comments when pcal is run anonymously
131 					from a CGI script (cf. writefil.c)
132 
133 			04/22/1996	specify alternate (taller) date box
134 					height, used when printing single-month
135 					portrait-mode calendars
136 
137 			11/29/1995	add ARRAYSIZE() macro (cf. readfile.c)
138 
139 			11/10/1995	add safe TOUPPER() macro
140 
141 	4.5	AWR	08/24/1994	Define CHAR_MSK (instead of hard-coded
142 					0377) to avoid negative result when
143 					promoting char to int (see comments)
144 
145 			12/21/1993	Removed obsolete COLOR_MIN, COLOR_MAX
146 					definitions
147 
148 			11/08/1993	Add IS_EURDATE() macro to support
149 					"nn." style of date specifications
150 
151 			09/09/1993	Support Roman8 and ISO Latin1
152 					character mappings (cf. fontmaps.ps,
153 					writefil.c)
154 
155 					Redefine MIN_YR from 1900 to 1753
156 
157 			03/20/1993	Allow several site-specific program
158 					defaults to be set in Makefile
159 
160 			03/05/1993	add MAPFONTS for optional mapping to
161 					8-bit fonts (for European languages)
162 
163 			12/29/1992	add PS_RELEASE to define PostScript
164 					version (for Encapsulated PostScript)
165 
166 			04/07/1992	Revise PUTCHAR macro: add <ctype.h>
167 					function/macro name and file pointer
168 					as arguments
169 
170 			02/11/1992	Many new declarations to help support
171 					predefined holidays
172 
173 	4.4	AWR	02/10/1992	Add PAGER_ENV (environment variable
174 					used in piping "help" message output
175 					[Un*x only])
176 
177 			01/20/1992	Added support for -z flag and revised
178 					versions of -[bgGO]
179 
180 			01/13/1992	Add default font size to DATEFONT and
181 					TITLEFONT; move initialization of all
182 					font sizes here (from pcalinit.ps);
183 					enlarge medium calendar font sizes
184 
185 	4.3	AWR	12/05/1991	Revise moonfile name templates for
186 					consistency with current standards
187 					for substituting year in strings
188 
189 			12/03/1991	Add support for -s flag
190 
191 			10/17/1991	Add support for -Z flag and subflags;
192 					removed obsolete PUTSTR macro
193 
194 	4.2	AWR	10/08/1991	Add support for -[kK] flags; renamed
195 					START_DAY as START_BOX for clarity
196 
197 			10/03/1991	Add various definitions relating to
198 					"note/<n>"
199 
200 			09/30/1991	Add MAX_IF_NESTING (related to "elif";
201 					cf. read_datefile() in readfile.c)
202 
203 	4.11	AWR	08/20/1991	Add "nearest" keyword (as per Andy
204 					Fyfe)
205 
206 	4.1	AWR	08/16/1991	Add support for -G flag
207 
208 	4.0	AWR	03/01/1991	Add STDLIB macro for systems which
209 					support <stdlib.h>
210 
211 			02/22/1991	add definitions for MS-DOS support (as
212 					per Floyd Miller)
213 
214 			02/19/1991	revise ORD_XXX to support negative
215 					ordinals
216 
217 					add definitions for Amiga support (as
218 					per Bill Hogsett)
219 
220 			02/06/1991	additional defs for expression
221 					processing
222 
223 			02/04/1991	support "year" as additional month
224 					name; use negative numbers for
225 					special ordinal codes (reserve
226 					positive numbers for ordinals)
227 
228 			01/28/1991	miscellaneous new constants/macros
229 
230 			01/07/1991	add FEB_29_OK (cf. enter_day_info())
231 
232 */
233 
234 /* ---------------------------------------------------------------------------
235 
236    Header Files
237 
238 */
239 
240 #include <stdlib.h>
241 
242 /* ---------------------------------------------------------------------------
243 
244    (Early) Constant Declarations
245 
246 */
247 
248 #define NOTE_DEFAULT	-1   /* default note box number (-1 = last box) */
249 #define FIRST_NOTE_BOX	 0   /* first box position for notes text */
250 #define LAST_NOTE_BOX	41   /* last position (w/o small calendars) */
251 #define NULL_NOTE_BOX	-1   /* negative number for nonexistent box */
252 
253 /* number and range of dummy days for notes text */
254 #define NUM_NOTE_DAYS   (LAST_NOTE_BOX - 28 + 1)
255 #define FIRST_NOTE_DAY   32
256 #define LAST_NOTE_DAY   (FIRST_NOTE_DAY + NUM_NOTE_DAYS - 1)
257 
258 
259 /* ---------------------------------------------------------------------------
260 
261    Type, Struct, & Enum Declarations
262 
263 */
264 
265 /*
266  * Define the structure which holds the information about the various settings
267  * for the various paper sizes.
268  */
269 typedef struct {
270    char *name;
271    int page_dim_short_axis_pts;
272    int page_dim_long_axis_pts;
273    int daybox_width_pts;
274    int daybox_height_pts;
275 } paper_info_str_typ;
276 
277 /*
278  * The internal data structure consists of a series of linked lists as
279  * pictured below (for clarity, only one instance of each node is shown):
280  *
281  *
282  * head
283  *  |
284  *  |        year_info
285  *  |    -----------------           month_info
286  *   -->| year            |       -----------------            day_info
287  *      | month_info*[0]  |----->| holidays        |       ----------------
288  *      |   ...           |      | day_info*[0]    |----->| is_holiday     |
289  *      | month_info*[11] |--->  |   ...           |      | text_string*   |--->
290  *      | next year_info* |--    | day_info*[30]   |--->  | next day_info* |--
291  *       -----------------   |   | day_info*[NOTE] |--->   ----------------   |
292  *                           |   |   ...           |                          |
293  *                           |    -----------------                           |
294  *             ...        <--                                     ...      <--
295  *
296  *
297  * Each year_info node consists of the year, 12 pointers (Jan .. Dec) to
298  * month_info nodes, and a pointer to the next year_info node in the chain.
299  * (The year_info chain is maintained in ascending order by year.)
300  *
301  * Each month_info node consists of a bitmap of the holidays for that month,
302  * a pointer to the day_info chain for all 31 possible days of the month, and
303  * N additional pointers to the day_info chains for the "Notes" pseudo-days.
304  * (A day_info chain is a linked list of all the text entries for a given
305  * day, in the order in which they were encountered in the date file.)
306  *
307  * Each day_info node consists of a flag indicating whether the associated
308  * text string is holiday or non-holiday text (any given day may have both),
309  * a pointer to the text string itself, and a pointer to the next day_info
310  * node in the chain.
311  *
312  */
313 
314 typedef struct d_i {
315    int is_holiday;
316    char *text;
317    struct d_i *next;
318 } day_info;
319 
320 typedef struct m_i {
321    unsigned long holidays;
322    day_info *day[LAST_NOTE_DAY];   /* including extra days for notes */
323 } month_info;
324 
325 typedef struct y_i {
326    int year;
327    month_info *month[12];
328    struct y_i *next;
329 } year_info;
330 
331 /*
332  * Global typedef declaration for date structure (cf. parse_ord())
333  */
334 typedef struct {
335    int mm;
336    int dd;
337    int yy;
338 } date_str;
339 
340 /*
341  * Global typedef declarations for keyword descriptors (cf. pcallang.h)
342  */
343 typedef struct {
344    char *name;
345    int   code;
346 } KWD;
347 
348 typedef struct {
349    char *name;
350    int   code;
351    int   value;
352 } KWD_O;   /* keyword plus ordinal value */
353 
354 typedef struct {
355    char *name;
356    int   code;
357    int (*pfcn)(char *);
358 } KWD_F;   /* keyword plus dispatch function */
359 
360 typedef struct {
361    char *name;
362    char *def;   /* "def" and "pfcn" are mutually exclusive */
363    int (*pfcn)(date_str *);
364 } KWD_H;   /* keyword, equivalent string, dispatch fcn */
365 
366 /*
367  * Global typedef declaration for flag usage struct (cf. pcallang.h, get_args())
368  */
369 
370 typedef struct {
371    char flag;   /* name of flag */
372    char has_arg;   /* TRUE if flag takes (optional) arg */
373    char passes;   /* "or" of P_xxx for relevant passes */
374 } FLAG_USAGE;
375 
376 /*
377  * Global typedef declaration for debugging info struct (cf. pcallang.h)
378  */
379 
380 typedef struct {
381    char flag;   /* name of flag */
382    int  value;   /* value corresponding to flag (1 << n) */
383 } DEBUG_INFO;
384 
385 /*
386  * Global typedef declarations for usage message (cf. pcallang.h, usage())
387  */
388 typedef struct {
389    char flag;   /* name of flag */
390    char *meta;   /* metaname for argument (if any) */
391    char *text;   /* associated text */
392    char *def;   /* default value (if any) */
393 } FLAG_MSG;
394 
395 typedef struct {
396    char *desc;   /* description of param */
397    char *text;   /* associated text */
398 } PARAM_MSG;
399 
400 typedef char *DATE_MSG;   /* date file syntax message */
401 
402 /* ---------------------------------------------------------------------------
403 
404    Constant Declarations
405 
406 */
407 
408 /*
409    Special definitions for a DOS environment
410 */
411 #if defined (BUILD_ENV_MSDOS) || defined (BUILD_ENV_DJGPP)
412 
413 #define DATEFILE	"pcal.dat"
414 #define MOONFILE	"moon%y.dat"	/* '%y' replaced with year */
415 #define START_PATH	'\\'
416 #define END_PATH	'\\'
417 #define HOME_DIR	"HOME"
418 #define ALT_DATEFILE	"calendar"	/* for backward compatibility */
419 
420 #else   /* not DOS -- assume Unix */
421 
422 /*
423    Special definitions for a Unix environment
424 */
425 #define HOME_DIR	"HOME"
426 #define DATEFILE	".calendar"
427 #define ALT_DATEFILE	"calendar"	/* for backward compatibility */
428 #define MOONFILE	".moon%y"	/* '%y' replaced with year */
429 #define ALT_MOONFILE	"moon%y"	/* analogous to ALT_DATEFILE */
430 #define START_PATH	'/'
431 #define END_PATH	'/'
432 
433 #ifndef AMIGA
434 #define PAGER_ENV	"PAGER"		/* points to help message pager */
435 #define PAGER_DEFAULT	"more"		/* default pager (NULL = none) */
436 #endif
437 
438 #endif
439 
440 
441 /*
442  * Define enumerations for the supported paper sizes.  The order of entries in
443  * the 'paper_info[]' array must correspond to these enumerations.
444  */
445 #define NUM_PAPER_SIZES		4	/* *** Change this if adding a new paper size. *** */
446 #define PAPERSIZE_LETTER	0
447 #define PAPERSIZE_LEGAL		1
448 #define PAPERSIZE_A4		2
449 #define PAPERSIZE_TABLOID	3
450 
451 #define PAPERSIZE_DEFAULT	PAPERSIZE_LETTER
452 
453 /*
454  * Define the distance (in typographic points) from the top edge of the paper
455  * to the top of the calendar boxes for a monthly calendar in landscape
456  * orientation.
457  *
458  * The value defined here includes the top margin, rather than defining proper
459  * margins and using them generically.  This is rather a inelegant way of
460  * doing it, but it's been done that way for a long time.
461  */
462 #define TOP_OF_CAL_BOXES_PTS	(-85)
463 
464 /*
465  * Define the default left, right, top, and bottom margins (in typographic
466  * points).
467  *
468  * Some of these values are not currently used, but are left here for a time
469  * when 'pcal' might be modified to provide proper, flexible margins.
470  */
471 #define DEFAULT_MARGIN_LEFT_PTS		46
472 #define DEFAULT_MARGIN_RIGHT_PTS	46
473 #define DEFAULT_MARGIN_TOP_PTS		46
474 #define DEFAULT_MARGIN_BOTTOM_PTS	46
475 
476 
477 
478 #define ALL	"all"		/* command-line or date file keywords */
479 #define HOLIDAY	"holiday"
480 
481 /* names of colors used in printing dates (cf. flag_msg[] below) */
482 
483 #define W_BLACK		"black"
484 #define W_GRAY		"gray"
485 #define W_OUTLINE	"outline"
486 #define W_OUTLINE_GRAY	"outline-gray"
487 
488 #define W_ROMAN		"Roman"		/* for -T usage message */
489 
490 /*
491    Define PS_OUTFILE and HTML_OUTFILE as DEFAULT_*_OUTFILE if defined;
492    otherwise define as "" (stdout)
493 */
494 #ifdef DEFAULT_PS_OUTFILE
495 #define PS_OUTFILE	DEFAULT_PS_OUTFILE
496 #else
497 #define PS_OUTFILE	""
498 #endif
499 
500 #ifdef DEFAULT_HTML_OUTFILE
501 #define HTML_OUTFILE	DEFAULT_HTML_OUTFILE
502 #else
503 #define HTML_OUTFILE	""
504 #endif
505 
506 
507 /* EXIT_SUCCESS and EXIT_FAILURE should be defined in <stdlib.h>
508  * (or above if non-standard); define here if necessary
509  */
510 
511 #ifndef EXIT_SUCCESS
512 #define EXIT_SUCCESS	0
513 #endif
514 #ifndef EXIT_FAILURE
515 #define EXIT_FAILURE	1
516 #endif
517 
518 /* definition of NULL (if needed) */
519 
520 #ifndef NULL
521 #define NULL	0
522 #endif
523 
524 /*
525  * Environment variables (global symbol, logical name on VMS):
526  */
527 
528 #define PCAL_OPTS	"PCAL_OPTS"	/* command-line flags */
529 #define PCAL_DIR	"PCAL_DIR"	/* calendar file directory */
530 #define PATH_ENV_VAR	"PATH"		/* cf. find_executable() (pcalutil.c) */
531 
532 /*
533  * mask to avoid sign extension when promoting char to int (as in the PUTCHAR
534  * macro below); some older compilers may sign-extend this mask anyway, in
535  * which case you may want to try defining it as ((int) 0377) or even 255 :
536  */
537 #define CHAR_MSK	0377
538 
539 /* debug subflag codes (must be distinct) - cf. pcallang.h */
540 #define DEBUG_DATES	(1 << 1)
541 #define DEBUG_MOON	(1 << 2)
542 #define DEBUG_PATHS	(1 << 3)
543 #define DEBUG_OPTS	(1 << 4)
544 #define DEBUG_PP	(1 << 5)
545 #define DEBUG_TEXT	(1 << 6)
546 
547 /* preprocessor token codes - cf. get_token(), pcallang.h */
548 #define PP_DEFINE	 0
549 #define PP_ELIF		 1
550 #define PP_ELSE		 2
551 #define PP_ENDIF	 3
552 #define PP_IFDEF	 4
553 #define PP_IFNDEF	 5
554 #define PP_INCLUDE	 6
555 #define PP_UNDEF	 7
556 #define PP_OTHER	-1	/* not pp token */
557 
558 /* ordinal number codes - cf. get_ordinal(), pcallang.h */
559 #define ORD_NEGNUM	-1	/* negative ordinal (-2nd == next to last) */
560 #define ORD_POSNUM	 1	/* positive ordinal */
561 #define ORD_ODD		 2	/* special codes for "odd" and "even" */
562 #define ORD_EVEN	 3
563 #define ORD_ALL		 4	/* special code for "all" used as ordinal */
564 #define ORD_OTHER	 0	/* not ordinal token */
565 
566 /* ordinal numbers themselves - added for predefined holiday routines */
567 #define FIRST		 1
568 #define SECOND		 2
569 #define THIRD		 3
570 #define FOURTH		 4
571 #define FIFTH		 5
572 #define LAST		-1
573 
574 /* moon phase codes - cf. pcallang.h and moonphas.c; these must take the
575  * values 0 (NM) .. 3 (3Q) since they are used in phase calculations
576  */
577 #define MOON_NM		 0	/* new moon */
578 #define MOON_1Q		 1	/* first quarter */
579 #define MOON_FM		 2	/* full moon */
580 #define MOON_3Q		 3	/* last quarter */
581 #define MOON_OTHER	-1	/* unrecognizable */
582 
583 /* date type codes - cf. date_type(), get_keywd(), and pcallang.h */
584 #define DT_ALL			 0	/* "all" keyword" */
585 #define DT_NOTE			 1	/* "note" keyword */
586 #define DT_OPT			 2	/* "opt" keyword */
587 #define DT_INPUT_LANGUAGE	 3	/* "input-language" keyword */
588 #define DT_YEAR			 4	/* "year" keyword */
589 #define DT_MONTH		 5	/* name of month */
590 #define DT_DATE			 6	/* date of form dd/mm{/yy} or mm/dd{/yy} */
591 #define DT_EURDATE		 7	/* European date of form dd <month> */
592 #define DT_ORDINAL		 8	/* ordinal (first, 1st, ... last) */
593 #define DT_WEEKDAY		 9	/* weekday name */
594 #define DT_PREDEF_EVENT		10	/* predefined event (often a holiday) */
595 #define DT_DELETE		11	/* delete date entry following on this line */
596 #define DT_OTHER		-1	/* unrecognizable first token */
597 
598 /* preposition token codes - cf. get_prep(), pcallang.h */
599 #define PR_BEFORE	  0
600 #define PR_ON_BEFORE	  1
601 #define PR_AFTER	  2
602 #define PR_ON_AFTER	  3
603 #define PR_NEAREST	  4
604 #define PR_NEAREST_BEFORE 5
605 #define PR_NEAREST_AFTER  6
606 #define PR_ON		  7
607 #define PR_OTHER	 -1	/* not a preposition */
608 
609 /*
610  * Miscellaneous other constants:
611  */
612 
613 #define COMMENT_CHAR	'#'	/* delimiter for datefile comments */
614 
615 #define RGB_CHAR	':'	/* delimiter for red/green/blue values */
616 
617 #ifndef TRUE
618 #define FALSE		0	/* pseudo-Booleans */
619 #define TRUE		1
620 #endif
621 
622 #define MAX_FILE_NESTING 10	/* maximum nesting level for file inclusion */
623 #define MAX_IF_NESTING	20	/* maximum nesting level for if{n}def */
624 
625 #define MAX_PP_SYMS	100	/* number of definable preprocessor symbols */
626 #define PP_SYM_UNDEF     -1	/* flag for undefined symbol */
627 
628 #define EXPR_ERR	-1	/* expression parsing error */
629 
630 #define MIN_YR		1753	/* significant years (calendar limits) */
631 #define MAX_YR		9999
632 
633 #define ALL_YEARS	-1	/* wildcard for years */
634 #define TM_YEAR	1900		/* offset for tm_year field of struct tm  */
635 				/* (cf. <time.h>); may need to be changed */
636 				/* for non-Unix implementations           */
637 
638 #define SCREENWIDTH	78	/* command-line message in usage() */
639 
640 #define FEB_29_OK	 1	/* if != 0, ignore 2/29 of common year */
641 
642 /*
643    Empty text associated with an event entry or a 'note' entry is propagated
644    to the calendar as a blank line.  This is useful for grouping related lines
645    together.  If you prefer to ignore such lines, define 'KEEP_NULL_LINES' as
646    0 here.
647 */
648 #define KEEP_NULL_LINES	 1
649 
650 #define NEAREST_INCR	 1	/* if 1, disambiguate "nearest" as later    */
651 				/* date; if -1, to earlier (cf. readfile.c) */
652 
653 #ifndef SEARCH_PCAL_DIR
654 #define SEARCH_PCAL_DIR  1	/* if 1, look for the calendar file in the  */
655 				/* same directory where the pcal executable */
656 				/* lives; if 0, avoid this (e.g., in case a */
657 				/* program named 'calendar' has also been   */
658 				/* installed in this directory)             */
659 #endif
660 
661 #define JAN		 1	/* months (for predefined holiday routines) */
662 #define FEB		 2
663 #define MAR		 3
664 #define APR		 4
665 #define MAY		 5
666 #define JUN		 6
667 #define JUL		 7
668 #define AUG		 8
669 #define SEP		 9
670 #define OCT		10
671 #define NOV		11
672 #define DEC		12
673 #define NOT_MONTH	-1	/* not valid month */
674 
675 #define ALL_MONTHS	 0	/* select all months */
676 #define ENTIRE_YEAR	13	/* select entire year as one entity */
677 
678 #define SUN		 0	/* weekdays - cf. wildcard codes below */
679 #define MON		 1
680 #define TUE		 2
681 #define WED		 3
682 #define THU		 4
683 #define FRI		 5
684 #define SAT		 6
685 #define NOT_WEEKDAY	-1	/* not valid weekday */
686 
687 #define NOT_PREDEF_EVENT	-1	/* flag for end of 'pre-defined event' list */
688 
689 /* wildcards - cf. days[] in pcallang.h and pdatefcn[] in pcalglob.h */
690 
691 #define ANY_DAY		 7	/* special - matches any day */
692 #define ANY_WEEKDAY	 8	/* matches any weekday (including holidays) */
693 #define ANY_WORKDAY	 9	/* matches any weekday (excluding holidays) */
694 #define ANY_HOLIDAY	10	/* matches any holiday */
695 #define ANY_NONWEEKDAY	11	/* converses of above three */
696 #define ANY_NONWORKDAY	12
697 #define ANY_NONHOLIDAY	13
698 /* moon phase wildcards - must be in same order as MOON_* below */
699 #define ANY_NM		14	/* matches any new moon, etc. */
700 #define ANY_1Q		15
701 #define ANY_FM		16
702 #define ANY_3Q		17
703 
704 #define WILD_FIRST	ANY_DAY
705 #define WILD_FIRST_WKD	ANY_DAY
706 #define WILD_LAST_WKD	ANY_NONHOLIDAY
707 #define WILD_FIRST_MOON ANY_NM
708 #define WILD_LAST_MOON	ANY_3Q
709 #define WILD_LAST	ANY_3Q
710 
711 
712 #define DAY_TEXT	0	/* types of text in data structure */
713 #define HOLIDAY_TEXT	1
714 #define NOTE_TEXT	2
715 
716 #define MAX_DATES	366	/* maximum "wildcard" dates */
717 
718 #define MAXWORD		300	/* maximum words in date file line */
719 #define STRSIZ		200	/* size of misc. strings */
720 #define VALSIZ		12	/* size of numeric value strings */
721 #define LINSIZ		512	/* size of source line buffer */
722 
723 #define MAXARGS		3	/* numeric command-line args */
724 
725 #define WHITESPACE	" \t"	/* token delimiters in date file */
726 #define DIGITS		"0123456789"
727 
728 /* passes where flags may be recognized (cf. get_args(), pcallang.h) */
729 #define P_CMD0	(1 << 1)   /* parsed in command line pre-pass (-Z only) */
730 #define P_ENV	(1 << 2)   /* parsed from environment variable */
731 #define P_CMD1	(1 << 3)   /* parsed in first command-line pass */
732 #define P_OPT	(1 << 4)   /* parsed on "opt" lines in date file */
733 #define P_CMD2	(1 << 5)   /* parsed in second command-line pass */
734 
735 /*
736  * Defaults for calendar layout:
737  */
738 
739 
740 /* Define strings for comments in PostScript output file... */
741 
742 #ifdef EPS   /* generate EPS-like comments */
743 #define PS_RELEASE   "PS-Adobe-2.0"
744 #else
745 #define PS_RELEASE   "PS-Adobe-1.0"
746 #endif
747 
748 #define PCAL_WEBSITE   "http://pcal.sourceforge.net"
749 
750 
751 /* default font names and sizes (large calendars) */
752 
753 #ifndef TITLEFONT
754 #define TITLEFONT	"Times-Bold/48"   /* month/year title */
755 #endif
756 #ifndef DATEFONT
757 #define DATEFONT	"Times-Bold/25"   /* dates */
758 #endif
759 #ifndef NOTESFONT
760 #define NOTESFONT	"Helvetica-Narrow/6"   /* notes in boxes */
761 #endif
762 
763 /* define secondary fonts in terms of main fonts */
764 #define WEEKDAYFONT	"titlefont"   /* weekday names */
765 #define FOOTFONT	"titlefont"   /* footer strings */
766 #define HEADINGFONT	"titlefont"   /* notes box heading */
767 
768 /* define MAP_DATEFONT as 1 if any secondary font (above) is defined as
769  * "datefont" (cf. writefil.c); otherwise, define as 0
770  */
771 #define MAP_DATEFONT	0   /* re-map date font? */
772 
773 /* font sizes (small, medium, large calendars respectively) - moved here
774  * from pcalinit.ps; enlarged (again) for medium (whole-year) calendars
775  */
776 #define SMALL		0
777 #define MEDIUM		1
778 #define LARGE		2
779 #define CALSIZE		{ "small", "medium", "large" };
780 
781 #define TITLEFONTSIZE	{ 60, 64, 48 }	/* month/year (cf. TITLEFONT above) */
782 #define DATEFONTSIZE	{ 60, 56, 25 }	/* dates (cf. DATEFONT above) */
783 #define WEEKDAYFONTSIZE	{  0, 30, 12 }	/* weekdays */
784 #define FOOTFONTSIZE	{  0, 14, 12 }	/* footer strings */
785 #define HEADINGFONTSIZE	12		/* same as large weekdays */
786 
787 #define GRIDLINEWIDTH   {2.5,  2,  1 }	/* grid lines */
788 #define DATEMARGIN	{ 10,  8,  4 }  /* top/side date margin */
789 
790 #ifndef SHADING
791 #define SHADING		"0.8/0.9"	/* default shading (dates/fill boxes) */
792 #endif
793 
794 #define IS_TITLE_ALIGN(s) (strcmp(s,"left") == 0 || strcmp(s,"center") == 0 || strcmp(s,"right") == 0)
795 #define TITLE_ALIGN "center"  /* default monthly title alignment */
796 
797 #define LFOOT		""              /* default foot strings */
798 #define CFOOT		""
799 #define RFOOT		""
800 
801 #define LANDSCAPE	90		/* degrees to rotate */
802 #define PORTRAIT	 0
803 #define ROTATE		LANDSCAPE	/* default */
804 
805 #define	NCOPY		1		/* copies of each output page */
806 #define MAXCOPY		100		/* just in case... */
807 
808 #define USA_DATES	0		/* date styles */
809 #define EUR_DATES	1
810 #ifndef DATE_STYLE
811 #define DATE_STYLE	USA_DATES	/* default */
812 #endif
813 
814 #ifndef FIRST_DAY
815 #define FIRST_DAY	SUN		/* first day of logical week */
816 #endif
817 
818 /* values below must be in sync with color_names[] in pcallang.h and also
819  * with prtday{} in pcalinit.ps
820  */
821 #define BLACK		0		/* colors for dates */
822 #define GRAY		1
823 #define OUTLINE		2
824 #define OUTLINE_GRAY	3
825 #define NUM_COLORS	4		/* total number of colors */
826 
827 #define HOLIDAY_DEFAULT	-1		/* use same color as weekends */
828 #define	HOLIDAY_COLOR	HOLIDAY_DEFAULT
829 
830 /* default time zone for -z flag; you may optionally define this as
831  * (say) "5 [Boston]" (note space) to print the city in the -h message
832  */
833 #ifndef TIMEZONE
834 #define TIMEZONE	"0"		/* hours west of GMT/UTC */
835 #endif
836 
837 /* default colors for weekdays (presumes black and at most one other color -
838  * cf. color_msg() in pcal.c)
839  */
840 #define DAY_COLOR	{ GRAY, BLACK, BLACK, BLACK, BLACK, BLACK, GRAY }
841 #define WEEKDAY_COLOR	BLACK		/* prevalent color in DAY_COLOR */
842 
843 #define NO_DATEFILE	0		/* date file (if any) to use */
844 #define USER_DATEFILE	1
845 #define SYS_DATEFILE	2
846 
847 /* position of small calendars */
848 #define SC_NONE		0		/* suppress small calendars */
849 #define SC_LAST		1		/* use last two boxes */
850 #define SC_FIRST	2		/* use first two boxes */
851 #define SC_SPLIT	3		/* split between first and last */
852 #define SMALL_CAL_POS	SC_LAST		/* default */
853 
854 /* box numbers for small calendars - must conform to order defined above */
855 #define PREV_CAL_BOX	\
856 	{ NULL_NOTE_BOX, LAST_NOTE_BOX - 1, FIRST_NOTE_BOX, FIRST_NOTE_BOX }
857 #define NEXT_CAL_BOX	\
858 	{ NULL_NOTE_BOX, LAST_NOTE_BOX, FIRST_NOTE_BOX + 1, LAST_NOTE_BOX }
859 
860 /* values below must be in sync with cond[] in writefil.c */
861 #define NO_MOONS	0		/* no moon icons */
862 #define ALL_MOONS	1		/* moon icon on every day */
863 #define SOME_MOONS	2		/* icons on full, half, new moons */
864 #define DRAW_MOONS	NO_MOONS	/* default */
865 
866 #define NO_JULIANS	0		/* no Julian dates */
867 #define ALL_JULIANS	1		/* Julian date + days left */
868 #define SOME_JULIANS	2		/* just Julian dates */
869 #define JULIAN_DATES	NO_JULIANS	/* default: none */
870 
871 #define DO_WHOLE_YEAR	FALSE		/* -w default */
872 #define BLANK_BOXES	FALSE		/* -B default */
873 
874 #define OUTPUT_PS	0		/* output PostScript */
875 #define OUTPUT_CAL	1		/* -c: output Un*x calendar(1) input */
876 #define OUTPUT_HTML	2		/* -H: output HTML table */
877 #define OUTPUT_TYPE	OUTPUT_PS	/* default for above */
878 
879 /*
880  * HTML definitions - may be changed according to local requirements either
881  * here or on the C compiler command line (cf. Makefile)
882  */
883 
884 /* attributes for <body> tag (cf. body_attributes[] in writefil.c) */
885 
886 #ifndef BGCOLOR
887 #define BGCOLOR		"ffffff"   /* background color */
888 #endif
889 
890 #ifndef BACKGROUND
891 #define BACKGROUND	NULL   /* background pattern */
892 #endif
893 
894 #ifndef TEXT
895 #define TEXT		NULL   /* text color */
896 #endif
897 
898 #ifndef LINK
899 #define LINK		NULL   /* link color */
900 #endif
901 
902 #ifndef ALINK
903 #define ALINK		NULL   /* active link color */
904 #endif
905 
906 #ifndef VLINK
907 #define VLINK		NULL   /* viewed link color */
908 #endif
909 
910 /* definitions for HTML table format */
911 
912 #ifndef BORDER
913 #define BORDER		1   /* border width attribute */
914 #endif
915 
916 #ifndef TEXTLINES
917 #define TEXTLINES	2   /* min. text lines per box */
918 #endif
919 
920 /* HTML sequences preceding/following holiday dates and headings */
921 
922 /* holiday dates are bold and red for HTML calendars */
923 #if !(defined(HOLIDAY_PRE) && defined(HOLIDAY_POST))
924 #define HOLIDAY_PRE	"<font color=#ff0000><b>"
925 #define HOLIDAY_POST	"</b></font>"
926 #endif
927 
928 /* month/year heading (single-month mode) */
929 #if !(defined(MONTHYEAR_PRE) && defined(MONTHYEAR_POST))
930 #define MONTHYEAR_PRE	"<br><font size=+1>"
931 #define MONTHYEAR_POST	"</font><br>&nbsp;"
932 #endif
933 
934 /* month/year heading (whole-year mode) */
935 #if !(defined(MONTHYEAR_W_PRE) && defined(MONTHYEAR_W_POST))
936 #define MONTHYEAR_W_PRE	 "<font size=+1>"
937 #define MONTHYEAR_W_POST "</font>"
938 #endif
939 
940 /* page heading (-C flag) */
941 #if !(defined(HEADING_PRE) && defined(HEADING_POST))
942 #define HEADING_PRE	"<h3 align=center>"
943 #define HEADING_POST	"</h3><p>"
944 #endif
945 
946 /* print blank space (vacant date boxes) at beginning/end of HTML calendars
947  * as N single-column boxes (1) or one N-column box (0) according to your
948  * preference
949  */
950 #ifndef DIVIDE_BLANK_SPACE
951 #define DIVIDE_BLANK_SPACE	0
952 #endif
953 
954 
955 /* minimum size of abbreviations - adjust as appropriate for target language */
956 
957 #define MIN_DAY_LEN	3	/* distinguish "Thursday" from "third" */
958 #define ABBR_DAY_LEN	3	/* length of abbreviated day names */
959 #define ABBR_MONTH_LEN	3	/* length of abbreviated month names */
960 #define MIN_PPTOK_LEN	3	/* minimum length of a pre-processor token */
961 #define MIN_PREP_LEN	9	/* distinguish "nearest", "nearest_before",
962 				   "nearest_after" */
963 #define MIN_ORD_LEN	4	/* distinguish "every" from "even" */
964 #define MIN_LANG_LEN	2	/* effective size of language names */
965 
966 
967 /*
968  * Symbolic names for command-line flags.  These may be changed
969  * as desired in order to be meaningful in languages other than
970  * English.
971  */
972 
973 #define F_INITIALIZE	'I'		/* re-initialize program defaults */
974 #define	F_BLACK_DAY	'b'		/* print day in black */
975 #define F_GRAY_DAY	'g'		/* print day in gray */
976 #define F_OUTLINE	'O'		/* draw "gray" dates as outlines */
977 #define F_OUTLINE_GRAY	'G'		/* outline and fill "gray" dates */
978 
979 #define F_DAY_FONT	'd'		/* select alternate day font */
980 #define F_NOTES_FONT	'n'		/* select alternate notes font */
981 #define F_TITLE_FONT	't'		/* select alternate title font */
982 
983 #define F_REMAP_FONT	'r'		/* remap font for 8-bit characters */
984 
985 #define F_EMPTY_CAL	'e'		/* print empty calendar */
986 #define F_DATE_FILE	'f'		/* select alternate date file */
987 #define F_OUT_FILE	'o'		/* select alternate output file */
988 
989 #define F_LANDSCAPE	'l'		/* landscape mode */
990 #define F_PORTRAIT	'p'		/* portrait mode */
991 
992 #define F_PAPERSIZE	'P'		/* paper size */
993 
994 #define F_HELP		'h'		/* generate full help message */
995 #define F_USAGE		'u'		/* generate parameter usage message */
996 #define F_VERSION	'v'		/* generate version ID */
997 
998 #define F_MOON_4	'm'		/* print new/quarter/full moons */
999 #define F_MOON_ALL	'M'		/* print all moons */
1000 
1001 #define F_DEFINE	'D'		/* define preprocessor symbol */
1002 #define F_UNDEF		'U'		/* undefine preprocessor symbol */
1003 
1004 #define F_L_FOOT	'L'		/* define left foot string */
1005 #define F_C_FOOT	'C'		/* define center foot string */
1006 #define F_R_FOOT	'R'		/* define right foot string */
1007 
1008 #define F_NOTES_HDR	'N'		/* define heading for notes box */
1009 
1010 #define F_FIRST_DAY	'F'		/* define alternate starting day */
1011 
1012 #define F_USA_DATES	'A'		/* parse American date format */
1013 #define F_EUR_DATES	'E'		/* parse European date format */
1014 
1015 #define F_X_TRANS	'X'		/* X-axis transformation */
1016 #define F_Y_TRANS	'Y'		/* Y-axis transformation */
1017 #define F_X_SCALE	'x'		/* X-axis scale factor */
1018 #define F_Y_SCALE	'y'		/* Y-axis scale factor */
1019 
1020 #define F_JULIAN	'j'		/* print Julian day (day of year) */
1021 #define F_JULIAN_ALL	'J'		/* print Julian day and days left */
1022 
1023 #define F_WHOLE_YEAR	'w'		/* print whole year per page */
1024 					/* (cf. W_WYFLAG below) */
1025 
1026 #define F_BLANK_BOXES	'B'		/* don't fill unused boxes */
1027 
1028 #define F_NUM_PAGES	'#'		/* print multiple copies of each page */
1029 
1030 #define F_SC_NONE	'S'		/* suppress small calendars */
1031 #define F_SC_FIRST	'k'		/* prev/next in first two boxes */
1032 #define F_SC_SPLIT	'K'		/* split between first and last boxes */
1033 
1034 #define F_SHADING	's'		/* define date/fill box shading */
1035 
1036 #define F_CALENDAR	'c'		/* generate "calendar" utility input */
1037 
1038 #define F_HTML		'H'		/* generate calendar in HTML */
1039 #define F_1COLUMN	'q'		/* print one column per month (HTML) */
1040 
1041 #define F_TIMEZONE	'z'		/* specify time zone for moon phase */
1042 
1043 #define F_SETLANG	'a'		/* set output lang for months/days */
1044 
1045 #define F_TYPEFACE	'T'		/* set fontstyle (Bold/Roman/Italic) */
1046 
1047 #define F_TITLEALIGN	'W'		/* set title alignment (left/center/right) */
1048 
1049 /* special "hidden" flag (and subflags) for debug info generation */
1050 
1051 #define F_DEBUG		'Z'		/* generate debugging information */
1052 
1053 #define D_DATES		'D'		/* debug dates as read */
1054 #define D_FILE_PATHS	'F'		/* debug date file paths */
1055 #define D_MOON		'M'		/* debug moon phases */
1056 #define D_TEXT		'T'		/* debug dates/text as written */
1057 #define D_OPT		'O'		/* debug option flags */
1058 #define D_PREPROCESSOR	'P'		/* debug "preprocessor" operation */
1059 
1060 
1061 
1062 
1063 /*
1064  * Words used in usage() message - translate as necessary
1065  */
1066 
1067 #define W_DEFAULT	"default"   /* translate as required */
1068 #define W_USAGE		"Usage"
1069 
1070 #define W_FONT_SIZE	"{<FONT>}{/<n>}"   /* names of metavariables */
1071 #define W_DAY		"<DAY>"
1072 #define W_DAY2		"<DAY>{-<DAY>}"
1073 #define W_STRING	"<STRING>"
1074 #define W_FILE		"<FILE>"
1075 #define W_SYMBOL	"<SYMBOL>"
1076 #define W_VALUE		"<VALUE>"
1077 #define W_LANG		"<LANG>"
1078 #define W_PAPERSIZE	"<PAPERSIZE>"
1079 #define W_TYPEFACE	"B|I|R"
1080 #define W_TITLEALIGN	"left|center|right"
1081 #define W_MAPPING	"<MAPPING>"
1082 #define W_N		"<n>"
1083 #define W_SHADING	"{<d>}{/<f>}"
1084 
1085 /* special flag_msg[] entries for end of option group, etc. */
1086 
1087 #define END_GROUP	'\n', NULL, NULL, NULL		/* end of option group */
1088 #define END_LIST	'\0', NULL, NULL, NULL		/* end of list */
1089 #define GROUP_DEFAULT	' ', NULL, " "			/* group default */
1090 
1091 
1092 
1093 
1094 
1095 /* Specify the number of entries from the 'param_msg[]' array to be printed in
1096    the 'pcal -h' output as part of the command-line syntax message... */
1097 #define PARAM_MSGS	3
1098 
1099 /* format strings for color_msg() - translate as necessary */
1100 #define COLOR_MSG_1	"all days in %s"
1101 #define COLOR_MSG_2	"in %s; others in %s"
1102 
1103 /* format string for short usage() message */
1104 #define USAGE_MSG	"\"%s -%c\" prints full description of flags, parameters, and file formats\n"
1105 
1106 /* font style special characters: \f[BIR] => " .[bir] " (cf. pcalutil.c) */
1107 #define BOLD		'B'		/* in calendar file (\fB[BIR]) */
1108 #define ITALIC		'I'
1109 #define ROMAN		'R'
1110 #define PREVFONT	'P'
1111 
1112 #define BOLD_FONT	".b"		/* in PostScript output */
1113 #define ITALIC_FONT	".i"
1114 #define ROMAN_FONT	".r"
1115 
1116 #define LINE_SEP	".p"		/* text line separator */
1117 
1118 /* strings used in error messages */
1119 #define ENV_VAR		"environment variable "
1120 #define DATE_FILE	"date file "
1121 
1122 /* Error and information messages - translate as necessary */
1123 
1124 /* program error messages */
1125 #define	E_ALLOC_ERR	"%s: calloc() failed - out of memory\n"
1126 #define	E_FOPEN_ERR	"%s: can't open file %s\n"
1127 #define	E_ILL_LINE	"%s: %s in file %s, line %d\n"
1128 #define	E_ILL_MONTH	"%s: month %d not in range %d .. %d\n"
1129 #define	E_ILL_OPT	"%s: unrecognized flag %s"
1130 #define E_ILL_OPT2	" (%s\"%s\")"
1131 #define	E_ILL_YEAR	"%s: year %d not in range %d .. %d\n"
1132 #define	E_SYMFULL	"%s: symbol table full - can't define %s\n"
1133 #define	E_UNT_IFDEF	"%s: unterminated if{n}def..{else..}endif in file %s\n"
1134 #define E_FLAG_IGNORED	"%s: -%c flag ignored (%s\"%s\")\n"
1135 #define	E_ILL_PAPERSIZE	"%s: unrecognized paper size '%s'\n"
1136 
1137 /* preprocessor error strings */
1138 #define E_ELSE_ERR	"unmatched \"else\""
1139 #define E_ELIF_ERR	"unmatched \"elif\""
1140 #define E_END_ERR	"unmatched \"endif\""
1141 #define E_GARBAGE	"extraneous data on \"%s\" line"
1142 #define E_INV_DATE	"invalid date"
1143 #define E_NO_MATCH	"no match for wildcard"
1144 #define E_INV_LINE	"unrecognized line"
1145 #define E_FILE_NESTING	"maximum file nesting level exceeded"
1146 #define E_IF_NESTING	"maximum \"if{n}def\" nesting level exceeded"
1147 #define E_EXPR_SYNTAX	"syntax error in expression"
1148 
1149 /* moon file error strings */
1150 #define E_DATE_SEQ	"date or phase out of sequence"
1151 #define E_PREM_EOF	"premature EOF"
1152 
1153 /* predefined macro names */
1154 #define DEF_WHOLE_YEAR	"whole_year"	/* defined when -w set */
1155 #define DEF_HTML	"html"		/* defined when -H set */
1156 #define DEF_LANG	"lang_"		/* lang_XX defined when -aXX set */
1157 
1158 
1159 
1160 /* ---------------------------------------------------------------------------
1161 
1162    Macro Definitions
1163 
1164 */
1165 
1166 /*
1167    Define a 'convenience' macro used to explicitly declare arguments as
1168    'unused' where intentionally-unused function parameters are declared.  This
1169    prevents warnings by the 'gcc' GNU C compiler that would otherwise appear
1170    because of using the '-W' compile option.
1171 
1172    The Unix and DOS+DJGPP build environments support this ability.  We assume
1173    that all other build environments do not support it, so this macro is
1174    defined as a null value in such cases.
1175  */
1176 #if defined (BUILD_ENV_UNIX) || defined (BUILD_ENV_DJGPP)
1177 #define GCC_UNUSED  __attribute__ ((unused))
1178 #else
1179 #define GCC_UNUSED
1180 #endif
1181 
1182 /* write character _c to file _fp; print as octal escape if _fc(_c) is FALSE */
1183 #define PUTCHAR(_fc, _c, _fp) \
1184    fprintf((_fp), (_c) == ' ' || _fc((_c) & CHAR_MSK) ? "%c" : "\\%03o" , (_c) & CHAR_MSK)
1185 
1186 #define PUTSTR(_fc, _s, _fp) \
1187    do { char *_p; for (_p = (_s); *_p; _p++) PUTCHAR(_fc, *_p, _fp); } while (0)
1188 
1189 #define IS_LEAP(y)   ((y) % 4 == 0 && ((y) % 100 != 0 || (y) % 400 == 0))
1190 #define LENGTH_OF(m, y) (month_len[(m)-1] + ((m) == FEB && IS_LEAP(y)))
1191 #define YEAR_LEN(y)   (IS_LEAP(y) ? 366 : 365)
1192 #define DAY_OF_YEAR(m, d, y) ((month_off[(m)-1] + ((m) > FEB && IS_LEAP(y))) + d)
1193 #define OFFSET_OF(m, y) ((month_off[(m)-1] + ((m) > FEB && IS_LEAP(y))) % 7)
1194 #define FIRST_OF(m, y)   calc_weekday(m, 1, y)
1195 #define START_BOX(m, y)   ((FIRST_OF(m, y) - first_day_of_week + 7) % 7)
1196 
1197 #define PREV_MONTH(m, y) ((m) == JAN ? DEC : (m) - 1)
1198 #define PREV_YEAR(m, y)  ((m) == JAN ? (y) - 1 : (y))
1199 #define NEXT_MONTH(m, y) ((m) == DEC ? JAN : (m) + 1)
1200 #define NEXT_YEAR(m, y)  ((m) == DEC ? (y) + 1 : (y))
1201 
1202 #define BUMP_MONTH_AND_YEAR(m, y) (((m) == DEC) ? (++(y), (m) = JAN) : (++(m)))
1203 
1204 #define INIT_COLORS   do { \
1205    memcpy(day_color, default_color, sizeof(day_color)); \
1206    holiday_color = HOLIDAY_COLOR; \
1207    weekday_color = WEEKDAY_COLOR; \
1208    } while (0)
1209 
1210 #define P_LASTCHAR(p)   ((p) && *(p) ? (p) + strlen(p) - 1 : NULL)
1211 #define LASTCHAR(p)   (p)[strlen(p) - 1]
1212 
1213 #define IS_NUMERIC(p)   ((p)[strspn((p), DIGITS)] == '\0')
1214 #define IS_EURDATE(p)   ((ispunct((int)(p)[strspn((p), DIGITS)])) && \
1215    ((p)[strspn((p), DIGITS)+1] == '\0'))
1216 #define IS_WILD(w)   ((w) >= WILD_FIRST && (w) <= WILD_LAST)
1217 
1218 #define MAKE_DATE(dt, m, d, y) \
1219    do { (dt).mm = m; (dt).dd = d; (dt).yy = y; } while (0)
1220 
1221 #define ERR(errmsg) \
1222    fprintf(stderr, E_ILL_LINE, progname, errmsg, filename, line);
1223 
1224 #define DEBUG(f)   ((debug_flags & f) != 0)
1225 
1226 #define ARRAYSIZE(a)   (sizeof(a)/sizeof(a[0]))
1227 
1228 #ifndef isodigit   /* rare */
1229 #define isodigit(c)   ((c) >= '0' && (c) <= '7')
1230 #endif
1231 #ifndef isxdigit   /* ANSI standard */
1232 #define isxdigit(c) \
1233    (isdigit(c) || ((c) >= 'a' && (c) <= 'f') || ((c) >= 'A' && (c) <= 'F'))
1234 #endif
1235 
1236 /* ---------------------------------------------------------------------------
1237 
1238    Data Declarations (including externals)
1239 
1240 */
1241 
1242 extern year_info *head;
1243 extern int curr_year;
1244 extern int init_month;
1245 extern int init_year;
1246 extern int nmonths;
1247 extern int final_month;
1248 extern int final_year;
1249 extern double xsval_pgm;
1250 extern double ysval_pgm;
1251 extern int xtval_pgm;
1252 extern int ytval_pgm;
1253 extern char *words[];
1254 extern char lbuf[];
1255 extern char progname[];
1256 extern char progpath[];
1257 extern char version[];
1258 
1259 extern char month_len[];
1260 extern short month_off[];
1261 
1262 extern int (*pdatefcn[])(int, int, int);
1263 
1264 extern char default_color[];
1265 extern char day_color[];
1266 extern int holiday_color;
1267 extern int weekday_color;
1268 
1269 extern int datefile_type;
1270 extern char datefile[];
1271 
1272 extern int rotate;
1273 
1274 extern int draw_moons;
1275 
1276 extern char datefont[];
1277 extern char titlefont[];
1278 extern char notesfont[];
1279 
1280 extern int mapfonts;
1281 
1282 extern char shading[];
1283 
1284 extern char lfoot[];
1285 extern char cfoot[];
1286 extern char rfoot[];
1287 
1288 extern char notes_hdr[];
1289 
1290 extern int first_day_of_week;
1291 
1292 extern int date_style;
1293 
1294 extern char outfile[];
1295 
1296 extern double xsval_user;
1297 extern double ysval_user;
1298 extern int xtval_user;
1299 extern int ytval_user;
1300 
1301 extern int julian_dates;
1302 
1303 extern int do_whole_year;
1304 
1305 extern int output_type;
1306 
1307 extern int one_column;
1308 
1309 extern int blank_boxes;
1310 
1311 extern int ncopy;
1312 
1313 extern int small_cal_pos;
1314 extern int prev_cal_box[];
1315 extern int next_cal_box[];
1316 
1317 extern char time_zone[];
1318 extern int tz_flag;
1319 
1320 extern char title_align[];
1321 
1322 extern int debug_flags;
1323 
1324 extern char *color_names[];
1325 extern char *days[];
1326 extern char *esp_accent;
1327 extern KWD_F pp_info[];
1328 extern KWD_H predef_events[];
1329 extern KWD preps[];
1330 extern KWD_O ordinals[];
1331 extern char *ord_suffix[];
1332 extern KWD keywds[];
1333 extern KWD phases[];
1334 extern char default_notes_hdr[];
1335 extern char fontstyle[];
1336 
1337 extern FLAG_USAGE flag_tbl[];
1338 extern DEBUG_INFO debug_info[];
1339 
1340 extern FLAG_MSG flag_msg[];
1341 extern PARAM_MSG param_msg[];
1342 
1343 extern paper_info_str_typ paper_info[];
1344 extern int paper_size;
1345 extern int page_dim_short_axis_pts, page_dim_long_axis_pts;
1346 extern int daybox_width_pts, daybox_height_pts;
1347 
1348 /* ---------------------------------------------------------------------------
1349 
1350    External Routine References & Function Prototypes
1351 
1352 */
1353