1#include <config.h> 2#include <stdlib.h> 3#include <string.h> 4#define YYBYACC 1 5#define YYMAJOR 1 6#define YYMINOR 9 7#define YYLEX yylex() 8#define YYEMPTY -1 9#define yyclearin (yychar=(YYEMPTY)) 10#define yyerrok (yyerrflag=0) 11#define YYRECOVERING() (yyerrflag!=0) 12#define YYPREFIX "yy" 13#line 2 "getdate.y" 14/* 15** Originally written by Steven M. Bellovin <smb@research.att.com> while 16** at the University of North Carolina at Chapel Hill. Later tweaked by 17** a couple of people on Usenet. Completely overhauled by Rich $alz 18** <rsalz@bbn.com> and Jim Berets <jberets@bbn.com> in August, 1990; 19** 20** This grammar has 10 shift/reduce conflicts. 21** 22** This code is in the public domain and has no copyright. 23*/ 24/* SUPPRESS 287 on yaccpar_sccsid *//* Unused static variable */ 25/* SUPPRESS 288 on yyerrlab *//* Label unused */ 26 27#include <config.h> 28 29#include <sys/types.h> 30#include <sys/time.h> 31#include <stdio.h> 32#ifdef STDC_HEADERS 33# include <stdlib.h> 34# include <stddef.h> 35#else 36# ifdef HAVE_STDLIB_H 37# include <stdlib.h> 38# endif 39#endif /* STDC_HEADERS */ 40#ifdef HAVE_STRING_H 41# if defined(HAVE_MEMORY_H) && !defined(STDC_HEADERS) 42# include <memory.h> 43# endif 44# include <string.h> 45#endif /* HAVE_STRING_H */ 46#ifdef HAVE_STRINGS_H 47# include <strings.h> 48#endif /* HAVE_STRINGS_H */ 49#if TIME_WITH_SYS_TIME 50# include <time.h> 51#endif 52#include <ctype.h> 53 54#include "missing.h" 55 56 57#define EPOCH 1970 58#define HOUR(x) ((time_t)(x) * 60) 59#define SECSPERDAY (24L * 60L * 60L) 60 61 62/* 63** An entry in the lexical lookup table. 64*/ 65typedef struct _TABLE { 66 char *name; 67 int type; 68 time_t value; 69} TABLE; 70 71 72/* 73** Daylight-savings mode: on, off, or not yet known. 74*/ 75typedef enum _DSTMODE { 76 DSTon, DSToff, DSTmaybe 77} DSTMODE; 78 79/* 80** Meridian: am, pm, or 24-hour style. 81*/ 82typedef enum _MERIDIAN { 83 MERam, MERpm, MER24 84} MERIDIAN; 85 86 87/* 88** Global variables. We could get rid of most of these by using a good 89** union as the yacc stack. (This routine was originally written before 90** yacc had the %union construct.) Maybe someday; right now we only use 91** the %union very rarely. 92*/ 93static char *yyInput; 94static DSTMODE yyDSTmode; 95static time_t yyDayOrdinal; 96static time_t yyDayNumber; 97static int yyHaveDate; 98static int yyHaveDay; 99static int yyHaveRel; 100static int yyHaveTime; 101static int yyHaveZone; 102static time_t yyTimezone; 103static time_t yyDay; 104static time_t yyHour; 105static time_t yyMinutes; 106static time_t yyMonth; 107static time_t yySeconds; 108static time_t yyYear; 109static MERIDIAN yyMeridian; 110static time_t yyRelMonth; 111static time_t yyRelSeconds; 112 113static int yyerror __P((char *s)); 114static int yylex __P((void)); 115 int yyparse __P((void)); 116 117#line 107 "getdate.y" 118#ifndef YYSTYPE_DEFINED 119#define YYSTYPE_DEFINED 120typedef union { 121 time_t Number; 122 enum _MERIDIAN Meridian; 123} YYSTYPE; 124#endif /* YYSTYPE_DEFINED */ 125#line 125 "y.tab.c" 126#define tAGO 257 127#define tDAY 258 128#define tDAYZONE 259 129#define tID 260 130#define tMERIDIAN 261 131#define tMINUTE_UNIT 262 132#define tMONTH 263 133#define tMONTH_UNIT 264 134#define tSEC_UNIT 265 135#define tSNUMBER 266 136#define tUNUMBER 267 137#define tZONE 268 138#define tDST 269 139#define YYERRCODE 256 140#if defined(__cplusplus) || defined(__STDC__) 141const short yylhs[] = 142#else 143short yylhs[] = 144#endif 145 { -1, 146 0, 0, 2, 2, 2, 2, 2, 2, 3, 3, 147 3, 3, 3, 4, 4, 4, 6, 6, 6, 5, 148 5, 5, 5, 5, 5, 5, 5, 7, 7, 9, 149 9, 9, 9, 9, 9, 9, 9, 9, 8, 1, 150 1, 151}; 152#if defined(__cplusplus) || defined(__STDC__) 153const short yylen[] = 154#else 155short yylen[] = 156#endif 157 { 2, 158 0, 2, 1, 1, 1, 1, 1, 1, 2, 4, 159 4, 6, 6, 1, 1, 2, 1, 2, 2, 3, 160 5, 3, 3, 2, 4, 2, 3, 2, 1, 2, 161 2, 1, 2, 2, 1, 2, 2, 1, 1, 0, 162 1, 163}; 164#if defined(__cplusplus) || defined(__STDC__) 165const short yydefred[] = 166#else 167short yydefred[] = 168#endif 169 { 1, 170 0, 0, 15, 32, 0, 38, 35, 0, 0, 0, 171 2, 3, 4, 5, 6, 7, 8, 0, 18, 0, 172 31, 36, 33, 19, 9, 30, 0, 37, 34, 0, 173 0, 0, 16, 28, 0, 23, 27, 22, 0, 0, 174 25, 41, 11, 0, 10, 0, 0, 21, 13, 12, 175}; 176#if defined(__cplusplus) || defined(__STDC__) 177const short yydgoto[] = 178#else 179short yydgoto[] = 180#endif 181 { 1, 182 45, 11, 12, 13, 14, 15, 16, 17, 18, 183}; 184#if defined(__cplusplus) || defined(__STDC__) 185const short yysindex[] = 186#else 187short yysindex[] = 188#endif 189 { 0, 190 -249, -38, 0, 0, -260, 0, 0, -240, -47, -248, 191 0, 0, 0, 0, 0, 0, 0, -237, 0, -18, 192 0, 0, 0, 0, 0, 0, -262, 0, 0, -239, 193 -238, -236, 0, 0, -235, 0, 0, 0, -56, -19, 194 0, 0, 0, -234, 0, -232, -258, 0, 0, 0,}; 195#if defined(__cplusplus) || defined(__STDC__) 196const short yyrindex[] = 197#else 198short yyrindex[] = 199#endif 200 { 0, 201 0, 1, 0, 0, 0, 0, 0, 0, 69, 12, 202 0, 0, 0, 0, 0, 0, 0, 23, 0, 34, 203 0, 0, 0, 0, 0, 0, 67, 0, 0, 0, 204 0, 0, 0, 0, 0, 0, 0, 0, 56, 45, 205 0, 0, 0, 0, 0, 0, 56, 0, 0, 0,}; 206#if defined(__cplusplus) || defined(__STDC__) 207const short yygindex[] = 208#else 209short yygindex[] = 210#endif 211 { 0, 212 -17, 0, 0, 0, 0, 0, 0, 0, 0, 213}; 214#define YYTABLESIZE 337 215#if defined(__cplusplus) || defined(__STDC__) 216const short yytable[] = 217#else 218short yytable[] = 219#endif 220 { 32, 221 17, 44, 42, 36, 37, 19, 20, 49, 2, 3, 222 31, 14, 4, 5, 6, 7, 8, 9, 10, 34, 223 33, 21, 29, 22, 23, 35, 38, 46, 39, 50, 224 40, 41, 47, 24, 48, 0, 0, 0, 0, 0, 225 0, 0, 0, 0, 20, 0, 0, 0, 0, 0, 226 0, 0, 0, 0, 0, 40, 0, 0, 0, 0, 227 0, 0, 0, 0, 0, 0, 26, 0, 39, 0, 228 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 229 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 230 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 231 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 232 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 233 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 234 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 235 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 236 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 237 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 238 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 239 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 240 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 241 0, 0, 0, 0, 42, 0, 0, 0, 0, 43, 242 24, 0, 0, 25, 26, 27, 28, 29, 30, 0, 243 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 244 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 245 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 246 0, 0, 0, 0, 0, 0, 0, 0, 17, 17, 247 0, 0, 17, 17, 17, 17, 17, 17, 17, 14, 248 14, 0, 0, 14, 14, 14, 14, 14, 14, 14, 249 29, 29, 0, 0, 29, 29, 29, 29, 29, 29, 250 29, 24, 24, 0, 0, 24, 24, 24, 24, 24, 251 24, 24, 20, 20, 0, 0, 20, 20, 20, 20, 252 20, 20, 20, 40, 40, 0, 0, 40, 40, 40, 253 40, 0, 40, 40, 26, 26, 0, 39, 26, 26, 254 26, 26, 0, 0, 26, 39, 39, 255}; 256#if defined(__cplusplus) || defined(__STDC__) 257const short yycheck[] = 258#else 259short yycheck[] = 260#endif 261 { 47, 262 0, 58, 261, 266, 267, 44, 267, 266, 258, 259, 263 58, 0, 262, 263, 264, 265, 266, 267, 268, 257, 264 269, 262, 0, 264, 265, 44, 266, 47, 267, 47, 265 267, 267, 267, 0, 267, -1, -1, -1, -1, -1, 266 -1, -1, -1, -1, 0, -1, -1, -1, -1, -1, 267 -1, -1, -1, -1, -1, 0, -1, -1, -1, -1, 268 -1, -1, -1, -1, -1, -1, 0, -1, 0, -1, 269 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 270 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 271 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 272 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 273 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 274 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 275 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 276 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 277 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 278 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 279 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 280 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 281 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 282 -1, -1, -1, -1, 261, -1, -1, -1, -1, 266, 283 258, -1, -1, 261, 262, 263, 264, 265, 266, -1, 284 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 285 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 286 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 287 -1, -1, -1, -1, -1, -1, -1, -1, 258, 259, 288 -1, -1, 262, 263, 264, 265, 266, 267, 268, 258, 289 259, -1, -1, 262, 263, 264, 265, 266, 267, 268, 290 258, 259, -1, -1, 262, 263, 264, 265, 266, 267, 291 268, 258, 259, -1, -1, 262, 263, 264, 265, 266, 292 267, 268, 258, 259, -1, -1, 262, 263, 264, 265, 293 266, 267, 268, 258, 259, -1, -1, 262, 263, 264, 294 265, -1, 267, 268, 258, 259, -1, 259, 262, 263, 295 264, 265, -1, -1, 268, 267, 268, 296}; 297#define YYFINAL 1 298#ifndef YYDEBUG 299#define YYDEBUG 0 300#endif 301#define YYMAXTOKEN 269 302#if YYDEBUG 303#if defined(__cplusplus) || defined(__STDC__) 304const char * const yyname[] = 305#else 306char *yyname[] = 307#endif 308 { 309"end-of-file",0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 3100,0,0,0,0,0,0,0,0,0,"','",0,0,"'/'",0,0,0,0,0,0,0,0,0,0,"':'",0,0,0,0,0,0,0,0,0, 3110,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 3120,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 3130,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 3140,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 3150,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,"tAGO","tDAY", 316"tDAYZONE","tID","tMERIDIAN","tMINUTE_UNIT","tMONTH","tMONTH_UNIT","tSEC_UNIT", 317"tSNUMBER","tUNUMBER","tZONE","tDST", 318}; 319#if defined(__cplusplus) || defined(__STDC__) 320const char * const yyrule[] = 321#else 322char *yyrule[] = 323#endif 324 {"$accept : spec", 325"spec :", 326"spec : spec item", 327"item : time", 328"item : zone", 329"item : date", 330"item : day", 331"item : rel", 332"item : number", 333"time : tUNUMBER tMERIDIAN", 334"time : tUNUMBER ':' tUNUMBER o_merid", 335"time : tUNUMBER ':' tUNUMBER tSNUMBER", 336"time : tUNUMBER ':' tUNUMBER ':' tUNUMBER o_merid", 337"time : tUNUMBER ':' tUNUMBER ':' tUNUMBER tSNUMBER", 338"zone : tZONE", 339"zone : tDAYZONE", 340"zone : tZONE tDST", 341"day : tDAY", 342"day : tDAY ','", 343"day : tUNUMBER tDAY", 344"date : tUNUMBER '/' tUNUMBER", 345"date : tUNUMBER '/' tUNUMBER '/' tUNUMBER", 346"date : tUNUMBER tSNUMBER tSNUMBER", 347"date : tUNUMBER tMONTH tSNUMBER", 348"date : tMONTH tUNUMBER", 349"date : tMONTH tUNUMBER ',' tUNUMBER", 350"date : tUNUMBER tMONTH", 351"date : tUNUMBER tMONTH tUNUMBER", 352"rel : relunit tAGO", 353"rel : relunit", 354"relunit : tUNUMBER tMINUTE_UNIT", 355"relunit : tSNUMBER tMINUTE_UNIT", 356"relunit : tMINUTE_UNIT", 357"relunit : tSNUMBER tSEC_UNIT", 358"relunit : tUNUMBER tSEC_UNIT", 359"relunit : tSEC_UNIT", 360"relunit : tSNUMBER tMONTH_UNIT", 361"relunit : tUNUMBER tMONTH_UNIT", 362"relunit : tMONTH_UNIT", 363"number : tUNUMBER", 364"o_merid :", 365"o_merid : tMERIDIAN", 366}; 367#endif 368#ifdef YYSTACKSIZE 369#undef YYMAXDEPTH 370#define YYMAXDEPTH YYSTACKSIZE 371#else 372#ifdef YYMAXDEPTH 373#define YYSTACKSIZE YYMAXDEPTH 374#else 375#define YYSTACKSIZE 10000 376#define YYMAXDEPTH 10000 377#endif 378#endif 379#define YYINITSTACKSIZE 200 380/* LINTUSED */ 381int yydebug; 382int yynerrs; 383int yyerrflag; 384int yychar; 385short *yyssp; 386YYSTYPE *yyvsp; 387YYSTYPE yyval; 388YYSTYPE yylval; 389short *yyss; 390short *yysslim; 391YYSTYPE *yyvs; 392int yystacksize; 393#line 326 "getdate.y" 394 395/* Month and day table. */ 396static TABLE const MonthDayTable[] = { 397 { "january", tMONTH, 1 }, 398 { "february", tMONTH, 2 }, 399 { "march", tMONTH, 3 }, 400 { "april", tMONTH, 4 }, 401 { "may", tMONTH, 5 }, 402 { "june", tMONTH, 6 }, 403 { "july", tMONTH, 7 }, 404 { "august", tMONTH, 8 }, 405 { "september", tMONTH, 9 }, 406 { "sept", tMONTH, 9 }, 407 { "october", tMONTH, 10 }, 408 { "november", tMONTH, 11 }, 409 { "december", tMONTH, 12 }, 410 { "sunday", tDAY, 0 }, 411 { "monday", tDAY, 1 }, 412 { "tuesday", tDAY, 2 }, 413 { "tues", tDAY, 2 }, 414 { "wednesday", tDAY, 3 }, 415 { "wednes", tDAY, 3 }, 416 { "thursday", tDAY, 4 }, 417 { "thur", tDAY, 4 }, 418 { "thurs", tDAY, 4 }, 419 { "friday", tDAY, 5 }, 420 { "saturday", tDAY, 6 }, 421 { NULL } 422}; 423 424/* Time units table. */ 425static TABLE const UnitsTable[] = { 426 { "year", tMONTH_UNIT, 12 }, 427 { "month", tMONTH_UNIT, 1 }, 428 { "fortnight", tMINUTE_UNIT, 14 * 24 * 60 }, 429 { "week", tMINUTE_UNIT, 7 * 24 * 60 }, 430 { "day", tMINUTE_UNIT, 1 * 24 * 60 }, 431 { "hour", tMINUTE_UNIT, 60 }, 432 { "minute", tMINUTE_UNIT, 1 }, 433 { "min", tMINUTE_UNIT, 1 }, 434 { "second", tSEC_UNIT, 1 }, 435 { "sec", tSEC_UNIT, 1 }, 436 { NULL } 437}; 438 439/* Assorted relative-time words. */ 440static TABLE const OtherTable[] = { 441 { "tomorrow", tMINUTE_UNIT, 1 * 24 * 60 }, 442 { "yesterday", tMINUTE_UNIT, -1 * 24 * 60 }, 443 { "today", tMINUTE_UNIT, 0 }, 444 { "now", tMINUTE_UNIT, 0 }, 445 { "last", tUNUMBER, -1 }, 446 { "this", tMINUTE_UNIT, 0 }, 447 { "next", tUNUMBER, 2 }, 448 { "first", tUNUMBER, 1 }, 449/* { "second", tUNUMBER, 2 }, */ 450 { "third", tUNUMBER, 3 }, 451 { "fourth", tUNUMBER, 4 }, 452 { "fifth", tUNUMBER, 5 }, 453 { "sixth", tUNUMBER, 6 }, 454 { "seventh", tUNUMBER, 7 }, 455 { "eighth", tUNUMBER, 8 }, 456 { "ninth", tUNUMBER, 9 }, 457 { "tenth", tUNUMBER, 10 }, 458 { "eleventh", tUNUMBER, 11 }, 459 { "twelfth", tUNUMBER, 12 }, 460 { "ago", tAGO, 1 }, 461 { NULL } 462}; 463 464/* The timezone table. */ 465/* Some of these are commented out because a time_t can't store a float. */ 466static TABLE const TimezoneTable[] = { 467 { "gmt", tZONE, HOUR( 0) }, /* Greenwich Mean */ 468 { "ut", tZONE, HOUR( 0) }, /* Universal (Coordinated) */ 469 { "utc", tZONE, HOUR( 0) }, 470 { "wet", tZONE, HOUR( 0) }, /* Western European */ 471 { "bst", tDAYZONE, HOUR( 0) }, /* British Summer */ 472 { "wat", tZONE, HOUR( 1) }, /* West Africa */ 473 { "at", tZONE, HOUR( 2) }, /* Azores */ 474#if 0 475 /* For completeness. BST is also British Summer, and GST is 476 * also Guam Standard. */ 477 { "bst", tZONE, HOUR( 3) }, /* Brazil Standard */ 478 { "gst", tZONE, HOUR( 3) }, /* Greenland Standard */ 479#endif 480#if 0 481 { "nft", tZONE, HOUR(3.5) }, /* Newfoundland */ 482 { "nst", tZONE, HOUR(3.5) }, /* Newfoundland Standard */ 483 { "ndt", tDAYZONE, HOUR(3.5) }, /* Newfoundland Daylight */ 484#endif 485 { "ast", tZONE, HOUR( 4) }, /* Atlantic Standard */ 486 { "adt", tDAYZONE, HOUR( 4) }, /* Atlantic Daylight */ 487 { "est", tZONE, HOUR( 5) }, /* Eastern Standard */ 488 { "edt", tDAYZONE, HOUR( 5) }, /* Eastern Daylight */ 489 { "cst", tZONE, HOUR( 6) }, /* Central Standard */ 490 { "cdt", tDAYZONE, HOUR( 6) }, /* Central Daylight */ 491 { "mst", tZONE, HOUR( 7) }, /* Mountain Standard */ 492 { "mdt", tDAYZONE, HOUR( 7) }, /* Mountain Daylight */ 493 { "pst", tZONE, HOUR( 8) }, /* Pacific Standard */ 494 { "pdt", tDAYZONE, HOUR( 8) }, /* Pacific Daylight */ 495 { "yst", tZONE, HOUR( 9) }, /* Yukon Standard */ 496 { "ydt", tDAYZONE, HOUR( 9) }, /* Yukon Daylight */ 497 { "hst", tZONE, HOUR(10) }, /* Hawaii Standard */ 498 { "hdt", tDAYZONE, HOUR(10) }, /* Hawaii Daylight */ 499 { "cat", tZONE, HOUR(10) }, /* Central Alaska */ 500 { "ahst", tZONE, HOUR(10) }, /* Alaska-Hawaii Standard */ 501 { "nt", tZONE, HOUR(11) }, /* Nome */ 502 { "idlw", tZONE, HOUR(12) }, /* International Date Line West */ 503 { "cet", tZONE, -HOUR(1) }, /* Central European */ 504 { "met", tZONE, -HOUR(1) }, /* Middle European */ 505 { "mewt", tZONE, -HOUR(1) }, /* Middle European Winter */ 506 { "mest", tDAYZONE, -HOUR(1) }, /* Middle European Summer */ 507 { "swt", tZONE, -HOUR(1) }, /* Swedish Winter */ 508 { "sst", tDAYZONE, -HOUR(1) }, /* Swedish Summer */ 509 { "fwt", tZONE, -HOUR(1) }, /* French Winter */ 510 { "fst", tDAYZONE, -HOUR(1) }, /* French Summer */ 511 { "eet", tZONE, -HOUR(2) }, /* Eastern Europe, USSR Zone 1 */ 512 { "bt", tZONE, -HOUR(3) }, /* Baghdad, USSR Zone 2 */ 513#if 0 514 { "it", tZONE, -HOUR(3.5) },/* Iran */ 515#endif 516 { "zp4", tZONE, -HOUR(4) }, /* USSR Zone 3 */ 517 { "zp5", tZONE, -HOUR(5) }, /* USSR Zone 4 */ 518#if 0 519 { "ist", tZONE, -HOUR(5.5) },/* Indian Standard */ 520#endif 521 { "zp6", tZONE, -HOUR(6) }, /* USSR Zone 5 */ 522#if 0 523 /* For completeness. NST is also Newfoundland Stanard, and SST is 524 * also Swedish Summer. */ 525 { "nst", tZONE, -HOUR(6.5) },/* North Sumatra */ 526 { "sst", tZONE, -HOUR(7) }, /* South Sumatra, USSR Zone 6 */ 527#endif /* 0 */ 528 { "wast", tZONE, -HOUR(7) }, /* West Australian Standard */ 529 { "wadt", tDAYZONE, -HOUR(7) }, /* West Australian Daylight */ 530#if 0 531 { "jt", tZONE, -HOUR(7.5) },/* Java (3pm in Cronusland!) */ 532#endif 533 { "cct", tZONE, -HOUR(8) }, /* China Coast, USSR Zone 7 */ 534 { "jst", tZONE, -HOUR(9) }, /* Japan Standard, USSR Zone 8 */ 535#if 0 536 { "cast", tZONE, -HOUR(9.5) },/* Central Australian Standard */ 537 { "cadt", tDAYZONE, -HOUR(9.5) },/* Central Australian Daylight */ 538#endif 539 { "east", tZONE, -HOUR(10) }, /* Eastern Australian Standard */ 540 { "eadt", tDAYZONE, -HOUR(10) }, /* Eastern Australian Daylight */ 541 { "gst", tZONE, -HOUR(10) }, /* Guam Standard, USSR Zone 9 */ 542 { "nzt", tZONE, -HOUR(12) }, /* New Zealand */ 543 { "nzst", tZONE, -HOUR(12) }, /* New Zealand Standard */ 544 { "nzdt", tDAYZONE, -HOUR(12) }, /* New Zealand Daylight */ 545 { "idle", tZONE, -HOUR(12) }, /* International Date Line East */ 546 { NULL } 547}; 548 549/* Military timezone table. */ 550static TABLE const MilitaryTable[] = { 551 { "a", tZONE, HOUR( 1) }, 552 { "b", tZONE, HOUR( 2) }, 553 { "c", tZONE, HOUR( 3) }, 554 { "d", tZONE, HOUR( 4) }, 555 { "e", tZONE, HOUR( 5) }, 556 { "f", tZONE, HOUR( 6) }, 557 { "g", tZONE, HOUR( 7) }, 558 { "h", tZONE, HOUR( 8) }, 559 { "i", tZONE, HOUR( 9) }, 560 { "k", tZONE, HOUR( 10) }, 561 { "l", tZONE, HOUR( 11) }, 562 { "m", tZONE, HOUR( 12) }, 563 { "n", tZONE, HOUR(- 1) }, 564 { "o", tZONE, HOUR(- 2) }, 565 { "p", tZONE, HOUR(- 3) }, 566 { "q", tZONE, HOUR(- 4) }, 567 { "r", tZONE, HOUR(- 5) }, 568 { "s", tZONE, HOUR(- 6) }, 569 { "t", tZONE, HOUR(- 7) }, 570 { "u", tZONE, HOUR(- 8) }, 571 { "v", tZONE, HOUR(- 9) }, 572 { "w", tZONE, HOUR(-10) }, 573 { "x", tZONE, HOUR(-11) }, 574 { "y", tZONE, HOUR(-12) }, 575 { "z", tZONE, HOUR( 0) }, 576 { NULL } 577}; 578 579 580 581 582/* ARGSUSED */ 583static int 584yyerror(s) 585 char *s; 586{ 587 return 0; 588} 589 590 591static time_t 592ToSeconds(Hours, Minutes, Seconds, Meridian) 593 time_t Hours; 594 time_t Minutes; 595 time_t Seconds; 596 MERIDIAN Meridian; 597{ 598 if (Minutes < 0 || Minutes > 59 || Seconds < 0 || Seconds > 59) 599 return -1; 600 switch (Meridian) { 601 case MER24: 602 if (Hours < 0 || Hours > 23) 603 return -1; 604 return (Hours * 60L + Minutes) * 60L + Seconds; 605 case MERam: 606 if (Hours < 1 || Hours > 12) 607 return -1; 608 if (Hours == 12) 609 Hours = 0; 610 return (Hours * 60L + Minutes) * 60L + Seconds; 611 case MERpm: 612 if (Hours < 1 || Hours > 12) 613 return -1; 614 if (Hours == 12) 615 Hours = 0; 616 return ((Hours + 12) * 60L + Minutes) * 60L + Seconds; 617 default: 618 abort (); 619 } 620 /* NOTREACHED */ 621} 622 623 624/* Year is either 625 * A negative number, which means to use its absolute value (why?) 626 * A number from 0 to 99, which means a year from 1900 to 1999, or 627 * The actual year (>=100). */ 628static time_t 629Convert(Month, Day, Year, Hours, Minutes, Seconds, Meridian, DSTmode) 630 time_t Month; 631 time_t Day; 632 time_t Year; 633 time_t Hours; 634 time_t Minutes; 635 time_t Seconds; 636 MERIDIAN Meridian; 637 DSTMODE DSTmode; 638{ 639 static int DaysInMonth[12] = { 640 31, 0, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 641 }; 642 time_t tod; 643 time_t Julian; 644 int i; 645 646 if (Year < 0) 647 Year = -Year; 648 if (Year < 69) 649 Year += 2000; 650 else if (Year < 100) { 651 Year += 1900; 652 if (Year < EPOCH) 653 Year += 100; 654 } 655 DaysInMonth[1] = Year % 4 == 0 && (Year % 100 != 0 || Year % 400 == 0) 656 ? 29 : 28; 657 /* Checking for 2038 bogusly assumes that time_t is 32 bits. But 658 I'm too lazy to try to check for time_t overflow in another way. */ 659 if (Year < EPOCH || Year > 2038 660 || Month < 1 || Month > 12 661 /* Lint fluff: "conversion from long may lose accuracy" */ 662 || Day < 1 || Day > DaysInMonth[(int)--Month]) 663 return -1; 664 665 for (Julian = Day - 1, i = 0; i < Month; i++) 666 Julian += DaysInMonth[i]; 667 for (i = EPOCH; i < Year; i++) 668 Julian += 365 + (i % 4 == 0); 669 Julian *= SECSPERDAY; 670 Julian += yyTimezone * 60L; 671 if ((tod = ToSeconds(Hours, Minutes, Seconds, Meridian)) < 0) 672 return -1; 673 Julian += tod; 674 if (DSTmode == DSTon 675 || (DSTmode == DSTmaybe && localtime(&Julian)->tm_isdst)) 676 Julian -= 60 * 60; 677 return Julian; 678} 679 680 681static time_t 682DSTcorrect(Start, Future) 683 time_t Start; 684 time_t Future; 685{ 686 time_t StartDay; 687 time_t FutureDay; 688 689 StartDay = (localtime(&Start)->tm_hour + 1) % 24; 690 FutureDay = (localtime(&Future)->tm_hour + 1) % 24; 691 return (Future - Start) + (StartDay - FutureDay) * 60L * 60L; 692} 693 694 695static time_t 696RelativeDate(Start, DayOrdinal, DayNumber) 697 time_t Start; 698 time_t DayOrdinal; 699 time_t DayNumber; 700{ 701 struct tm *tm; 702 time_t now; 703 704 now = Start; 705 tm = localtime(&now); 706 now += SECSPERDAY * ((DayNumber - tm->tm_wday + 7) % 7); 707 now += 7 * SECSPERDAY * (DayOrdinal <= 0 ? DayOrdinal : DayOrdinal - 1); 708 return DSTcorrect(Start, now); 709} 710 711 712static time_t 713RelativeMonth(Start, RelMonth) 714 time_t Start; 715 time_t RelMonth; 716{ 717 struct tm *tm; 718 time_t Month; 719 time_t Year; 720 721 if (RelMonth == 0) 722 return 0; 723 tm = localtime(&Start); 724 Month = 12 * (tm->tm_year + 1900) + tm->tm_mon + RelMonth; 725 Year = Month / 12; 726 Month = Month % 12 + 1; 727 return DSTcorrect(Start, 728 Convert(Month, (time_t)tm->tm_mday, Year, 729 (time_t)tm->tm_hour, (time_t)tm->tm_min, (time_t)tm->tm_sec, 730 MER24, DSTmaybe)); 731} 732 733 734static int 735LookupWord(buff) 736 char *buff; 737{ 738 char *p; 739 char *q; 740 const TABLE *tp; 741 int i; 742 int abbrev; 743 744 /* Make it lowercase. */ 745 for (p = buff; *p; p++) 746 if (isupper((unsigned char)*p)) 747 *p = tolower((unsigned char)*p); 748 749 if (strcmp(buff, "am") == 0 || strcmp(buff, "a.m.") == 0) { 750 yylval.Meridian = MERam; 751 return tMERIDIAN; 752 } 753 if (strcmp(buff, "pm") == 0 || strcmp(buff, "p.m.") == 0) { 754 yylval.Meridian = MERpm; 755 return tMERIDIAN; 756 } 757 758 /* See if we have an abbreviation for a month. */ 759 if (strlen(buff) == 3) 760 abbrev = 1; 761 else if (strlen(buff) == 4 && buff[3] == '.') { 762 abbrev = 1; 763 buff[3] = '\0'; 764 } 765 else 766 abbrev = 0; 767 768 for (tp = MonthDayTable; tp->name; tp++) { 769 if (abbrev) { 770 if (strncmp(buff, tp->name, 3) == 0) { 771 yylval.Number = tp->value; 772 return tp->type; 773 } 774 } 775 else if (strcmp(buff, tp->name) == 0) { 776 yylval.Number = tp->value; 777 return tp->type; 778 } 779 } 780 781 for (tp = TimezoneTable; tp->name; tp++) 782 if (strcmp(buff, tp->name) == 0) { 783 yylval.Number = tp->value; 784 return tp->type; 785 } 786 787 if (strcmp(buff, "dst") == 0) 788 return tDST; 789 790 for (tp = UnitsTable; tp->name; tp++) 791 if (strcmp(buff, tp->name) == 0) { 792 yylval.Number = tp->value; 793 return tp->type; 794 } 795 796 /* Strip off any plural and try the units table again. */ 797 i = strlen(buff) - 1; 798 if (buff[i] == 's') { 799 buff[i] = '\0'; 800 for (tp = UnitsTable; tp->name; tp++) 801 if (strcmp(buff, tp->name) == 0) { 802 yylval.Number = tp->value; 803 return tp->type; 804 } 805 buff[i] = 's'; /* Put back for "this" in OtherTable. */ 806 } 807 808 for (tp = OtherTable; tp->name; tp++) 809 if (strcmp(buff, tp->name) == 0) { 810 yylval.Number = tp->value; 811 return tp->type; 812 } 813 814 /* Military timezones. */ 815 if (buff[1] == '\0' && isalpha((unsigned char)*buff)) { 816 for (tp = MilitaryTable; tp->name; tp++) 817 if (strcmp(buff, tp->name) == 0) { 818 yylval.Number = tp->value; 819 return tp->type; 820 } 821 } 822 823 /* Drop out any periods and try the timezone table again. */ 824 for (i = 0, p = q = buff; *q; q++) 825 if (*q != '.') 826 *p++ = *q; 827 else 828 i++; 829 *p = '\0'; 830 if (i) 831 for (tp = TimezoneTable; tp->name; tp++) 832 if (strcmp(buff, tp->name) == 0) { 833 yylval.Number = tp->value; 834 return tp->type; 835 } 836 837 return tID; 838} 839 840 841static int 842yylex() 843{ 844 char c; 845 char *p; 846 char buff[20]; 847 int Count; 848 int sign; 849 850 for ( ; ; ) { 851 while (isspace((unsigned char)*yyInput)) 852 yyInput++; 853 854 if (isdigit((unsigned char)(c = *yyInput)) || c == '-' || c == '+') { 855 if (c == '-' || c == '+') { 856 sign = c == '-' ? -1 : 1; 857 if (!isdigit((unsigned char)*++yyInput)) 858 /* skip the '-' sign */ 859 continue; 860 } 861 else 862 sign = 0; 863 for (yylval.Number = 0; isdigit((unsigned char)(c = *yyInput++)); ) 864 yylval.Number = 10 * yylval.Number + c - '0'; 865 yyInput--; 866 if (sign < 0) 867 yylval.Number = -yylval.Number; 868 return sign ? tSNUMBER : tUNUMBER; 869 } 870 if (isalpha((unsigned char)c)) { 871 for (p = buff; isalpha((unsigned char)(c = *yyInput++)) || c == '.'; ) 872 if (p < &buff[sizeof buff - 1]) 873 *p++ = c; 874 *p = '\0'; 875 yyInput--; 876 return LookupWord(buff); 877 } 878 if (c != '(') 879 return *yyInput++; 880 Count = 0; 881 do { 882 c = *yyInput++; 883 if (c == '\0') 884 return c; 885 if (c == '(') 886 Count++; 887 else if (c == ')') 888 Count--; 889 } while (Count > 0); 890 } 891} 892 893#define TM_YEAR_ORIGIN 1900 894 895/* Yield A - B, measured in seconds. */ 896static long 897difftm (a, b) 898 struct tm *a, *b; 899{ 900 int ay = a->tm_year + (TM_YEAR_ORIGIN - 1); 901 int by = b->tm_year + (TM_YEAR_ORIGIN - 1); 902 int days = ( 903 /* difference in day of year */ 904 a->tm_yday - b->tm_yday 905 /* + intervening leap days */ 906 + ((ay >> 2) - (by >> 2)) 907 - (ay/100 - by/100) 908 + ((ay/100 >> 2) - (by/100 >> 2)) 909 /* + difference in years * 365 */ 910 + (long)(ay-by) * 365 911 ); 912 return (60*(60*(24*days + (a->tm_hour - b->tm_hour)) 913 + (a->tm_min - b->tm_min)) 914 + (a->tm_sec - b->tm_sec)); 915} 916 917time_t 918get_date(p) 919 char *p; 920{ 921 struct tm *tm, *gmt, gmtbuf; 922 time_t Start; 923 time_t tod; 924 time_t now; 925 time_t timezone; 926 927 yyInput = p; 928 (void)time (&now); 929 930 gmt = gmtime (&now); 931 if (gmt != NULL) 932 { 933 /* Make a copy, in case localtime modifies *tm (I think 934 that comment now applies to *gmt, but I am too 935 lazy to dig into how gmtime and locatime allocate the 936 structures they return pointers to). */ 937 gmtbuf = *gmt; 938 gmt = &gmtbuf; 939 } 940 941 if (! (tm = localtime (&now))) 942 return -1; 943 944 if (gmt != NULL) 945 timezone = difftm (gmt, tm) / 60; 946 else 947 /* We are on a system like VMS, where the system clock is 948 in local time and the system has no concept of timezones. 949 Hopefully we can fake this out (for the case in which the 950 user specifies no timezone) by just saying the timezone 951 is zero. */ 952 timezone = 0; 953 954 if(tm->tm_isdst) 955 timezone += 60; 956 957 tm = localtime(&now); 958 yyYear = tm->tm_year + 1900; 959 yyMonth = tm->tm_mon + 1; 960 yyDay = tm->tm_mday; 961 yyTimezone = timezone; 962 yyDSTmode = DSTmaybe; 963 yyHour = 0; 964 yyMinutes = 0; 965 yySeconds = 0; 966 yyMeridian = MER24; 967 yyRelSeconds = 0; 968 yyRelMonth = 0; 969 yyHaveDate = 0; 970 yyHaveDay = 0; 971 yyHaveRel = 0; 972 yyHaveTime = 0; 973 yyHaveZone = 0; 974 975 if (yyparse() 976 || yyHaveTime > 1 || yyHaveZone > 1 || yyHaveDate > 1 || yyHaveDay > 1) 977 return -1; 978 979 if (yyHaveDate || yyHaveTime || yyHaveDay) { 980 Start = Convert(yyMonth, yyDay, yyYear, yyHour, yyMinutes, yySeconds, 981 yyMeridian, yyDSTmode); 982 if (Start < 0) 983 return -1; 984 } 985 else { 986 Start = now; 987 if (!yyHaveRel) 988 Start -= ((tm->tm_hour * 60L + tm->tm_min) * 60L) + tm->tm_sec; 989 } 990 991 Start += yyRelSeconds; 992 Start += RelativeMonth(Start, yyRelMonth); 993 994 if (yyHaveDay && !yyHaveDate) { 995 tod = RelativeDate(Start, yyDayOrdinal, yyDayNumber); 996 Start += tod; 997 } 998 999 /* Have to do *something* with a legitimate -1 so it's distinguishable 1000 * from the error return value. (Alternately could set errno on error.) */ 1001 return Start == -1 ? 0 : Start; 1002} 1003 1004 1005#if defined(TEST) 1006 1007/* ARGSUSED */ 1008int 1009main(ac, av) 1010 int ac; 1011 char *av[]; 1012{ 1013 char buff[128]; 1014 time_t d; 1015 1016 (void)printf("Enter date, or blank line to exit.\n\t> "); 1017 (void)fflush(stdout); 1018 while (gets(buff) && buff[0]) { 1019 d = get_date(buff); 1020 if (d == -1) 1021 (void)printf("Bad format - couldn't convert.\n"); 1022 else 1023 (void)printf("%s", ctime(&d)); 1024 (void)printf("\t> "); 1025 (void)fflush(stdout); 1026 } 1027 exit(0); 1028 /* NOTREACHED */ 1029} 1030#endif /* defined(TEST) */ 1031#line 979 "y.tab.c" 1032/* allocate initial stack or double stack size, up to YYMAXDEPTH */ 1033#if defined(__cplusplus) || defined(__STDC__) 1034static int yygrowstack(void) 1035#else 1036static int yygrowstack() 1037#endif 1038{ 1039 int newsize, i; 1040 short *newss; 1041 YYSTYPE *newvs; 1042 1043 if ((newsize = yystacksize) == 0) 1044 newsize = YYINITSTACKSIZE; 1045 else if (newsize >= YYMAXDEPTH) 1046 return -1; 1047 else if ((newsize *= 2) > YYMAXDEPTH) 1048 newsize = YYMAXDEPTH; 1049#ifdef SIZE_MAX 1050#define YY_SIZE_MAX SIZE_MAX 1051#else 1052#define YY_SIZE_MAX 0x7fffffff 1053#endif 1054 if (YY_SIZE_MAX / newsize < sizeof *newss) 1055 goto bail; 1056 i = yyssp - yyss; 1057 newss = yyss ? (short *)realloc(yyss, newsize * sizeof *newss) : 1058 (short *)malloc(newsize * sizeof *newss); /* overflow check above */ 1059 if (newss == NULL) 1060 goto bail; 1061 yyss = newss; 1062 yyssp = newss + i; 1063 newvs = yyvs ? (YYSTYPE *)realloc(yyvs, newsize * sizeof *newvs) : 1064 (YYSTYPE *)malloc(newsize * sizeof *newvs); /* overflow check above */ 1065 if (newvs == NULL) 1066 goto bail; 1067 yyvs = newvs; 1068 yyvsp = newvs + i; 1069 yystacksize = newsize; 1070 yysslim = yyss + newsize - 1; 1071 return 0; 1072bail: 1073 if (yyss) 1074 free(yyss); 1075 if (yyvs) 1076 free(yyvs); 1077 yyss = yyssp = NULL; 1078 yyvs = yyvsp = NULL; 1079 yystacksize = 0; 1080 return -1; 1081} 1082 1083#define YYABORT goto yyabort 1084#define YYREJECT goto yyabort 1085#define YYACCEPT goto yyaccept 1086#define YYERROR goto yyerrlab 1087int 1088#if defined(__cplusplus) || defined(__STDC__) 1089yyparse(void) 1090#else 1091yyparse() 1092#endif 1093{ 1094 int yym, yyn, yystate; 1095#if YYDEBUG 1096#if defined(__cplusplus) || defined(__STDC__) 1097 const char *yys; 1098#else /* !(defined(__cplusplus) || defined(__STDC__)) */ 1099 char *yys; 1100#endif /* !(defined(__cplusplus) || defined(__STDC__)) */ 1101 1102 if ((yys = getenv("YYDEBUG"))) 1103 { 1104 yyn = *yys; 1105 if (yyn >= '0' && yyn <= '9') 1106 yydebug = yyn - '0'; 1107 } 1108#endif /* YYDEBUG */ 1109 1110 yynerrs = 0; 1111 yyerrflag = 0; 1112 yychar = (-1); 1113 1114 if (yyss == NULL && yygrowstack()) goto yyoverflow; 1115 yyssp = yyss; 1116 yyvsp = yyvs; 1117 *yyssp = yystate = 0; 1118 1119yyloop: 1120 if ((yyn = yydefred[yystate]) != 0) goto yyreduce; 1121 if (yychar < 0) 1122 { 1123 if ((yychar = yylex()) < 0) yychar = 0; 1124#if YYDEBUG 1125 if (yydebug) 1126 { 1127 yys = 0; 1128 if (yychar <= YYMAXTOKEN) yys = yyname[yychar]; 1129 if (!yys) yys = "illegal-symbol"; 1130 printf("%sdebug: state %d, reading %d (%s)\n", 1131 YYPREFIX, yystate, yychar, yys); 1132 } 1133#endif 1134 } 1135 if ((yyn = yysindex[yystate]) && (yyn += yychar) >= 0 && 1136 yyn <= YYTABLESIZE && yycheck[yyn] == yychar) 1137 { 1138#if YYDEBUG 1139 if (yydebug) 1140 printf("%sdebug: state %d, shifting to state %d\n", 1141 YYPREFIX, yystate, yytable[yyn]); 1142#endif 1143 if (yyssp >= yysslim && yygrowstack()) 1144 { 1145 goto yyoverflow; 1146 } 1147 *++yyssp = yystate = yytable[yyn]; 1148 *++yyvsp = yylval; 1149 yychar = (-1); 1150 if (yyerrflag > 0) --yyerrflag; 1151 goto yyloop; 1152 } 1153 if ((yyn = yyrindex[yystate]) && (yyn += yychar) >= 0 && 1154 yyn <= YYTABLESIZE && yycheck[yyn] == yychar) 1155 { 1156 yyn = yytable[yyn]; 1157 goto yyreduce; 1158 } 1159 if (yyerrflag) goto yyinrecovery; 1160#if defined(lint) || defined(__GNUC__) 1161 goto yynewerror; 1162#endif 1163yynewerror: 1164 yyerror("syntax error"); 1165#if defined(lint) || defined(__GNUC__) 1166 goto yyerrlab; 1167#endif 1168yyerrlab: 1169 ++yynerrs; 1170yyinrecovery: 1171 if (yyerrflag < 3) 1172 { 1173 yyerrflag = 3; 1174 for (;;) 1175 { 1176 if ((yyn = yysindex[*yyssp]) && (yyn += YYERRCODE) >= 0 && 1177 yyn <= YYTABLESIZE && yycheck[yyn] == YYERRCODE) 1178 { 1179#if YYDEBUG 1180 if (yydebug) 1181 printf("%sdebug: state %d, error recovery shifting\ 1182 to state %d\n", YYPREFIX, *yyssp, yytable[yyn]); 1183#endif 1184 if (yyssp >= yysslim && yygrowstack()) 1185 { 1186 goto yyoverflow; 1187 } 1188 *++yyssp = yystate = yytable[yyn]; 1189 *++yyvsp = yylval; 1190 goto yyloop; 1191 } 1192 else 1193 { 1194#if YYDEBUG 1195 if (yydebug) 1196 printf("%sdebug: error recovery discarding state %d\n", 1197 YYPREFIX, *yyssp); 1198#endif 1199 if (yyssp <= yyss) goto yyabort; 1200 --yyssp; 1201 --yyvsp; 1202 } 1203 } 1204 } 1205 else 1206 { 1207 if (yychar == 0) goto yyabort; 1208#if YYDEBUG 1209 if (yydebug) 1210 { 1211 yys = 0; 1212 if (yychar <= YYMAXTOKEN) yys = yyname[yychar]; 1213 if (!yys) yys = "illegal-symbol"; 1214 printf("%sdebug: state %d, error recovery discards token %d (%s)\n", 1215 YYPREFIX, yystate, yychar, yys); 1216 } 1217#endif 1218 yychar = (-1); 1219 goto yyloop; 1220 } 1221yyreduce: 1222#if YYDEBUG 1223 if (yydebug) 1224 printf("%sdebug: state %d, reducing by rule %d (%s)\n", 1225 YYPREFIX, yystate, yyn, yyrule[yyn]); 1226#endif 1227 yym = yylen[yyn]; 1228 if (yym) 1229 yyval = yyvsp[1-yym]; 1230 else 1231 memset(&yyval, 0, sizeof yyval); 1232 switch (yyn) 1233 { 1234case 3: 1235#line 125 "getdate.y" 1236{ 1237 yyHaveTime++; 1238 } 1239break; 1240case 4: 1241#line 128 "getdate.y" 1242{ 1243 yyHaveZone++; 1244 } 1245break; 1246case 5: 1247#line 131 "getdate.y" 1248{ 1249 yyHaveDate++; 1250 } 1251break; 1252case 6: 1253#line 134 "getdate.y" 1254{ 1255 yyHaveDay++; 1256 } 1257break; 1258case 7: 1259#line 137 "getdate.y" 1260{ 1261 yyHaveRel++; 1262 } 1263break; 1264case 9: 1265#line 143 "getdate.y" 1266{ 1267 yyHour = yyvsp[-1].Number; 1268 yyMinutes = 0; 1269 yySeconds = 0; 1270 yyMeridian = yyvsp[0].Meridian; 1271 } 1272break; 1273case 10: 1274#line 149 "getdate.y" 1275{ 1276 yyHour = yyvsp[-3].Number; 1277 yyMinutes = yyvsp[-1].Number; 1278 yySeconds = 0; 1279 yyMeridian = yyvsp[0].Meridian; 1280 } 1281break; 1282case 11: 1283#line 155 "getdate.y" 1284{ 1285 yyHour = yyvsp[-3].Number; 1286 yyMinutes = yyvsp[-1].Number; 1287 yyMeridian = MER24; 1288 yyDSTmode = DSToff; 1289 yyTimezone = - (yyvsp[0].Number % 100 + (yyvsp[0].Number / 100) * 60); 1290 } 1291break; 1292case 12: 1293#line 162 "getdate.y" 1294{ 1295 yyHour = yyvsp[-5].Number; 1296 yyMinutes = yyvsp[-3].Number; 1297 yySeconds = yyvsp[-1].Number; 1298 yyMeridian = yyvsp[0].Meridian; 1299 } 1300break; 1301case 13: 1302#line 168 "getdate.y" 1303{ 1304 yyHour = yyvsp[-5].Number; 1305 yyMinutes = yyvsp[-3].Number; 1306 yySeconds = yyvsp[-1].Number; 1307 yyMeridian = MER24; 1308 yyDSTmode = DSToff; 1309 yyTimezone = - (yyvsp[0].Number % 100 + (yyvsp[0].Number / 100) * 60); 1310 } 1311break; 1312case 14: 1313#line 178 "getdate.y" 1314{ 1315 yyTimezone = yyvsp[0].Number; 1316 yyDSTmode = DSToff; 1317 } 1318break; 1319case 15: 1320#line 182 "getdate.y" 1321{ 1322 yyTimezone = yyvsp[0].Number; 1323 yyDSTmode = DSTon; 1324 } 1325break; 1326case 16: 1327#line 187 "getdate.y" 1328{ 1329 yyTimezone = yyvsp[-1].Number; 1330 yyDSTmode = DSTon; 1331 } 1332break; 1333case 17: 1334#line 193 "getdate.y" 1335{ 1336 yyDayOrdinal = 1; 1337 yyDayNumber = yyvsp[0].Number; 1338 } 1339break; 1340case 18: 1341#line 197 "getdate.y" 1342{ 1343 yyDayOrdinal = 1; 1344 yyDayNumber = yyvsp[-1].Number; 1345 } 1346break; 1347case 19: 1348#line 201 "getdate.y" 1349{ 1350 yyDayOrdinal = yyvsp[-1].Number; 1351 yyDayNumber = yyvsp[0].Number; 1352 } 1353break; 1354case 20: 1355#line 207 "getdate.y" 1356{ 1357 yyMonth = yyvsp[-2].Number; 1358 yyDay = yyvsp[0].Number; 1359 } 1360break; 1361case 21: 1362#line 211 "getdate.y" 1363{ 1364 if (yyvsp[-4].Number >= 100) { 1365 yyYear = yyvsp[-4].Number; 1366 yyMonth = yyvsp[-2].Number; 1367 yyDay = yyvsp[0].Number; 1368 } else { 1369 yyMonth = yyvsp[-4].Number; 1370 yyDay = yyvsp[-2].Number; 1371 yyYear = yyvsp[0].Number; 1372 } 1373 } 1374break; 1375case 22: 1376#line 222 "getdate.y" 1377{ 1378 /* ISO 8601 format. yyyy-mm-dd. */ 1379 yyYear = yyvsp[-2].Number; 1380 yyMonth = -yyvsp[-1].Number; 1381 yyDay = -yyvsp[0].Number; 1382 } 1383break; 1384case 23: 1385#line 228 "getdate.y" 1386{ 1387 /* e.g. 17-JUN-1992. */ 1388 yyDay = yyvsp[-2].Number; 1389 yyMonth = yyvsp[-1].Number; 1390 yyYear = -yyvsp[0].Number; 1391 } 1392break; 1393case 24: 1394#line 234 "getdate.y" 1395{ 1396 yyMonth = yyvsp[-1].Number; 1397 yyDay = yyvsp[0].Number; 1398 } 1399break; 1400case 25: 1401#line 238 "getdate.y" 1402{ 1403 yyMonth = yyvsp[-3].Number; 1404 yyDay = yyvsp[-2].Number; 1405 yyYear = yyvsp[0].Number; 1406 } 1407break; 1408case 26: 1409#line 243 "getdate.y" 1410{ 1411 yyMonth = yyvsp[0].Number; 1412 yyDay = yyvsp[-1].Number; 1413 } 1414break; 1415case 27: 1416#line 247 "getdate.y" 1417{ 1418 yyMonth = yyvsp[-1].Number; 1419 yyDay = yyvsp[-2].Number; 1420 yyYear = yyvsp[0].Number; 1421 } 1422break; 1423case 28: 1424#line 254 "getdate.y" 1425{ 1426 yyRelSeconds = -yyRelSeconds; 1427 yyRelMonth = -yyRelMonth; 1428 } 1429break; 1430case 30: 1431#line 261 "getdate.y" 1432{ 1433 yyRelSeconds += yyvsp[-1].Number * yyvsp[0].Number * 60L; 1434 } 1435break; 1436case 31: 1437#line 264 "getdate.y" 1438{ 1439 yyRelSeconds += yyvsp[-1].Number * yyvsp[0].Number * 60L; 1440 } 1441break; 1442case 32: 1443#line 267 "getdate.y" 1444{ 1445 yyRelSeconds += yyvsp[0].Number * 60L; 1446 } 1447break; 1448case 33: 1449#line 270 "getdate.y" 1450{ 1451 yyRelSeconds += yyvsp[-1].Number; 1452 } 1453break; 1454case 34: 1455#line 273 "getdate.y" 1456{ 1457 yyRelSeconds += yyvsp[-1].Number; 1458 } 1459break; 1460case 35: 1461#line 276 "getdate.y" 1462{ 1463 yyRelSeconds++; 1464 } 1465break; 1466case 36: 1467#line 279 "getdate.y" 1468{ 1469 yyRelMonth += yyvsp[-1].Number * yyvsp[0].Number; 1470 } 1471break; 1472case 37: 1473#line 282 "getdate.y" 1474{ 1475 yyRelMonth += yyvsp[-1].Number * yyvsp[0].Number; 1476 } 1477break; 1478case 38: 1479#line 285 "getdate.y" 1480{ 1481 yyRelMonth += yyvsp[0].Number; 1482 } 1483break; 1484case 39: 1485#line 290 "getdate.y" 1486{ 1487 if (yyHaveTime && yyHaveDate && !yyHaveRel) 1488 yyYear = yyvsp[0].Number; 1489 else { 1490 if(yyvsp[0].Number>10000) { 1491 yyHaveDate++; 1492 yyDay= (yyvsp[0].Number)%100; 1493 yyMonth= (yyvsp[0].Number/100)%100; 1494 yyYear = yyvsp[0].Number/10000; 1495 } 1496 else { 1497 yyHaveTime++; 1498 if (yyvsp[0].Number < 100) { 1499 yyHour = yyvsp[0].Number; 1500 yyMinutes = 0; 1501 } 1502 else { 1503 yyHour = yyvsp[0].Number / 100; 1504 yyMinutes = yyvsp[0].Number % 100; 1505 } 1506 yySeconds = 0; 1507 yyMeridian = MER24; 1508 } 1509 } 1510 } 1511break; 1512case 40: 1513#line 317 "getdate.y" 1514{ 1515 yyval.Meridian = MER24; 1516 } 1517break; 1518case 41: 1519#line 320 "getdate.y" 1520{ 1521 yyval.Meridian = yyvsp[0].Meridian; 1522 } 1523break; 1524#line 1472 "y.tab.c" 1525 } 1526 yyssp -= yym; 1527 yystate = *yyssp; 1528 yyvsp -= yym; 1529 yym = yylhs[yyn]; 1530 if (yystate == 0 && yym == 0) 1531 { 1532#if YYDEBUG 1533 if (yydebug) 1534 printf("%sdebug: after reduction, shifting from state 0 to\ 1535 state %d\n", YYPREFIX, YYFINAL); 1536#endif 1537 yystate = YYFINAL; 1538 *++yyssp = YYFINAL; 1539 *++yyvsp = yyval; 1540 if (yychar < 0) 1541 { 1542 if ((yychar = yylex()) < 0) yychar = 0; 1543#if YYDEBUG 1544 if (yydebug) 1545 { 1546 yys = 0; 1547 if (yychar <= YYMAXTOKEN) yys = yyname[yychar]; 1548 if (!yys) yys = "illegal-symbol"; 1549 printf("%sdebug: state %d, reading %d (%s)\n", 1550 YYPREFIX, YYFINAL, yychar, yys); 1551 } 1552#endif 1553 } 1554 if (yychar == 0) goto yyaccept; 1555 goto yyloop; 1556 } 1557 if ((yyn = yygindex[yym]) && (yyn += yystate) >= 0 && 1558 yyn <= YYTABLESIZE && yycheck[yyn] == yystate) 1559 yystate = yytable[yyn]; 1560 else 1561 yystate = yydgoto[yym]; 1562#if YYDEBUG 1563 if (yydebug) 1564 printf("%sdebug: after reduction, shifting from state %d \ 1565to state %d\n", YYPREFIX, *yyssp, yystate); 1566#endif 1567 if (yyssp >= yysslim && yygrowstack()) 1568 { 1569 goto yyoverflow; 1570 } 1571 *++yyssp = yystate; 1572 *++yyvsp = yyval; 1573 goto yyloop; 1574yyoverflow: 1575 yyerror("yacc stack overflow"); 1576yyabort: 1577 if (yyss) 1578 free(yyss); 1579 if (yyvs) 1580 free(yyvs); 1581 yyss = yyssp = NULL; 1582 yyvs = yyvsp = NULL; 1583 yystacksize = 0; 1584 return (1); 1585yyaccept: 1586 if (yyss) 1587 free(yyss); 1588 if (yyvs) 1589 free(yyvs); 1590 yyss = yyssp = NULL; 1591 yyvs = yyvsp = NULL; 1592 yystacksize = 0; 1593 return (0); 1594} 1595