Home | History | Annotate | Line # | Download | only in time
localtime.c revision 1.133
      1 /*	$NetBSD: localtime.c,v 1.133 2022/03/25 19:34:04 rillig Exp $	*/
      2 
      3 /* Convert timestamp from time_t to struct tm.  */
      4 
      5 /*
      6 ** This file is in the public domain, so clarified as of
      7 ** 1996-06-05 by Arthur David Olson.
      8 */
      9 
     10 #include <sys/cdefs.h>
     11 #if defined(LIBC_SCCS) && !defined(lint)
     12 #if 0
     13 static char	elsieid[] = "@(#)localtime.c	8.17";
     14 #else
     15 __RCSID("$NetBSD: localtime.c,v 1.133 2022/03/25 19:34:04 rillig Exp $");
     16 #endif
     17 #endif /* LIBC_SCCS and not lint */
     18 
     19 /*
     20 ** Leap second handling from Bradley White.
     21 ** POSIX-style TZ environment variable handling from Guy Harris.
     22 */
     23 
     24 /*LINTLIBRARY*/
     25 
     26 #include "namespace.h"
     27 #include <assert.h>
     28 #define LOCALTIME_IMPLEMENTATION
     29 #include "private.h"
     30 
     31 #include "tzfile.h"
     32 #include <fcntl.h>
     33 
     34 #if defined(__weak_alias)
     35 __weak_alias(daylight,_daylight)
     36 __weak_alias(tzname,_tzname)
     37 #endif
     38 
     39 #ifndef TZ_ABBR_MAX_LEN
     40 #define TZ_ABBR_MAX_LEN	16
     41 #endif /* !defined TZ_ABBR_MAX_LEN */
     42 
     43 #ifndef TZ_ABBR_CHAR_SET
     44 #define TZ_ABBR_CHAR_SET \
     45 	"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789 :+-._"
     46 #endif /* !defined TZ_ABBR_CHAR_SET */
     47 
     48 #ifndef TZ_ABBR_ERR_CHAR
     49 #define TZ_ABBR_ERR_CHAR	'_'
     50 #endif /* !defined TZ_ABBR_ERR_CHAR */
     51 
     52 /*
     53 ** SunOS 4.1.1 headers lack O_BINARY.
     54 */
     55 
     56 #ifdef O_BINARY
     57 #define OPEN_MODE	(O_RDONLY | O_BINARY | O_CLOEXEC)
     58 #endif /* defined O_BINARY */
     59 #ifndef O_BINARY
     60 #define OPEN_MODE	(O_RDONLY | O_CLOEXEC)
     61 #endif /* !defined O_BINARY */
     62 
     63 #ifndef WILDABBR
     64 /*
     65 ** Someone might make incorrect use of a time zone abbreviation:
     66 **	1.	They might reference tzname[0] before calling tzset (explicitly
     67 **		or implicitly).
     68 **	2.	They might reference tzname[1] before calling tzset (explicitly
     69 **		or implicitly).
     70 **	3.	They might reference tzname[1] after setting to a time zone
     71 **		in which Daylight Saving Time is never observed.
     72 **	4.	They might reference tzname[0] after setting to a time zone
     73 **		in which Standard Time is never observed.
     74 **	5.	They might reference tm.TM_ZONE after calling offtime.
     75 ** What's best to do in the above cases is open to debate;
     76 ** for now, we just set things up so that in any of the five cases
     77 ** WILDABBR is used. Another possibility: initialize tzname[0] to the
     78 ** string "tzname[0] used before set", and similarly for the other cases.
     79 ** And another: initialize tzname[0] to "ERA", with an explanation in the
     80 ** manual page of what this "time zone abbreviation" means (doing this so
     81 ** that tzname[0] has the "normal" length of three characters).
     82 */
     83 #define WILDABBR	"   "
     84 #endif /* !defined WILDABBR */
     85 
     86 static const char	wildabbr[] = WILDABBR;
     87 
     88 static const char	gmt[] = "GMT";
     89 
     90 /*
     91 ** The DST rules to use if TZ has no rules and we can't load TZDEFRULES.
     92 ** Default to US rules as of 2017-05-07.
     93 ** POSIX does not specify the default DST rules;
     94 ** for historical reasons, US rules are a common default.
     95 */
     96 #ifndef TZDEFRULESTRING
     97 #define TZDEFRULESTRING ",M3.2.0,M11.1.0"
     98 #endif
     99 
    100 typedef int_fast64_t __time_t;
    101 
    102 struct ttinfo {				/* time type information */
    103 	int_fast32_t	tt_utoff;	/* UT offset in seconds */
    104 	bool		tt_isdst;	/* used to set tm_isdst */
    105 	int		tt_desigidx;	/* abbreviation list index */
    106 	bool		tt_ttisstd;	/* transition is std time */
    107 	bool		tt_ttisut;	/* transition is UT */
    108 };
    109 
    110 struct lsinfo {				/* leap second information */
    111 	__time_t	ls_trans;	/* transition time */
    112 	int_fast32_t	ls_corr;	/* correction to apply */
    113 };
    114 
    115 #define SMALLEST(a, b)	(((a) < (b)) ? (a) : (b))
    116 #define BIGGEST(a, b)	(((a) > (b)) ? (a) : (b))
    117 
    118 /* This abbreviation means local time is unspecified.  */
    119 static char const UNSPEC[] = "-00";
    120 
    121 /* How many extra bytes are needed at the end of struct state's chars array.
    122    This needs to be at least 1 for null termination in case the input
    123    data isn't properly terminated, and it also needs to be big enough
    124    for ttunspecified to work without crashing.  */
    125 enum { CHARS_EXTRA = BIGGEST(sizeof UNSPEC, 2) - 1 };
    126 
    127 #ifdef TZNAME_MAX
    128 #define MY_TZNAME_MAX	TZNAME_MAX
    129 #endif /* defined TZNAME_MAX */
    130 #ifndef TZNAME_MAX
    131 #define MY_TZNAME_MAX	255
    132 #endif /* !defined TZNAME_MAX */
    133 
    134 #define state __state
    135 struct state {
    136 	int		leapcnt;
    137 	int		timecnt;
    138 	int		typecnt;
    139 	int		charcnt;
    140 	bool		goback;
    141 	bool		goahead;
    142 	__time_t	ats[TZ_MAX_TIMES];
    143 	unsigned char	types[TZ_MAX_TIMES];
    144 	struct ttinfo	ttis[TZ_MAX_TYPES];
    145 	char		chars[/*CONSTCOND*/
    146 			    BIGGEST(BIGGEST(TZ_MAX_CHARS + CHARS_EXTRA,
    147 			    sizeof gmt), (2 * (MY_TZNAME_MAX + 1)))];
    148 	struct lsinfo	lsis[TZ_MAX_LEAPS];
    149 
    150 	/* The time type to use for early times or if no transitions.
    151 	   It is always zero for recent tzdb releases.
    152 	   It might be nonzero for data from tzdb 2018e or earlier.  */
    153 	int defaulttype;
    154 };
    155 
    156 enum r_type {
    157   JULIAN_DAY,		/* Jn = Julian day */
    158   DAY_OF_YEAR,		/* n = day of year */
    159   MONTH_NTH_DAY_OF_WEEK	/* Mm.n.d = month, week, day of week */
    160 };
    161 
    162 struct rule {
    163 	enum r_type	r_type;		/* type of rule */
    164 	int		r_day;		/* day number of rule */
    165 	int		r_week;		/* week number of rule */
    166 	int		r_mon;		/* month number of rule */
    167 	int_fast32_t	r_time;		/* transition time of rule */
    168 };
    169 
    170 static struct tm *gmtsub(struct state const *, time_t const *, int_fast32_t,
    171 			 struct tm *);
    172 static bool increment_overflow(int *, int);
    173 static bool increment_overflow_time(__time_t *, int_fast32_t);
    174 static int_fast32_t leapcorr(struct state const *, time_t);
    175 static bool normalize_overflow32(int_fast32_t *, int *, int);
    176 static struct tm *timesub(time_t const *, int_fast32_t, struct state const *,
    177 			  struct tm *);
    178 static bool typesequiv(struct state const *, int, int);
    179 static bool tzparse(char const *, struct state *, struct state *);
    180 
    181 static timezone_t gmtptr;
    182 
    183 #ifndef TZ_STRLEN_MAX
    184 #define TZ_STRLEN_MAX 255
    185 #endif /* !defined TZ_STRLEN_MAX */
    186 
    187 static char		lcl_TZname[TZ_STRLEN_MAX + 1];
    188 static int		lcl_is_set;
    189 
    190 
    191 #if !defined(__LIBC12_SOURCE__)
    192 timezone_t __lclptr;
    193 #ifdef _REENTRANT
    194 rwlock_t __lcl_lock = RWLOCK_INITIALIZER;
    195 #endif
    196 #endif
    197 
    198 /*
    199 ** Section 4.12.3 of X3.159-1989 requires that
    200 **	Except for the strftime function, these functions [asctime,
    201 **	ctime, gmtime, localtime] return values in one of two static
    202 **	objects: a broken-down time structure and an array of char.
    203 ** Thanks to Paul Eggert for noting this.
    204 */
    205 
    206 static struct tm	tm;
    207 
    208 #if 2 <= HAVE_TZNAME + TZ_TIME_T || defined(__NetBSD__)
    209 # if !defined(__LIBC12_SOURCE__)
    210 
    211 __aconst char *		tzname[2] = {
    212 	(__aconst char *)__UNCONST(wildabbr),
    213 	(__aconst char *)__UNCONST(wildabbr)
    214 };
    215 
    216 # else
    217 
    218 extern __aconst char *	tzname[2];
    219 
    220 # endif /* __LIBC12_SOURCE__ */
    221 #endif
    222 
    223 #if 2 <= USG_COMPAT + TZ_TIME_T || defined(__NetBSD__)
    224 # if !defined(__LIBC12_SOURCE__)
    225 long 			timezone = 0;
    226 int			daylight = 0;
    227 # else
    228 extern int		daylight;
    229 extern long		timezone __RENAME(__timezone13);
    230 # endif /* __LIBC12_SOURCE__ */
    231 #endif /* 2<= USG_COMPAT + TZ_TIME_T */
    232 
    233 #if 2 <= ALTZONE + TZ_TIME_T
    234 long			altzone = 0;
    235 #endif /* 2 <= ALTZONE + TZ_TIME_T */
    236 
    237 /* Initialize *S to a value based on UTOFF, ISDST, and DESIGIDX.  */
    238 static void
    239 init_ttinfo(struct ttinfo *s, int_fast32_t utoff, bool isdst, int desigidx)
    240 {
    241   s->tt_utoff = utoff;
    242   s->tt_isdst = isdst;
    243   s->tt_desigidx = desigidx;
    244   s->tt_ttisstd = false;
    245   s->tt_ttisut = false;
    246 }
    247 
    248 /* Return true if SP's time type I does not specify local time.  */
    249 static bool
    250 ttunspecified(struct state const *sp, int i)
    251 {
    252   char const *abbr = &sp->chars[sp->ttis[i].tt_desigidx];
    253   /* memcmp is likely faster than strcmp, and is safe due to CHARS_EXTRA.  */
    254   return memcmp(abbr, UNSPEC, sizeof UNSPEC) == 0;
    255 }
    256 
    257 static int_fast32_t
    258 detzcode(const char *const codep)
    259 {
    260 	register int_fast32_t	result;
    261 	register int		i;
    262 	int_fast32_t one = 1;
    263 	int_fast32_t halfmaxval = one << (32 - 2);
    264 	int_fast32_t maxval = halfmaxval - 1 + halfmaxval;
    265 	int_fast32_t minval = -1 - maxval;
    266 
    267 	result = codep[0] & 0x7f;
    268 	for (i = 1; i < 4; ++i)
    269 		result = (result << 8) | (codep[i] & 0xff);
    270 
    271 	if (codep[0] & 0x80) {
    272 	  /* Do two's-complement negation even on non-two's-complement machines.
    273 	     If the result would be minval - 1, return minval.  */
    274 	  result -= !TWOS_COMPLEMENT(int_fast32_t) && result != 0;
    275 	  result += minval;
    276 	}
    277 	return result;
    278 }
    279 
    280 static int_fast64_t
    281 detzcode64(const char *const codep)
    282 {
    283 	register int_fast64_t result;
    284 	register int	i;
    285 	int_fast64_t one = 1;
    286 	int_fast64_t halfmaxval = one << (64 - 2);
    287 	int_fast64_t maxval = halfmaxval - 1 + halfmaxval;
    288 	int_fast64_t minval = -TWOS_COMPLEMENT(int_fast64_t) - maxval;
    289 
    290 	result = codep[0] & 0x7f;
    291 	for (i = 1; i < 8; ++i)
    292 		result = (result << 8) | (codep[i] & 0xff);
    293 
    294 	if (codep[0] & 0x80) {
    295 	  /* Do two's-complement negation even on non-two's-complement machines.
    296 	     If the result would be minval - 1, return minval.  */
    297 	  result -= !TWOS_COMPLEMENT(int_fast64_t) && result != 0;
    298 	  result += minval;
    299 	}
    300 	return result;
    301 }
    302 
    303 #include <stdio.h>
    304 
    305 const char *
    306 tzgetname(const timezone_t sp, int isdst)
    307 {
    308 	int i;
    309 	const char *name = NULL;
    310 	for (i = 0; i < sp->typecnt; ++i) {
    311 		const struct ttinfo *const ttisp = &sp->ttis[i];
    312 		if (ttisp->tt_isdst == isdst)
    313 			name = &sp->chars[ttisp->tt_desigidx];
    314 	}
    315 	if (name != NULL)
    316 		return name;
    317 	errno = ESRCH;
    318 	return NULL;
    319 }
    320 
    321 long
    322 tzgetgmtoff(const timezone_t sp, int isdst)
    323 {
    324 	int i;
    325 	long l = -1;
    326 	for (i = 0; i < sp->typecnt; ++i) {
    327 		const struct ttinfo *const ttisp = &sp->ttis[i];
    328 
    329 		if (ttisp->tt_isdst == isdst) {
    330 			l = ttisp->tt_utoff;
    331 		}
    332 	}
    333 	if (l == -1)
    334 		errno = ESRCH;
    335 	return l;
    336 }
    337 
    338 static void
    339 update_tzname_etc(struct state const *sp, struct ttinfo const *ttisp)
    340 {
    341 #if HAVE_TZNAME
    342   tzname[ttisp->tt_isdst] = __UNCONST(&sp->chars[ttisp->tt_desigidx]);
    343 #endif
    344 #if USG_COMPAT
    345   if (!ttisp->tt_isdst)
    346     timezone = - ttisp->tt_utoff;
    347 #endif
    348 #if ALTZONE
    349   if (ttisp->tt_isdst)
    350     altzone = - ttisp->tt_utoff;
    351 #endif
    352 }
    353 
    354 static void
    355 settzname(void)
    356 {
    357 	register timezone_t const	sp = __lclptr;
    358 	register int			i;
    359 
    360 #if HAVE_TZNAME
    361 	tzname[0] = tzname[1] =
    362 	    (__aconst char *) __UNCONST(sp ? wildabbr : gmt);
    363 #endif
    364 #if USG_COMPAT
    365 	daylight = 0;
    366 	timezone = 0;
    367 #endif
    368 #if ALTZONE
    369 	altzone = 0;
    370 #endif
    371 	if (sp == NULL) {
    372 		return;
    373 	}
    374 	/*
    375 	** And to get the latest time zone abbreviations into tzname. . .
    376 	*/
    377 	for (i = 0; i < sp->typecnt; ++i)
    378 		update_tzname_etc(sp, &sp->ttis[i]);
    379 
    380 	for (i = 0; i < sp->timecnt; ++i) {
    381 		register const struct ttinfo * const	ttisp =
    382 							&sp->ttis[
    383 								sp->types[i]];
    384 		update_tzname_etc(sp, ttisp);
    385 #if USG_COMPAT
    386 		if (ttisp->tt_isdst)
    387 			daylight = 1;
    388 #endif
    389 	}
    390 }
    391 
    392 static void
    393 scrub_abbrs(struct state *sp)
    394 {
    395 	int i;
    396 	/*
    397 	** First, replace bogus characters.
    398 	*/
    399 	for (i = 0; i < sp->charcnt; ++i)
    400 		if (strchr(TZ_ABBR_CHAR_SET, sp->chars[i]) == NULL)
    401 			sp->chars[i] = TZ_ABBR_ERR_CHAR;
    402 	/*
    403 	** Second, truncate long abbreviations.
    404 	*/
    405 	for (i = 0; i < sp->typecnt; ++i) {
    406 		register const struct ttinfo * const	ttisp = &sp->ttis[i];
    407 		char *cp = &sp->chars[ttisp->tt_desigidx];
    408 
    409 		if (strlen(cp) > TZ_ABBR_MAX_LEN &&
    410 			strcmp(cp, GRANDPARENTED) != 0)
    411 				*(cp + TZ_ABBR_MAX_LEN) = '\0';
    412 	}
    413 }
    414 
    415 /* Input buffer for data read from a compiled tz file.  */
    416 union input_buffer {
    417   /* The first part of the buffer, interpreted as a header.  */
    418   struct tzhead tzhead;
    419 
    420   /* The entire buffer.  */
    421   char buf[2 * sizeof(struct tzhead) + 2 * sizeof(struct state)
    422 	   + 4 * TZ_MAX_TIMES];
    423 };
    424 
    425 /* TZDIR with a trailing '/' rather than a trailing '\0'.  */
    426 static char const tzdirslash[sizeof TZDIR] = TZDIR "/";
    427 
    428 /* Local storage needed for 'tzloadbody'.  */
    429 union local_storage {
    430   /* The results of analyzing the file's contents after it is opened.  */
    431   struct file_analysis {
    432     /* The input buffer.  */
    433     union input_buffer u;
    434 
    435     /* A temporary state used for parsing a TZ string in the file.  */
    436     struct state st;
    437   } u;
    438 
    439   /* The file name to be opened.  */
    440   char fullname[/*CONSTCOND*/BIGGEST(sizeof(struct file_analysis),
    441 			sizeof tzdirslash + 1024)];
    442 };
    443 
    444 /* Load tz data from the file named NAME into *SP.  Read extended
    445    format if DOEXTEND.  Use *LSP for temporary storage.  Return 0 on
    446    success, an errno value on failure.  */
    447 static int
    448 tzloadbody(char const *name, struct state *sp, bool doextend,
    449 	   union local_storage *lsp)
    450 {
    451 	register int			i;
    452 	register int			fid;
    453 	register int			stored;
    454 	register ssize_t		nread;
    455 	register bool doaccess;
    456 	register union input_buffer *up = &lsp->u.u;
    457 	register size_t tzheadsize = sizeof(struct tzhead);
    458 
    459 	sp->goback = sp->goahead = false;
    460 
    461 	if (! name) {
    462 		name = TZDEFAULT;
    463 		if (! name)
    464 		  return EINVAL;
    465 	}
    466 
    467 	if (name[0] == ':')
    468 		++name;
    469 #ifdef SUPPRESS_TZDIR
    470 	/* Do not prepend TZDIR.  This is intended for specialized
    471 	   applications only, due to its security implications.  */
    472 	doaccess = true;
    473 #else
    474 	doaccess = name[0] == '/';
    475 #endif
    476 	if (!doaccess) {
    477 		char const *dot;
    478 		size_t namelen = strlen(name);
    479 		if (sizeof lsp->fullname - sizeof tzdirslash <= namelen)
    480 		  return ENAMETOOLONG;
    481 
    482 		/* Create a string "TZDIR/NAME".  Using sprintf here
    483 		   would pull in stdio (and would fail if the
    484 		   resulting string length exceeded INT_MAX!).  */
    485 		memcpy(lsp->fullname, tzdirslash, sizeof tzdirslash);
    486 		strcpy(lsp->fullname + sizeof tzdirslash, name);
    487 
    488 		/* Set doaccess if NAME contains a ".." file name
    489 		   component, as such a name could read a file outside
    490 		   the TZDIR virtual subtree.  */
    491 		for (dot = name; (dot = strchr(dot, '.')); dot++)
    492 		  if ((dot == name || dot[-1] == '/') && dot[1] == '.'
    493 		      && (dot[2] == '/' || !dot[2])) {
    494 		    doaccess = true;
    495 		    break;
    496 		  }
    497 
    498 		name = lsp->fullname;
    499 	}
    500 	if (doaccess && access(name, R_OK) != 0)
    501 	  return errno;
    502 	fid = open(name, OPEN_MODE);
    503 	if (fid < 0)
    504 	  return errno;
    505 
    506 	nread = read(fid, up->buf, sizeof up->buf);
    507 	if (nread < (ssize_t)tzheadsize) {
    508 	  int err = nread < 0 ? errno : EINVAL;
    509 	  close(fid);
    510 	  return err;
    511 	}
    512 	if (close(fid) < 0)
    513 	  return errno;
    514 	for (stored = 4; stored <= 8; stored *= 2) {
    515 	    char version = up->tzhead.tzh_version[0];
    516 	    bool skip_datablock = stored == 4 && version;
    517 	    int_fast32_t datablock_size;
    518 	    int_fast32_t ttisstdcnt = detzcode(up->tzhead.tzh_ttisstdcnt);
    519 	    int_fast32_t ttisutcnt = detzcode(up->tzhead.tzh_ttisutcnt);
    520 	    int_fast64_t prevtr = -1;
    521 	    int_fast32_t prevcorr = 0;
    522 	    int_fast32_t leapcnt = detzcode(up->tzhead.tzh_leapcnt);
    523 	    int_fast32_t timecnt = detzcode(up->tzhead.tzh_timecnt);
    524 	    int_fast32_t typecnt = detzcode(up->tzhead.tzh_typecnt);
    525 	    int_fast32_t charcnt = detzcode(up->tzhead.tzh_charcnt);
    526 	    char const *p = up->buf + tzheadsize;
    527 	    /* Although tzfile(5) currently requires typecnt to be nonzero,
    528 	       support future formats that may allow zero typecnt
    529 	       in files that have a TZ string and no transitions.  */
    530 	    if (! (0 <= leapcnt && leapcnt < TZ_MAX_LEAPS
    531 		   && 0 <= typecnt && typecnt < TZ_MAX_TYPES
    532 		   && 0 <= timecnt && timecnt < TZ_MAX_TIMES
    533 		   && 0 <= charcnt && charcnt < TZ_MAX_CHARS
    534 		   && 0 <= ttisstdcnt && ttisstdcnt < TZ_MAX_TYPES
    535 		   && 0 <= ttisutcnt && ttisutcnt < TZ_MAX_TYPES))
    536 	      return EINVAL;
    537 	    datablock_size
    538 		    = (timecnt * stored		/* ats */
    539 		       + timecnt		/* types */
    540 		       + typecnt * 6		/* ttinfos */
    541 		       + charcnt		/* chars */
    542 		       + leapcnt * (stored + 4)	/* lsinfos */
    543 		       + ttisstdcnt		/* ttisstds */
    544 		       + ttisutcnt);		/* ttisuts */
    545 	    if (nread < (ssize_t)(tzheadsize + datablock_size))
    546 	      return EINVAL;
    547 	    if (skip_datablock)
    548 		p += datablock_size;
    549 	    else {
    550 		if (! ((ttisstdcnt == typecnt || ttisstdcnt == 0)
    551 		       && (ttisutcnt == typecnt || ttisutcnt == 0)))
    552 		  return EINVAL;
    553 
    554 		sp->leapcnt = leapcnt;
    555 		sp->timecnt = timecnt;
    556 		sp->typecnt = typecnt;
    557 		sp->charcnt = charcnt;
    558 
    559 		/* Read transitions, discarding those out of time_t range.
    560 		   But pretend the last transition before TIME_T_MIN
    561 		   occurred at TIME_T_MIN.  */
    562 		timecnt = 0;
    563 		for (i = 0; i < sp->timecnt; ++i) {
    564 			int_fast64_t at
    565 			  = stored == 4 ? detzcode(p) : detzcode64(p);
    566 			sp->types[i] = at <= TIME_T_MAX;
    567 			if (sp->types[i]) {
    568 			  time_t attime
    569 			    = ((TYPE_SIGNED(time_t) ? at < TIME_T_MIN : at < 0)
    570 			       ? TIME_T_MIN : (time_t)at);
    571 			  if (timecnt && attime <= sp->ats[timecnt - 1]) {
    572 			    if (attime < sp->ats[timecnt - 1])
    573 			      return EINVAL;
    574 			    sp->types[i - 1] = 0;
    575 			    timecnt--;
    576 			  }
    577 			  sp->ats[timecnt++] = attime;
    578 			}
    579 			p += stored;
    580 		}
    581 
    582 		timecnt = 0;
    583 		for (i = 0; i < sp->timecnt; ++i) {
    584 			unsigned char typ = *p++;
    585 			if (sp->typecnt <= typ)
    586 			  return EINVAL;
    587 			if (sp->types[i])
    588 				sp->types[timecnt++] = typ;
    589 		}
    590 		sp->timecnt = timecnt;
    591 		for (i = 0; i < sp->typecnt; ++i) {
    592 			register struct ttinfo *	ttisp;
    593 			unsigned char isdst, desigidx;
    594 
    595 			ttisp = &sp->ttis[i];
    596 			ttisp->tt_utoff = detzcode(p);
    597 			p += 4;
    598 			isdst = *p++;
    599 			if (! (isdst < 2))
    600 			  return EINVAL;
    601 			ttisp->tt_isdst = isdst;
    602 			desigidx = *p++;
    603 			if (! (desigidx < sp->charcnt))
    604 			  return EINVAL;
    605 			ttisp->tt_desigidx = desigidx;
    606 		}
    607 		for (i = 0; i < sp->charcnt; ++i)
    608 			sp->chars[i] = *p++;
    609 		/* Ensure '\0'-terminated, and make it safe to call
    610 		   ttunspecified later.  */
    611 		memset(&sp->chars[i], 0, CHARS_EXTRA);
    612 
    613 		/* Read leap seconds, discarding those out of time_t range.  */
    614 		leapcnt = 0;
    615 		for (i = 0; i < sp->leapcnt; ++i) {
    616 		  int_fast64_t tr = stored == 4 ? detzcode(p) : detzcode64(p);
    617 		  int_fast32_t corr = detzcode(p + stored);
    618 		  p += stored + 4;
    619 
    620 		  /* Leap seconds cannot occur before the Epoch,
    621 		     or out of order.  */
    622 		  if (tr <= prevtr)
    623 		    return EINVAL;
    624 
    625 		  /* To avoid other botches in this code, each leap second's
    626 		     correction must differ from the previous one's by 1
    627 		     second or less, except that the first correction can be
    628 		     any value; these requirements are more generous than
    629 		     RFC 8536, to allow future RFC extensions.  */
    630 		  if (! (i == 0
    631 			 || (prevcorr < corr
    632 			     ? corr == prevcorr + 1
    633 			     : (corr == prevcorr
    634 				|| corr == prevcorr - 1))))
    635 		    return EINVAL;
    636 		  prevtr = tr;
    637 		  prevcorr = corr;
    638 
    639 		  if (tr <= TIME_T_MAX) {
    640 		    sp->lsis[leapcnt].ls_trans = (time_t)tr;
    641 		    sp->lsis[leapcnt].ls_corr = corr;
    642 		    leapcnt++;
    643 		  }
    644 		}
    645 		sp->leapcnt = leapcnt;
    646 
    647 		for (i = 0; i < sp->typecnt; ++i) {
    648 			register struct ttinfo *	ttisp;
    649 
    650 			ttisp = &sp->ttis[i];
    651 			if (ttisstdcnt == 0)
    652 				ttisp->tt_ttisstd = false;
    653 			else {
    654 				if (*p != true && *p != false)
    655 				  return EINVAL;
    656 				ttisp->tt_ttisstd = *p++;
    657 			}
    658 		}
    659 		for (i = 0; i < sp->typecnt; ++i) {
    660 			register struct ttinfo *	ttisp;
    661 
    662 			ttisp = &sp->ttis[i];
    663 			if (ttisutcnt == 0)
    664 				ttisp->tt_ttisut = false;
    665 			else {
    666 				if (*p != true && *p != false)
    667 						return EINVAL;
    668 				ttisp->tt_ttisut = *p++;
    669 			}
    670 		}
    671 	    }
    672 
    673 	    nread -= p - up->buf;
    674 	    memmove(up->buf, p, (size_t)nread);
    675 
    676 	    /* If this is an old file, we're done.  */
    677 	    if (!version)
    678 	      break;
    679 	}
    680 	if (doextend && nread > 2 &&
    681 		up->buf[0] == '\n' && up->buf[nread - 1] == '\n' &&
    682 		sp->typecnt + 2 <= TZ_MAX_TYPES) {
    683 			struct state	*ts = &lsp->u.st;
    684 
    685 			up->buf[nread - 1] = '\0';
    686 			if (tzparse(&up->buf[1], ts, sp)) {
    687 
    688 			  /* Attempt to reuse existing abbreviations.
    689 			     Without this, America/Anchorage would be right on
    690 			     the edge after 2037 when TZ_MAX_CHARS is 50, as
    691 			     sp->charcnt equals 40 (for LMT AST AWT APT AHST
    692 			     AHDT YST AKDT AKST) and ts->charcnt equals 10
    693 			     (for AKST AKDT).  Reusing means sp->charcnt can
    694 			     stay 40 in this example.  */
    695 			  int gotabbr = 0;
    696 			  int charcnt = sp->charcnt;
    697 			  for (i = 0; i < ts->typecnt; i++) {
    698 			    char *tsabbr = ts->chars + ts->ttis[i].tt_desigidx;
    699 			    int j;
    700 			    for (j = 0; j < charcnt; j++)
    701 			      if (strcmp(sp->chars + j, tsabbr) == 0) {
    702 				ts->ttis[i].tt_desigidx = j;
    703 				gotabbr++;
    704 				break;
    705 			      }
    706 			    if (! (j < charcnt)) {
    707 			      size_t tsabbrlen = strlen(tsabbr);
    708 			      if (j + tsabbrlen < TZ_MAX_CHARS) {
    709 				strcpy(sp->chars + j, tsabbr);
    710 				charcnt = (int_fast32_t)(j + tsabbrlen + 1);
    711 				ts->ttis[i].tt_desigidx = j;
    712 				gotabbr++;
    713 			      }
    714 			    }
    715 			  }
    716 			  if (gotabbr == ts->typecnt) {
    717 			    sp->charcnt = charcnt;
    718 
    719 			    /* Ignore any trailing, no-op transitions generated
    720 			       by zic as they don't help here and can run afoul
    721 			       of bugs in zic 2016j or earlier.  */
    722 			    while (1 < sp->timecnt
    723 				   && (sp->types[sp->timecnt - 1]
    724 				       == sp->types[sp->timecnt - 2]))
    725 			      sp->timecnt--;
    726 
    727 			    for (i = 0;
    728 				 i < ts->timecnt && sp->timecnt < TZ_MAX_TIMES;
    729 				 i++) {
    730 			      __time_t t = ts->ats[i];
    731 			      if (increment_overflow_time(&t, leapcorr(sp, t))
    732 				  || (0 < sp->timecnt
    733 				      && t <= sp->ats[sp->timecnt - 1]))
    734 				continue;
    735 			      sp->ats[sp->timecnt] = t;
    736 			      sp->types[sp->timecnt] = (sp->typecnt
    737 							+ ts->types[i]);
    738 			      sp->timecnt++;
    739 			    }
    740 			    for (i = 0; i < ts->typecnt; i++)
    741 			      sp->ttis[sp->typecnt++] = ts->ttis[i];
    742 			  }
    743 			}
    744 	}
    745 	if (sp->typecnt == 0)
    746 	  return EINVAL;
    747 	if (sp->timecnt > 1) {
    748 	    if (sp->ats[0] <= (time_t)(TIME_T_MAX - SECSPERREPEAT)) {
    749 		time_t repeatat = (time_t)(sp->ats[0] + SECSPERREPEAT);
    750 		int repeattype = sp->types[0];
    751 		for (i = 1; i < sp->timecnt; ++i)
    752 		  if (sp->ats[i] == repeatat
    753 		      && typesequiv(sp, sp->types[i], repeattype)) {
    754 					sp->goback = true;
    755 					break;
    756 		  }
    757 	    }
    758 	    if ((time_t)(TIME_T_MIN + SECSPERREPEAT) <= sp->ats[sp->timecnt - 1]) {
    759 		time_t repeatat =
    760 		    (time_t)(sp->ats[sp->timecnt - 1] - SECSPERREPEAT);
    761 		int repeattype = sp->types[sp->timecnt - 1];
    762 		for (i = sp->timecnt - 2; i >= 0; --i)
    763 		  if (sp->ats[i] == repeatat
    764 		      && typesequiv(sp, sp->types[i], repeattype)) {
    765 					sp->goahead = true;
    766 					break;
    767 		  }
    768 	    }
    769 	}
    770 
    771 	/* Infer sp->defaulttype from the data.  Although this default
    772 	   type is always zero for data from recent tzdb releases,
    773 	   things are trickier for data from tzdb 2018e or earlier.
    774 
    775 	   The first set of heuristics work around bugs in 32-bit data
    776 	   generated by tzdb 2013c or earlier.  The workaround is for
    777 	   zones like Australia/Macquarie where timestamps before the
    778 	   first transition have a time type that is not the earliest
    779 	   standard-time type.  See:
    780 	   https://mm.icann.org/pipermail/tz/2013-May/019368.html */
    781 	/*
    782 	** If type 0 does not specify local time, or is unused in transitions,
    783 	** it's the type to use for early times.
    784 	*/
    785 	for (i = 0; i < sp->timecnt; ++i)
    786 		if (sp->types[i] == 0)
    787 			break;
    788 	i = i < sp->timecnt && ! ttunspecified(sp, 0) ? -1 : 0;
    789 	/*
    790 	** Absent the above,
    791 	** if there are transition times
    792 	** and the first transition is to a daylight time
    793 	** find the standard type less than and closest to
    794 	** the type of the first transition.
    795 	*/
    796 	if (i < 0 && sp->timecnt > 0 && sp->ttis[sp->types[0]].tt_isdst) {
    797 		i = sp->types[0];
    798 		while (--i >= 0)
    799 			if (!sp->ttis[i].tt_isdst)
    800 				break;
    801 	}
    802 	/* The next heuristics are for data generated by tzdb 2018e or
    803 	   earlier, for zones like EST5EDT where the first transition
    804 	   is to DST.  */
    805 	/*
    806 	** If no result yet, find the first standard type.
    807 	** If there is none, punt to type zero.
    808 	*/
    809 	if (i < 0) {
    810 		i = 0;
    811 		while (sp->ttis[i].tt_isdst)
    812 			if (++i >= sp->typecnt) {
    813 				i = 0;
    814 				break;
    815 			}
    816 	}
    817 	/* A simple 'sp->defaulttype = 0;' would suffice here if we
    818 	   didn't have to worry about 2018e-or-earlier data.  Even
    819 	   simpler would be to remove the defaulttype member and just
    820 	   use 0 in its place.  */
    821 	sp->defaulttype = i;
    822 
    823 	return 0;
    824 }
    825 
    826 /* Load tz data from the file named NAME into *SP.  Read extended
    827    format if DOEXTEND.  Return 0 on success, an errno value on failure.  */
    828 static int
    829 tzload(char const *name, struct state *sp, bool doextend)
    830 {
    831   union local_storage *lsp = malloc(sizeof *lsp);
    832   if (!lsp) {
    833     return /*CONSTCOND*/HAVE_MALLOC_ERRNO ? errno : ENOMEM;
    834   } else {
    835     int err = tzloadbody(name, sp, doextend, lsp);
    836     free(lsp);
    837     return err;
    838   }
    839 }
    840 
    841 static bool
    842 typesequiv(const struct state *sp, int a, int b)
    843 {
    844 	register bool result;
    845 
    846 	if (sp == NULL ||
    847 		a < 0 || a >= sp->typecnt ||
    848 		b < 0 || b >= sp->typecnt)
    849 			result = false;
    850 	else {
    851 		register const struct ttinfo *	ap = &sp->ttis[a];
    852 		register const struct ttinfo *	bp = &sp->ttis[b];
    853 		result = (ap->tt_utoff == bp->tt_utoff
    854 			  && ap->tt_isdst == bp->tt_isdst
    855 			  && ap->tt_ttisstd == bp->tt_ttisstd
    856 			  && ap->tt_ttisut == bp->tt_ttisut
    857 			  && (strcmp(&sp->chars[ap->tt_desigidx],
    858 				     &sp->chars[bp->tt_desigidx])
    859 			      == 0));
    860 	}
    861 	return result;
    862 }
    863 
    864 static const int	mon_lengths[2][MONSPERYEAR] = {
    865 	{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 },
    866 	{ 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }
    867 };
    868 
    869 static const int	year_lengths[2] = {
    870 	DAYSPERNYEAR, DAYSPERLYEAR
    871 };
    872 
    873 /* Is C an ASCII digit?  */
    874 static bool
    875 is_digit(char c)
    876 {
    877   return '0' <= c && c <= '9';
    878 }
    879 
    880 /*
    881 ** Given a pointer into a timezone string, scan until a character that is not
    882 ** a valid character in a time zone abbreviation is found.
    883 ** Return a pointer to that character.
    884 */
    885 
    886 static ATTRIBUTE_PURE const char *
    887 getzname(register const char *strp)
    888 {
    889 	register char	c;
    890 
    891 	while ((c = *strp) != '\0' && !is_digit(c) && c != ',' && c != '-' &&
    892 		c != '+')
    893 			++strp;
    894 	return strp;
    895 }
    896 
    897 /*
    898 ** Given a pointer into an extended timezone string, scan until the ending
    899 ** delimiter of the time zone abbreviation is located.
    900 ** Return a pointer to the delimiter.
    901 **
    902 ** As with getzname above, the legal character set is actually quite
    903 ** restricted, with other characters producing undefined results.
    904 ** We don't do any checking here; checking is done later in common-case code.
    905 */
    906 
    907 static ATTRIBUTE_PURE const char *
    908 getqzname(register const char *strp, const int delim)
    909 {
    910 	register int	c;
    911 
    912 	while ((c = *strp) != '\0' && c != delim)
    913 		++strp;
    914 	return strp;
    915 }
    916 
    917 /*
    918 ** Given a pointer into a timezone string, extract a number from that string.
    919 ** Check that the number is within a specified range; if it is not, return
    920 ** NULL.
    921 ** Otherwise, return a pointer to the first character not part of the number.
    922 */
    923 
    924 static const char *
    925 getnum(register const char *strp, int *const nump, const int min, const int max)
    926 {
    927 	register char	c;
    928 	register int	num;
    929 
    930 	if (strp == NULL || !is_digit(c = *strp)) {
    931 		errno = EINVAL;
    932 		return NULL;
    933 	}
    934 	num = 0;
    935 	do {
    936 		num = num * 10 + (c - '0');
    937 		if (num > max) {
    938 			errno = EOVERFLOW;
    939 			return NULL;	/* illegal value */
    940 		}
    941 		c = *++strp;
    942 	} while (is_digit(c));
    943 	if (num < min) {
    944 		errno = EINVAL;
    945 		return NULL;		/* illegal value */
    946 	}
    947 	*nump = num;
    948 	return strp;
    949 }
    950 
    951 /*
    952 ** Given a pointer into a timezone string, extract a number of seconds,
    953 ** in hh[:mm[:ss]] form, from the string.
    954 ** If any error occurs, return NULL.
    955 ** Otherwise, return a pointer to the first character not part of the number
    956 ** of seconds.
    957 */
    958 
    959 static const char *
    960 getsecs(register const char *strp, int_fast32_t *const secsp)
    961 {
    962 	int	num;
    963 	int_fast32_t secsperhour = SECSPERHOUR;
    964 
    965 	/*
    966 	** 'HOURSPERDAY * DAYSPERWEEK - 1' allows quasi-Posix rules like
    967 	** "M10.4.6/26", which does not conform to Posix,
    968 	** but which specifies the equivalent of
    969 	** "02:00 on the first Sunday on or after 23 Oct".
    970 	*/
    971 	strp = getnum(strp, &num, 0, HOURSPERDAY * DAYSPERWEEK - 1);
    972 	if (strp == NULL)
    973 		return NULL;
    974 	*secsp = num * secsperhour;
    975 	if (*strp == ':') {
    976 		++strp;
    977 		strp = getnum(strp, &num, 0, MINSPERHOUR - 1);
    978 		if (strp == NULL)
    979 			return NULL;
    980 		*secsp += num * SECSPERMIN;
    981 		if (*strp == ':') {
    982 			++strp;
    983 			/* 'SECSPERMIN' allows for leap seconds.  */
    984 			strp = getnum(strp, &num, 0, SECSPERMIN);
    985 			if (strp == NULL)
    986 				return NULL;
    987 			*secsp += num;
    988 		}
    989 	}
    990 	return strp;
    991 }
    992 
    993 /*
    994 ** Given a pointer into a timezone string, extract an offset, in
    995 ** [+-]hh[:mm[:ss]] form, from the string.
    996 ** If any error occurs, return NULL.
    997 ** Otherwise, return a pointer to the first character not part of the time.
    998 */
    999 
   1000 static const char *
   1001 getoffset(register const char *strp, int_fast32_t *const offsetp)
   1002 {
   1003 	register bool neg = false;
   1004 
   1005 	if (*strp == '-') {
   1006 		neg = true;
   1007 		++strp;
   1008 	} else if (*strp == '+')
   1009 		++strp;
   1010 	strp = getsecs(strp, offsetp);
   1011 	if (strp == NULL)
   1012 		return NULL;		/* illegal time */
   1013 	if (neg)
   1014 		*offsetp = -*offsetp;
   1015 	return strp;
   1016 }
   1017 
   1018 /*
   1019 ** Given a pointer into a timezone string, extract a rule in the form
   1020 ** date[/time]. See POSIX section 8 for the format of "date" and "time".
   1021 ** If a valid rule is not found, return NULL.
   1022 ** Otherwise, return a pointer to the first character not part of the rule.
   1023 */
   1024 
   1025 static const char *
   1026 getrule(const char *strp, register struct rule *const rulep)
   1027 {
   1028 	if (*strp == 'J') {
   1029 		/*
   1030 		** Julian day.
   1031 		*/
   1032 		rulep->r_type = JULIAN_DAY;
   1033 		++strp;
   1034 		strp = getnum(strp, &rulep->r_day, 1, DAYSPERNYEAR);
   1035 	} else if (*strp == 'M') {
   1036 		/*
   1037 		** Month, week, day.
   1038 		*/
   1039 		rulep->r_type = MONTH_NTH_DAY_OF_WEEK;
   1040 		++strp;
   1041 		strp = getnum(strp, &rulep->r_mon, 1, MONSPERYEAR);
   1042 		if (strp == NULL)
   1043 			return NULL;
   1044 		if (*strp++ != '.')
   1045 			return NULL;
   1046 		strp = getnum(strp, &rulep->r_week, 1, 5);
   1047 		if (strp == NULL)
   1048 			return NULL;
   1049 		if (*strp++ != '.')
   1050 			return NULL;
   1051 		strp = getnum(strp, &rulep->r_day, 0, DAYSPERWEEK - 1);
   1052 	} else if (is_digit(*strp)) {
   1053 		/*
   1054 		** Day of year.
   1055 		*/
   1056 		rulep->r_type = DAY_OF_YEAR;
   1057 		strp = getnum(strp, &rulep->r_day, 0, DAYSPERLYEAR - 1);
   1058 	} else	return NULL;		/* invalid format */
   1059 	if (strp == NULL)
   1060 		return NULL;
   1061 	if (*strp == '/') {
   1062 		/*
   1063 		** Time specified.
   1064 		*/
   1065 		++strp;
   1066 		strp = getoffset(strp, &rulep->r_time);
   1067 	} else	rulep->r_time = 2 * SECSPERHOUR;	/* default = 2:00:00 */
   1068 	return strp;
   1069 }
   1070 
   1071 /*
   1072 ** Given a year, a rule, and the offset from UT at the time that rule takes
   1073 ** effect, calculate the year-relative time that rule takes effect.
   1074 */
   1075 
   1076 static int_fast32_t
   1077 transtime(const int year, register const struct rule *const rulep,
   1078 	  const int_fast32_t offset)
   1079 {
   1080 	register bool	leapyear;
   1081 	register int_fast32_t value;
   1082 	register int	i;
   1083 	int		d, m1, yy0, yy1, yy2, dow;
   1084 
   1085 	leapyear = isleap(year);
   1086 	switch (rulep->r_type) {
   1087 
   1088 	case JULIAN_DAY:
   1089 		/*
   1090 		** Jn - Julian day, 1 == January 1, 60 == March 1 even in leap
   1091 		** years.
   1092 		** In non-leap years, or if the day number is 59 or less, just
   1093 		** add SECSPERDAY times the day number-1 to the time of
   1094 		** January 1, midnight, to get the day.
   1095 		*/
   1096 		value = (rulep->r_day - 1) * SECSPERDAY;
   1097 		if (leapyear && rulep->r_day >= 60)
   1098 			value += SECSPERDAY;
   1099 		break;
   1100 
   1101 	case DAY_OF_YEAR:
   1102 		/*
   1103 		** n - day of year.
   1104 		** Just add SECSPERDAY times the day number to the time of
   1105 		** January 1, midnight, to get the day.
   1106 		*/
   1107 		value = rulep->r_day * SECSPERDAY;
   1108 		break;
   1109 
   1110 	case MONTH_NTH_DAY_OF_WEEK:
   1111 		/*
   1112 		** Mm.n.d - nth "dth day" of month m.
   1113 		*/
   1114 
   1115 		/*
   1116 		** Use Zeller's Congruence to get day-of-week of first day of
   1117 		** month.
   1118 		*/
   1119 		m1 = (rulep->r_mon + 9) % 12 + 1;
   1120 		yy0 = (rulep->r_mon <= 2) ? (year - 1) : year;
   1121 		yy1 = yy0 / 100;
   1122 		yy2 = yy0 % 100;
   1123 		dow = ((26 * m1 - 2) / 10 +
   1124 			1 + yy2 + yy2 / 4 + yy1 / 4 - 2 * yy1) % 7;
   1125 		if (dow < 0)
   1126 			dow += DAYSPERWEEK;
   1127 
   1128 		/*
   1129 		** "dow" is the day-of-week of the first day of the month. Get
   1130 		** the day-of-month (zero-origin) of the first "dow" day of the
   1131 		** month.
   1132 		*/
   1133 		d = rulep->r_day - dow;
   1134 		if (d < 0)
   1135 			d += DAYSPERWEEK;
   1136 		for (i = 1; i < rulep->r_week; ++i) {
   1137 			if (d + DAYSPERWEEK >=
   1138 				mon_lengths[leapyear][rulep->r_mon - 1])
   1139 					break;
   1140 			d += DAYSPERWEEK;
   1141 		}
   1142 
   1143 		/*
   1144 		** "d" is the day-of-month (zero-origin) of the day we want.
   1145 		*/
   1146 		value = d * SECSPERDAY;
   1147 		for (i = 0; i < rulep->r_mon - 1; ++i)
   1148 			value += mon_lengths[leapyear][i] * SECSPERDAY;
   1149 		break;
   1150 
   1151 	default: UNREACHABLE();
   1152 	}
   1153 
   1154 	/*
   1155 	** "value" is the year-relative time of 00:00:00 UT on the day in
   1156 	** question. To get the year-relative time of the specified local
   1157 	** time on that day, add the transition time and the current offset
   1158 	** from UT.
   1159 	*/
   1160 	return value + rulep->r_time + offset;
   1161 }
   1162 
   1163 /*
   1164 ** Given a POSIX section 8-style TZ string, fill in the rule tables as
   1165 ** appropriate.
   1166 */
   1167 
   1168 static bool
   1169 tzparse(const char *name, struct state *sp, struct state *basep)
   1170 {
   1171 	const char *			stdname;
   1172 	const char *			dstname;
   1173 	size_t				stdlen;
   1174 	size_t				dstlen;
   1175 	size_t				charcnt;
   1176 	int_fast32_t			stdoffset;
   1177 	int_fast32_t			dstoffset;
   1178 	register char *			cp;
   1179 	register bool			load_ok;
   1180 	time_t atlo = TIME_T_MIN, leaplo = TIME_T_MIN;
   1181 
   1182 	dstname = NULL; /* XXX gcc */
   1183 	stdname = name;
   1184 	if (*name == '<') {
   1185 	  name++;
   1186 	  stdname = name;
   1187 	  name = getqzname(name, '>');
   1188 	  if (*name != '>')
   1189 	    return false;
   1190 	  stdlen = name - stdname;
   1191 	  name++;
   1192 	} else {
   1193 	  name = getzname(name);
   1194 	  stdlen = name - stdname;
   1195 	}
   1196 	if (!stdlen)
   1197 	  return false;
   1198 	name = getoffset(name, &stdoffset);
   1199 	if (name == NULL)
   1200 	  return false;
   1201 	charcnt = stdlen + 1;
   1202 	if (sizeof sp->chars < charcnt)
   1203 	  return false;
   1204 	if (basep) {
   1205 	  if (0 < basep->timecnt)
   1206 	    atlo = basep->ats[basep->timecnt - 1];
   1207 	  load_ok = false;
   1208 	  sp->leapcnt = basep->leapcnt;
   1209 	  memcpy(sp->lsis, basep->lsis, sp->leapcnt * sizeof *sp->lsis);
   1210 	} else {
   1211 	  load_ok = tzload(TZDEFRULES, sp, false) == 0;
   1212 	  if (!load_ok)
   1213 	    sp->leapcnt = 0;	/* So, we're off a little.  */
   1214 	}
   1215 	if (0 < sp->leapcnt)
   1216 	  leaplo = sp->lsis[sp->leapcnt - 1].ls_trans;
   1217 	if (*name != '\0') {
   1218 		if (*name == '<') {
   1219 			dstname = ++name;
   1220 			name = getqzname(name, '>');
   1221 			if (*name != '>')
   1222 			  return false;
   1223 			dstlen = name - dstname;
   1224 			name++;
   1225 		} else {
   1226 			dstname = name;
   1227 			name = getzname(name);
   1228 			dstlen = name - dstname; /* length of DST abbr. */
   1229 		}
   1230 		if (!dstlen)
   1231 		  return false;
   1232 		charcnt += dstlen + 1;
   1233 		if (sizeof sp->chars < charcnt)
   1234 		  return false;
   1235 		if (*name != '\0' && *name != ',' && *name != ';') {
   1236 			name = getoffset(name, &dstoffset);
   1237 			if (name == NULL)
   1238 			  return false;
   1239 		} else	dstoffset = stdoffset - SECSPERHOUR;
   1240 		if (*name == '\0' && !load_ok)
   1241 			name = TZDEFRULESTRING;
   1242 		if (*name == ',' || *name == ';') {
   1243 			struct rule	start;
   1244 			struct rule	end;
   1245 			register int	year;
   1246 			register int	timecnt;
   1247 			__time_t	janfirst;
   1248 			int_fast32_t janoffset = 0;
   1249 			int yearbeg, yearlim;
   1250 
   1251 			++name;
   1252 			if ((name = getrule(name, &start)) == NULL)
   1253 			  return false;
   1254 			if (*name++ != ',')
   1255 			  return false;
   1256 			if ((name = getrule(name, &end)) == NULL)
   1257 			  return false;
   1258 			if (*name != '\0')
   1259 			  return false;
   1260 			sp->typecnt = 2;	/* standard time and DST */
   1261 			/*
   1262 			** Two transitions per year, from EPOCH_YEAR forward.
   1263 			*/
   1264 			init_ttinfo(&sp->ttis[0], -stdoffset, false, 0);
   1265 			init_ttinfo(&sp->ttis[1], -dstoffset, true,
   1266 			    (int)(stdlen + 1));
   1267 			sp->defaulttype = 0;
   1268 			timecnt = 0;
   1269 			janfirst = 0;
   1270 			yearbeg = EPOCH_YEAR;
   1271 
   1272 			do {
   1273 			  int_fast32_t yearsecs
   1274 			    = year_lengths[isleap(yearbeg - 1)] * SECSPERDAY;
   1275 			  yearbeg--;
   1276 			  if (increment_overflow_time(&janfirst, -yearsecs)) {
   1277 			    janoffset = -yearsecs;
   1278 			    break;
   1279 			  }
   1280 			} while (atlo < janfirst
   1281 				 && EPOCH_YEAR - YEARSPERREPEAT / 2 < yearbeg);
   1282 
   1283 			while (true) {
   1284 			  int_fast32_t yearsecs
   1285 			    = year_lengths[isleap(yearbeg)] * SECSPERDAY;
   1286 			  int yearbeg1 = yearbeg;
   1287 			  __time_t janfirst1 = janfirst;
   1288 			  if (increment_overflow_time(&janfirst1, yearsecs)
   1289 			      || increment_overflow(&yearbeg1, 1)
   1290 			      || atlo <= janfirst1)
   1291 			    break;
   1292 			  yearbeg = yearbeg1;
   1293 			  janfirst = janfirst1;
   1294 			}
   1295 
   1296 			yearlim = yearbeg;
   1297 			if (increment_overflow(&yearlim, YEARSPERREPEAT + 1))
   1298 			  yearlim = INT_MAX;
   1299 			for (year = yearbeg; year < yearlim; year++) {
   1300 				int_fast32_t
   1301 				  starttime = transtime(year, &start, stdoffset),
   1302 				  endtime = transtime(year, &end, dstoffset);
   1303 				int_fast32_t
   1304 				  yearsecs = (year_lengths[isleap(year)]
   1305 					      * SECSPERDAY);
   1306 				bool reversed = endtime < starttime;
   1307 				if (reversed) {
   1308 					int_fast32_t swap = starttime;
   1309 					starttime = endtime;
   1310 					endtime = swap;
   1311 				}
   1312 				if (reversed
   1313 				    || (starttime < endtime
   1314 					&& endtime - starttime < yearsecs)) {
   1315 					if (TZ_MAX_TIMES - 2 < timecnt)
   1316 						break;
   1317 					sp->ats[timecnt] = janfirst;
   1318 					if (! increment_overflow_time
   1319 					    (&sp->ats[timecnt],
   1320 					     janoffset + starttime)
   1321 					    && atlo <= sp->ats[timecnt])
   1322 					  sp->types[timecnt++] = !reversed;
   1323 					sp->ats[timecnt] = janfirst;
   1324 					if (! increment_overflow_time
   1325 					    (&sp->ats[timecnt],
   1326 					     janoffset + endtime)
   1327 					    && atlo <= sp->ats[timecnt]) {
   1328 					  sp->types[timecnt++] = reversed;
   1329 					}
   1330 				}
   1331 				if (endtime < leaplo) {
   1332 				  yearlim = year;
   1333 				  if (increment_overflow(&yearlim,
   1334 							 YEARSPERREPEAT + 1))
   1335 				    yearlim = INT_MAX;
   1336 				}
   1337 				if (increment_overflow_time
   1338 				    (&janfirst, janoffset + yearsecs))
   1339 					break;
   1340 				janoffset = 0;
   1341 			}
   1342 			sp->timecnt = timecnt;
   1343 			if (! timecnt) {
   1344 				sp->ttis[0] = sp->ttis[1];
   1345 				sp->typecnt = 1;	/* Perpetual DST.  */
   1346 			} else if (YEARSPERREPEAT < year - yearbeg)
   1347 				sp->goback = sp->goahead = true;
   1348 		} else {
   1349 			register int_fast32_t	theirstdoffset;
   1350 			register int_fast32_t	theirdstoffset;
   1351 			register int_fast32_t	theiroffset;
   1352 			register bool		isdst;
   1353 			register int		i;
   1354 			register int		j;
   1355 
   1356 			if (*name != '\0')
   1357 			  return false;
   1358 			/*
   1359 			** Initial values of theirstdoffset and theirdstoffset.
   1360 			*/
   1361 			theirstdoffset = 0;
   1362 			for (i = 0; i < sp->timecnt; ++i) {
   1363 				j = sp->types[i];
   1364 				if (!sp->ttis[j].tt_isdst) {
   1365 					theirstdoffset =
   1366 						- sp->ttis[j].tt_utoff;
   1367 					break;
   1368 				}
   1369 			}
   1370 			theirdstoffset = 0;
   1371 			for (i = 0; i < sp->timecnt; ++i) {
   1372 				j = sp->types[i];
   1373 				if (sp->ttis[j].tt_isdst) {
   1374 					theirdstoffset =
   1375 						- sp->ttis[j].tt_utoff;
   1376 					break;
   1377 				}
   1378 			}
   1379 			/*
   1380 			** Initially we're assumed to be in standard time.
   1381 			*/
   1382 			isdst = false;
   1383 			/*
   1384 			** Now juggle transition times and types
   1385 			** tracking offsets as you do.
   1386 			*/
   1387 			for (i = 0; i < sp->timecnt; ++i) {
   1388 				j = sp->types[i];
   1389 				sp->types[i] = sp->ttis[j].tt_isdst;
   1390 				if (sp->ttis[j].tt_ttisut) {
   1391 					/* No adjustment to transition time */
   1392 				} else {
   1393 					/*
   1394 					** If daylight saving time is in
   1395 					** effect, and the transition time was
   1396 					** not specified as standard time, add
   1397 					** the daylight saving time offset to
   1398 					** the transition time; otherwise, add
   1399 					** the standard time offset to the
   1400 					** transition time.
   1401 					*/
   1402 					/*
   1403 					** Transitions from DST to DDST
   1404 					** will effectively disappear since
   1405 					** POSIX provides for only one DST
   1406 					** offset.
   1407 					*/
   1408 					if (isdst && !sp->ttis[j].tt_ttisstd) {
   1409 						sp->ats[i] += (time_t)
   1410 						    (dstoffset - theirdstoffset);
   1411 					} else {
   1412 						sp->ats[i] += (time_t)
   1413 						    (stdoffset - theirstdoffset);
   1414 					}
   1415 				}
   1416 				theiroffset = -sp->ttis[j].tt_utoff;
   1417 				if (sp->ttis[j].tt_isdst)
   1418 					theirstdoffset = theiroffset;
   1419 				else	theirdstoffset = theiroffset;
   1420 			}
   1421 			/*
   1422 			** Finally, fill in ttis.
   1423 			*/
   1424 			init_ttinfo(&sp->ttis[0], -stdoffset, false, 0);
   1425 			init_ttinfo(&sp->ttis[1], -dstoffset, true,
   1426 			    (int)(stdlen + 1));
   1427 			sp->typecnt = 2;
   1428 			sp->defaulttype = 0;
   1429 		}
   1430 	} else {
   1431 		dstlen = 0;
   1432 		sp->typecnt = 1;		/* only standard time */
   1433 		sp->timecnt = 0;
   1434 		init_ttinfo(&sp->ttis[0], -stdoffset, false, 0);
   1435 		init_ttinfo(&sp->ttis[1], 0, false, 0);
   1436 		sp->defaulttype = 0;
   1437 	}
   1438 	sp->charcnt = (int)charcnt;
   1439 	cp = sp->chars;
   1440 	memcpy(cp, stdname, stdlen);
   1441 	cp += stdlen;
   1442 	*cp++ = '\0';
   1443 	if (dstlen != 0) {
   1444 		(void) memcpy(cp, dstname, dstlen);
   1445 		*(cp + dstlen) = '\0';
   1446 	}
   1447 	return true;
   1448 }
   1449 
   1450 static void
   1451 gmtload(struct state *const sp)
   1452 {
   1453 	if (tzload(gmt, sp, true) != 0)
   1454 	  (void)tzparse("GMT0", sp, NULL);
   1455 }
   1456 
   1457 /* Initialize *SP to a value appropriate for the TZ setting NAME.
   1458    Return 0 on success, an errno value on failure.  */
   1459 static int
   1460 zoneinit(struct state *sp, char const *name)
   1461 {
   1462   if (name && ! name[0]) {
   1463     /*
   1464     ** User wants it fast rather than right.
   1465     */
   1466     sp->leapcnt = 0;		/* so, we're off a little */
   1467     sp->timecnt = 0;
   1468     sp->typecnt = 1;
   1469     sp->charcnt = 0;
   1470     sp->goback = sp->goahead = false;
   1471     init_ttinfo(&sp->ttis[0], 0, false, 0);
   1472     strcpy(sp->chars, gmt);
   1473     sp->defaulttype = 0;
   1474     return 0;
   1475   } else {
   1476     int err = tzload(name, sp, true);
   1477     if (err != 0 && name && name[0] != ':' && tzparse(name, sp, NULL))
   1478       err = 0;
   1479     if (err == 0)
   1480       scrub_abbrs(sp);
   1481     return err;
   1482   }
   1483 }
   1484 
   1485 static void
   1486 tzsetlcl(char const *name)
   1487 {
   1488   struct state *sp = __lclptr;
   1489   int lcl = name ? strlen(name) < sizeof lcl_TZname : -1;
   1490   if (lcl < 0
   1491       ? lcl_is_set < 0
   1492       : 0 < lcl_is_set && strcmp(lcl_TZname, name) == 0)
   1493     return;
   1494 
   1495   if (! sp)
   1496     __lclptr = sp = malloc(sizeof *__lclptr);
   1497   if (sp) {
   1498     if (zoneinit(sp, name) != 0)
   1499       zoneinit(sp, "");
   1500     if (0 < lcl)
   1501       strcpy(lcl_TZname, name);
   1502   }
   1503   settzname();
   1504   lcl_is_set = lcl;
   1505 }
   1506 
   1507 #ifdef STD_INSPIRED
   1508 void
   1509 tzsetwall(void)
   1510 {
   1511 	rwlock_wrlock(&__lcl_lock);
   1512 	tzsetlcl(NULL);
   1513 	rwlock_unlock(&__lcl_lock);
   1514 }
   1515 #endif
   1516 
   1517 void
   1518 tzset_unlocked(void)
   1519 {
   1520 	tzsetlcl(getenv("TZ"));
   1521 }
   1522 
   1523 void
   1524 tzset(void)
   1525 {
   1526   rwlock_wrlock(&__lcl_lock);
   1527   tzset_unlocked();
   1528   rwlock_unlock(&__lcl_lock);
   1529 }
   1530 
   1531 static void
   1532 gmtcheck(void)
   1533 {
   1534   static bool gmt_is_set;
   1535   rwlock_wrlock(&__lcl_lock);
   1536   if (! gmt_is_set) {
   1537     gmtptr = malloc(sizeof *gmtptr);
   1538     if (gmtptr)
   1539       gmtload(gmtptr);
   1540     gmt_is_set = true;
   1541   }
   1542   rwlock_unlock(&__lcl_lock);
   1543 }
   1544 
   1545 #if NETBSD_INSPIRED
   1546 
   1547 timezone_t
   1548 tzalloc(char const *name)
   1549 {
   1550   timezone_t sp = malloc(sizeof *sp);
   1551   if (sp) {
   1552     int err = zoneinit(sp, name);
   1553     if (err != 0) {
   1554       free(sp);
   1555       errno = err;
   1556       return NULL;
   1557     }
   1558   } else if (!HAVE_MALLOC_ERRNO)
   1559     errno = ENOMEM;
   1560   return sp;
   1561 }
   1562 
   1563 void
   1564 tzfree(timezone_t sp)
   1565 {
   1566   free(sp);
   1567 }
   1568 
   1569 /*
   1570 ** NetBSD 6.1.4 has ctime_rz, but omit it because POSIX says ctime and
   1571 ** ctime_r are obsolescent and have potential security problems that
   1572 ** ctime_rz would share.  Callers can instead use localtime_rz + strftime.
   1573 **
   1574 ** NetBSD 6.1.4 has tzgetname, but omit it because it doesn't work
   1575 ** in zones with three or more time zone abbreviations.
   1576 ** Callers can instead use localtime_rz + strftime.
   1577 */
   1578 
   1579 #endif
   1580 
   1581 /*
   1582 ** The easy way to behave "as if no library function calls" localtime
   1583 ** is to not call it, so we drop its guts into "localsub", which can be
   1584 ** freely called. (And no, the PANS doesn't require the above behavior,
   1585 ** but it *is* desirable.)
   1586 **
   1587 ** If successful and SETNAME is nonzero,
   1588 ** set the applicable parts of tzname, timezone and altzone;
   1589 ** however, it's OK to omit this step if the timezone is POSIX-compatible,
   1590 ** since in that case tzset should have already done this step correctly.
   1591 ** SETNAME's type is intfast32_t for compatibility with gmtsub,
   1592 ** but it is actually a boolean and its value should be 0 or 1.
   1593 */
   1594 
   1595 /*ARGSUSED*/
   1596 static struct tm *
   1597 localsub(struct state const *sp, time_t const *timep, int_fast32_t setname,
   1598 	 struct tm *const tmp)
   1599 {
   1600 	register const struct ttinfo *	ttisp;
   1601 	register int			i;
   1602 	register struct tm *		result;
   1603 	const time_t			t = *timep;
   1604 
   1605 	if (sp == NULL) {
   1606 	  /* Don't bother to set tzname etc.; tzset has already done it.  */
   1607 	  return gmtsub(gmtptr, timep, 0, tmp);
   1608 	}
   1609 	if ((sp->goback && t < sp->ats[0]) ||
   1610 		(sp->goahead && t > sp->ats[sp->timecnt - 1])) {
   1611 			time_t newt;
   1612 			register time_t		seconds;
   1613 			register time_t		years;
   1614 
   1615 			if (t < sp->ats[0])
   1616 				seconds = sp->ats[0] - t;
   1617 			else	seconds = t - sp->ats[sp->timecnt - 1];
   1618 			--seconds;
   1619 
   1620 			/* Beware integer overflow, as SECONDS might
   1621 			   be close to the maximum time_t.  */
   1622 			years = (time_t)(seconds / SECSPERREPEAT
   1623 			    * YEARSPERREPEAT);
   1624 			seconds = (time_t)(years * AVGSECSPERYEAR);
   1625 			years += YEARSPERREPEAT;
   1626 			if (t < sp->ats[0])
   1627 			  newt = (time_t)(t + seconds + SECSPERREPEAT);
   1628 			else
   1629 			  newt = (time_t)(t - seconds - SECSPERREPEAT);
   1630 
   1631 			if (newt < sp->ats[0] ||
   1632 				newt > sp->ats[sp->timecnt - 1]) {
   1633 				errno = EINVAL;
   1634 				return NULL;	/* "cannot happen" */
   1635 			}
   1636 			result = localsub(sp, &newt, setname, tmp);
   1637 			if (result) {
   1638 				register int_fast64_t newy;
   1639 
   1640 				newy = result->tm_year;
   1641 				if (t < sp->ats[0])
   1642 					newy -= years;
   1643 				else	newy += years;
   1644 				if (! (INT_MIN <= newy && newy <= INT_MAX)) {
   1645 					errno = EOVERFLOW;
   1646 					return NULL;
   1647 				}
   1648 				result->tm_year = (int)newy;
   1649 			}
   1650 			return result;
   1651 	}
   1652 	if (sp->timecnt == 0 || t < sp->ats[0]) {
   1653 		i = sp->defaulttype;
   1654 	} else {
   1655 		register int	lo = 1;
   1656 		register int	hi = sp->timecnt;
   1657 
   1658 		while (lo < hi) {
   1659 			register int	mid = (lo + hi) / 2;
   1660 
   1661 			if (t < sp->ats[mid])
   1662 				hi = mid;
   1663 			else	lo = mid + 1;
   1664 		}
   1665 		i = sp->types[lo - 1];
   1666 	}
   1667 	ttisp = &sp->ttis[i];
   1668 	/*
   1669 	** To get (wrong) behavior that's compatible with System V Release 2.0
   1670 	** you'd replace the statement below with
   1671 	**	t += ttisp->tt_utoff;
   1672 	**	timesub(&t, 0L, sp, tmp);
   1673 	*/
   1674 	result = timesub(&t, ttisp->tt_utoff, sp, tmp);
   1675 	if (result) {
   1676 	  result->tm_isdst = ttisp->tt_isdst;
   1677 #ifdef TM_ZONE
   1678 	  result->TM_ZONE = __UNCONST(&sp->chars[ttisp->tt_desigidx]);
   1679 #endif /* defined TM_ZONE */
   1680 	  if (setname)
   1681 	    update_tzname_etc(sp, ttisp);
   1682 	}
   1683 	return result;
   1684 }
   1685 
   1686 #if NETBSD_INSPIRED
   1687 
   1688 struct tm *
   1689 localtime_rz(timezone_t sp, time_t const *timep, struct tm *tmp)
   1690 {
   1691   return localsub(sp, timep, 0, tmp);
   1692 }
   1693 
   1694 #endif
   1695 
   1696 static struct tm *
   1697 localtime_tzset(time_t const *timep, struct tm *tmp, bool setname)
   1698 {
   1699   rwlock_wrlock(&__lcl_lock);
   1700   if (setname || !lcl_is_set)
   1701     tzset_unlocked();
   1702   tmp = localsub(__lclptr, timep, setname, tmp);
   1703   rwlock_unlock(&__lcl_lock);
   1704   return tmp;
   1705 }
   1706 
   1707 struct tm *
   1708 localtime(const time_t *timep)
   1709 {
   1710   return localtime_tzset(timep, &tm, true);
   1711 }
   1712 
   1713 struct tm *
   1714 localtime_r(const time_t * __restrict timep, struct tm *tmp)
   1715 {
   1716   return localtime_tzset(timep, tmp, true);
   1717 }
   1718 
   1719 /*
   1720 ** gmtsub is to gmtime as localsub is to localtime.
   1721 */
   1722 
   1723 static struct tm *
   1724 gmtsub(struct state const *sp, time_t const *timep, int_fast32_t offset,
   1725        struct tm *tmp)
   1726 {
   1727 	register struct tm *	result;
   1728 
   1729 	result = timesub(timep, offset, gmtptr, tmp);
   1730 #ifdef TM_ZONE
   1731 	/*
   1732 	** Could get fancy here and deliver something such as
   1733 	** "+xx" or "-xx" if offset is non-zero,
   1734 	** but this is no time for a treasure hunt.
   1735 	*/
   1736 	if (result)
   1737 		result->TM_ZONE = offset ? __UNCONST(wildabbr) : gmtptr ?
   1738 		    gmtptr->chars : __UNCONST(gmt);
   1739 #endif /* defined TM_ZONE */
   1740 	return result;
   1741 }
   1742 
   1743 /*
   1744 * Re-entrant version of gmtime.
   1745 */
   1746 
   1747 struct tm *
   1748 gmtime_r(const time_t *timep, struct tm *tmp)
   1749 {
   1750   gmtcheck();
   1751   return gmtsub(NULL, timep, 0, tmp);
   1752 }
   1753 
   1754 struct tm *
   1755 gmtime(const time_t *timep)
   1756 {
   1757   return gmtime_r(timep, &tm);
   1758 }
   1759 
   1760 #ifdef STD_INSPIRED
   1761 
   1762 struct tm *
   1763 offtime(const time_t *timep, long offset)
   1764 {
   1765   gmtcheck();
   1766   return gmtsub(gmtptr, timep, (int_fast32_t)offset, &tm);
   1767 }
   1768 
   1769 struct tm *
   1770 offtime_r(const time_t *timep, long offset, struct tm *tmp)
   1771 {
   1772 	gmtcheck();
   1773 	return gmtsub(NULL, timep, (int_fast32_t)offset, tmp);
   1774 }
   1775 
   1776 #endif /* defined STD_INSPIRED */
   1777 
   1778 #if TZ_TIME_T
   1779 
   1780 # if USG_COMPAT
   1781 #  define daylight 0
   1782 #  define timezone 0
   1783 # endif
   1784 # if !ALTZONE
   1785 #  define altzone 0
   1786 # endif
   1787 
   1788 /* Convert from the underlying system's time_t to the ersatz time_tz,
   1789    which is called 'time_t' in this file.  Typically, this merely
   1790    converts the time's integer width.  On some platforms, the system
   1791    time is local time not UT, or uses some epoch other than the POSIX
   1792    epoch.
   1793 
   1794    Although this code appears to define a function named 'time' that
   1795    returns time_t, the macros in private.h cause this code to actually
   1796    define a function named 'tz_time' that returns tz_time_t.  The call
   1797    to sys_time invokes the underlying system's 'time' function.  */
   1798 
   1799 time_t
   1800 time(time_t *p)
   1801 {
   1802   __time_t r = sys_time(0);
   1803   if (r != (time_t) -1) {
   1804     int_fast32_t offset = EPOCH_LOCAL ? (daylight ? timezone : altzone) : 0;
   1805     if (increment_overflow32(&offset, -EPOCH_OFFSET)
   1806 	|| increment_overflow_time(&r, offset)) {
   1807       errno = EOVERFLOW;
   1808       r = -1;
   1809     }
   1810   }
   1811   if (p)
   1812     *p = (time_t)r;
   1813   return (time_t)r;
   1814 }
   1815 #endif
   1816 
   1817 /*
   1818 ** Return the number of leap years through the end of the given year
   1819 ** where, to make the math easy, the answer for year zero is defined as zero.
   1820 */
   1821 
   1822 static time_t
   1823 leaps_thru_end_of_nonneg(time_t y)
   1824 {
   1825   return y / 4 - y / 100 + y / 400;
   1826 }
   1827 
   1828 static time_t
   1829 leaps_thru_end_of(time_t y)
   1830 {
   1831   return (y < 0
   1832 	  ? -1 - leaps_thru_end_of_nonneg(-1 - y)
   1833 	  : leaps_thru_end_of_nonneg(y));
   1834 }
   1835 
   1836 static struct tm *
   1837 timesub(const time_t *timep, int_fast32_t offset,
   1838 	const struct state *sp, struct tm *tmp)
   1839 {
   1840 	register const struct lsinfo *	lp;
   1841 	register time_t			tdays;
   1842 	register const int *		ip;
   1843 	register int_fast32_t		corr;
   1844 	register int			i;
   1845 	int_fast32_t idays, rem, dayoff, dayrem;
   1846 	time_t y;
   1847 
   1848 	/* If less than SECSPERMIN, the number of seconds since the
   1849 	   most recent positive leap second; otherwise, do not add 1
   1850 	   to localtime tm_sec because of leap seconds.  */
   1851 	time_t secs_since_posleap = SECSPERMIN;
   1852 
   1853 	corr = 0;
   1854 	i = (sp == NULL) ? 0 : sp->leapcnt;
   1855 	while (--i >= 0) {
   1856 		lp = &sp->lsis[i];
   1857 		if (*timep >= lp->ls_trans) {
   1858 			corr = lp->ls_corr;
   1859 			if ((i == 0 ? 0 : lp[-1].ls_corr) < corr)
   1860 			  secs_since_posleap = *timep - lp->ls_trans;
   1861 			break;
   1862 		}
   1863 	}
   1864 
   1865 	/* Calculate the year, avoiding integer overflow even if
   1866 	   time_t is unsigned.  */
   1867 	tdays = (time_t)(*timep / SECSPERDAY);
   1868 	rem = (int)(*timep % SECSPERDAY);
   1869 	rem += offset % SECSPERDAY - corr % SECSPERDAY + 3 * SECSPERDAY;
   1870 	dayoff = offset / SECSPERDAY - corr / SECSPERDAY + rem / SECSPERDAY - 3;
   1871 	rem %= SECSPERDAY;
   1872 	/* y = (EPOCH_YEAR
   1873 	        + floor((tdays + dayoff) / DAYSPERREPEAT) * YEARSPERREPEAT),
   1874 	   sans overflow.  But calculate against 1570 (EPOCH_YEAR -
   1875 	   YEARSPERREPEAT) instead of against 1970 so that things work
   1876 	   for localtime values before 1970 when time_t is unsigned.  */
   1877 	dayrem = (int)(tdays % DAYSPERREPEAT);
   1878 	dayrem += dayoff % DAYSPERREPEAT;
   1879 	y = (EPOCH_YEAR - YEARSPERREPEAT
   1880 	     + ((1 + dayoff / DAYSPERREPEAT + dayrem / DAYSPERREPEAT
   1881 		 - ((dayrem % DAYSPERREPEAT) < 0)
   1882 		 + tdays / DAYSPERREPEAT)
   1883 		* YEARSPERREPEAT));
   1884 	/* idays = (tdays + dayoff) mod DAYSPERREPEAT, sans overflow.  */
   1885 	idays = (int)(tdays % DAYSPERREPEAT);
   1886 	idays += dayoff % DAYSPERREPEAT + 2 * DAYSPERREPEAT;
   1887 	idays %= DAYSPERREPEAT;
   1888 	/* Increase Y and decrease IDAYS until IDAYS is in range for Y.  */
   1889 	while (year_lengths[isleap(y)] <= idays) {
   1890 		int tdelta = idays / DAYSPERLYEAR;
   1891 		int_fast32_t ydelta = tdelta + !tdelta;
   1892 		time_t newy = y + ydelta;
   1893 		register int	leapdays;
   1894 		leapdays = (int)(leaps_thru_end_of(newy - 1) -
   1895 			leaps_thru_end_of(y - 1));
   1896 		idays -= ydelta * DAYSPERNYEAR;
   1897 		idays -= leapdays;
   1898 		y = newy;
   1899 	}
   1900 
   1901 	if (!TYPE_SIGNED(time_t) && y < TM_YEAR_BASE) {
   1902 	  int signed_y = (int)y;
   1903 	  tmp->tm_year = signed_y - TM_YEAR_BASE;
   1904 	} else if ((!TYPE_SIGNED(time_t) || INT_MIN + TM_YEAR_BASE <= y)
   1905 		   && y - TM_YEAR_BASE <= INT_MAX)
   1906 	  tmp->tm_year = (int)(y - TM_YEAR_BASE);
   1907 	else {
   1908 	  errno = EOVERFLOW;
   1909 	  return NULL;
   1910 	}
   1911 	tmp->tm_yday = idays;
   1912 	/*
   1913 	** The "extra" mods below avoid overflow problems.
   1914 	*/
   1915 	tmp->tm_wday = (int)(TM_WDAY_BASE
   1916 			+ ((tmp->tm_year % DAYSPERWEEK)
   1917 			   * (DAYSPERNYEAR % DAYSPERWEEK))
   1918 			+ leaps_thru_end_of(y - 1)
   1919 			- leaps_thru_end_of(TM_YEAR_BASE - 1)
   1920 			+ idays);
   1921 	tmp->tm_wday %= DAYSPERWEEK;
   1922 	if (tmp->tm_wday < 0)
   1923 		tmp->tm_wday += DAYSPERWEEK;
   1924 	tmp->tm_hour = (int) (rem / SECSPERHOUR);
   1925 	rem %= SECSPERHOUR;
   1926 	tmp->tm_min = rem / SECSPERMIN;
   1927 	tmp->tm_sec = rem % SECSPERMIN;
   1928 
   1929 	/* Use "... ??:??:60" at the end of the localtime minute containing
   1930 	   the second just before the positive leap second.  */
   1931 	tmp->tm_sec += secs_since_posleap <= tmp->tm_sec;
   1932 
   1933 	ip = mon_lengths[isleap(y)];
   1934 	for (tmp->tm_mon = 0; idays >= ip[tmp->tm_mon]; ++(tmp->tm_mon))
   1935 		idays -= ip[tmp->tm_mon];
   1936 	tmp->tm_mday = idays + 1;
   1937 	tmp->tm_isdst = 0;
   1938 #ifdef TM_GMTOFF
   1939 	tmp->TM_GMTOFF = offset;
   1940 #endif /* defined TM_GMTOFF */
   1941 	return tmp;
   1942 }
   1943 
   1944 char *
   1945 ctime(const time_t *timep)
   1946 {
   1947 /*
   1948 ** Section 4.12.3.2 of X3.159-1989 requires that
   1949 **	The ctime function converts the calendar time pointed to by timer
   1950 **	to local time in the form of a string. It is equivalent to
   1951 **		asctime(localtime(timer))
   1952 */
   1953   struct tm *tmp = localtime(timep);
   1954   return tmp ? asctime(tmp) : NULL;
   1955 }
   1956 
   1957 char *
   1958 ctime_r(const time_t *timep, char *buf)
   1959 {
   1960   struct tm mytm;
   1961   struct tm *tmp = localtime_r(timep, &mytm);
   1962   return tmp ? asctime_r(tmp, buf) : NULL;
   1963 }
   1964 
   1965 char *
   1966 ctime_rz(const timezone_t sp, const time_t * timep, char *buf)
   1967 {
   1968 	struct tm	mytm, *rtm;
   1969 
   1970 	rtm = localtime_rz(sp, timep, &mytm);
   1971 	if (rtm == NULL)
   1972 		return NULL;
   1973 	return asctime_r(rtm, buf);
   1974 }
   1975 
   1976 /*
   1977 ** Adapted from code provided by Robert Elz, who writes:
   1978 **	The "best" way to do mktime I think is based on an idea of Bob
   1979 **	Kridle's (so its said...) from a long time ago.
   1980 **	It does a binary search of the time_t space. Since time_t's are
   1981 **	just 32 bits, its a max of 32 iterations (even at 64 bits it
   1982 **	would still be very reasonable).
   1983 */
   1984 
   1985 #ifndef WRONG
   1986 #define WRONG	((time_t)-1)
   1987 #endif /* !defined WRONG */
   1988 
   1989 /*
   1990 ** Normalize logic courtesy Paul Eggert.
   1991 */
   1992 
   1993 static bool
   1994 increment_overflow(int *ip, int j)
   1995 {
   1996 	register int const	i = *ip;
   1997 
   1998 	/*
   1999 	** If i >= 0 there can only be overflow if i + j > INT_MAX
   2000 	** or if j > INT_MAX - i; given i >= 0, INT_MAX - i cannot overflow.
   2001 	** If i < 0 there can only be overflow if i + j < INT_MIN
   2002 	** or if j < INT_MIN - i; given i < 0, INT_MIN - i cannot overflow.
   2003 	*/
   2004 	if ((i >= 0) ? (j > INT_MAX - i) : (j < INT_MIN - i))
   2005 		return true;
   2006 	*ip += j;
   2007 	return false;
   2008 }
   2009 
   2010 static bool
   2011 increment_overflow32(int_fast32_t *const lp, int const m)
   2012 {
   2013 	register int_fast32_t const	l = *lp;
   2014 
   2015 	if ((l >= 0) ? (m > INT_FAST32_MAX - l) : (m < INT_FAST32_MIN - l))
   2016 		return true;
   2017 	*lp += m;
   2018 	return false;
   2019 }
   2020 
   2021 static bool
   2022 increment_overflow_time(__time_t *tp, int_fast32_t j)
   2023 {
   2024 	/*
   2025 	** This is like
   2026 	** 'if (! (TIME_T_MIN <= *tp + j && *tp + j <= TIME_T_MAX)) ...',
   2027 	** except that it does the right thing even if *tp + j would overflow.
   2028 	*/
   2029 	if (! (j < 0
   2030 	       ? (TYPE_SIGNED(time_t) ? TIME_T_MIN - j <= *tp : -1 - j < *tp)
   2031 	       : *tp <= TIME_T_MAX - j))
   2032 		return true;
   2033 	*tp += j;
   2034 	return false;
   2035 }
   2036 
   2037 static bool
   2038 normalize_overflow(int *const tensptr, int *const unitsptr, const int base)
   2039 {
   2040 	register int	tensdelta;
   2041 
   2042 	tensdelta = (*unitsptr >= 0) ?
   2043 		(*unitsptr / base) :
   2044 		(-1 - (-1 - *unitsptr) / base);
   2045 	*unitsptr -= tensdelta * base;
   2046 	return increment_overflow(tensptr, tensdelta);
   2047 }
   2048 
   2049 static bool
   2050 normalize_overflow32(int_fast32_t *tensptr, int *unitsptr, int base)
   2051 {
   2052 	register int	tensdelta;
   2053 
   2054 	tensdelta = (*unitsptr >= 0) ?
   2055 		(*unitsptr / base) :
   2056 		(-1 - (-1 - *unitsptr) / base);
   2057 	*unitsptr -= tensdelta * base;
   2058 	return increment_overflow32(tensptr, tensdelta);
   2059 }
   2060 
   2061 static int
   2062 tmcomp(register const struct tm *const atmp,
   2063        register const struct tm *const btmp)
   2064 {
   2065 	register int	result;
   2066 
   2067 	if (atmp->tm_year != btmp->tm_year)
   2068 		return atmp->tm_year < btmp->tm_year ? -1 : 1;
   2069 	if ((result = (atmp->tm_mon - btmp->tm_mon)) == 0 &&
   2070 		(result = (atmp->tm_mday - btmp->tm_mday)) == 0 &&
   2071 		(result = (atmp->tm_hour - btmp->tm_hour)) == 0 &&
   2072 		(result = (atmp->tm_min - btmp->tm_min)) == 0)
   2073 			result = atmp->tm_sec - btmp->tm_sec;
   2074 	return result;
   2075 }
   2076 
   2077 static time_t
   2078 time2sub(struct tm *const tmp,
   2079 	 struct tm *(*funcp)(struct state const *, time_t const *,
   2080 			     int_fast32_t, struct tm *),
   2081 	 struct state const *sp,
   2082 	 const int_fast32_t offset,
   2083 	 bool *okayp,
   2084 	 bool do_norm_secs)
   2085 {
   2086 	register int			dir;
   2087 	register int			i, j;
   2088 	register int			saved_seconds;
   2089 	register int_fast32_t		li;
   2090 	register time_t			lo;
   2091 	register time_t			hi;
   2092 #ifdef NO_ERROR_IN_DST_GAP
   2093 	time_t				ilo;
   2094 #endif
   2095 	int_fast32_t			y;
   2096 	time_t				newt;
   2097 	time_t				t;
   2098 	struct tm			yourtm, mytm;
   2099 
   2100 	*okayp = false;
   2101 	yourtm = *tmp;
   2102 #ifdef NO_ERROR_IN_DST_GAP
   2103 again:
   2104 #endif
   2105 	if (do_norm_secs) {
   2106 		if (normalize_overflow(&yourtm.tm_min, &yourtm.tm_sec,
   2107 		    SECSPERMIN))
   2108 			goto out_of_range;
   2109 	}
   2110 	if (normalize_overflow(&yourtm.tm_hour, &yourtm.tm_min, MINSPERHOUR))
   2111 		goto out_of_range;
   2112 	if (normalize_overflow(&yourtm.tm_mday, &yourtm.tm_hour, HOURSPERDAY))
   2113 		goto out_of_range;
   2114 	y = yourtm.tm_year;
   2115 	if (normalize_overflow32(&y, &yourtm.tm_mon, MONSPERYEAR))
   2116 		goto out_of_range;
   2117 	/*
   2118 	** Turn y into an actual year number for now.
   2119 	** It is converted back to an offset from TM_YEAR_BASE later.
   2120 	*/
   2121 	if (increment_overflow32(&y, TM_YEAR_BASE))
   2122 		goto out_of_range;
   2123 	while (yourtm.tm_mday <= 0) {
   2124 		if (increment_overflow32(&y, -1))
   2125 			goto out_of_range;
   2126 		li = y + (1 < yourtm.tm_mon);
   2127 		yourtm.tm_mday += year_lengths[isleap(li)];
   2128 	}
   2129 	while (yourtm.tm_mday > DAYSPERLYEAR) {
   2130 		li = y + (1 < yourtm.tm_mon);
   2131 		yourtm.tm_mday -= year_lengths[isleap(li)];
   2132 		if (increment_overflow32(&y, 1))
   2133 			goto out_of_range;
   2134 	}
   2135 	for ( ; ; ) {
   2136 		i = mon_lengths[isleap(y)][yourtm.tm_mon];
   2137 		if (yourtm.tm_mday <= i)
   2138 			break;
   2139 		yourtm.tm_mday -= i;
   2140 		if (++yourtm.tm_mon >= MONSPERYEAR) {
   2141 			yourtm.tm_mon = 0;
   2142 			if (increment_overflow32(&y, 1))
   2143 				goto out_of_range;
   2144 		}
   2145 	}
   2146 	if (increment_overflow32(&y, -TM_YEAR_BASE))
   2147 		goto out_of_range;
   2148 	if (! (INT_MIN <= y && y <= INT_MAX))
   2149 		goto out_of_range;
   2150 	yourtm.tm_year = (int)y;
   2151 	if (yourtm.tm_sec >= 0 && yourtm.tm_sec < SECSPERMIN)
   2152 		saved_seconds = 0;
   2153 	else if (y + TM_YEAR_BASE < EPOCH_YEAR) {
   2154 		/*
   2155 		** We can't set tm_sec to 0, because that might push the
   2156 		** time below the minimum representable time.
   2157 		** Set tm_sec to 59 instead.
   2158 		** This assumes that the minimum representable time is
   2159 		** not in the same minute that a leap second was deleted from,
   2160 		** which is a safer assumption than using 58 would be.
   2161 		*/
   2162 		if (increment_overflow(&yourtm.tm_sec, 1 - SECSPERMIN))
   2163 			goto out_of_range;
   2164 		saved_seconds = yourtm.tm_sec;
   2165 		yourtm.tm_sec = SECSPERMIN - 1;
   2166 	} else {
   2167 		saved_seconds = yourtm.tm_sec;
   2168 		yourtm.tm_sec = 0;
   2169 	}
   2170 	/*
   2171 	** Do a binary search (this works whatever time_t's type is).
   2172 	*/
   2173 	lo = TIME_T_MIN;
   2174 	hi = TIME_T_MAX;
   2175 #ifdef NO_ERROR_IN_DST_GAP
   2176 	ilo = lo;
   2177 #endif
   2178 	for ( ; ; ) {
   2179 		t = lo / 2 + hi / 2;
   2180 		if (t < lo)
   2181 			t = lo;
   2182 		else if (t > hi)
   2183 			t = hi;
   2184 		if (! funcp(sp, &t, offset, &mytm)) {
   2185 			/*
   2186 			** Assume that t is too extreme to be represented in
   2187 			** a struct tm; arrange things so that it is less
   2188 			** extreme on the next pass.
   2189 			*/
   2190 			dir = (t > 0) ? 1 : -1;
   2191 		} else	dir = tmcomp(&mytm, &yourtm);
   2192 		if (dir != 0) {
   2193 			if (t == lo) {
   2194 				if (t == TIME_T_MAX)
   2195 					goto out_of_range;
   2196 				++t;
   2197 				++lo;
   2198 			} else if (t == hi) {
   2199 				if (t == TIME_T_MIN)
   2200 					goto out_of_range;
   2201 				--t;
   2202 				--hi;
   2203 			}
   2204 #ifdef NO_ERROR_IN_DST_GAP
   2205 			if (ilo != lo && lo - 1 == hi && yourtm.tm_isdst < 0 &&
   2206 			    do_norm_secs) {
   2207 				for (i = sp->typecnt - 1; i >= 0; --i) {
   2208 					for (j = sp->typecnt - 1; j >= 0; --j) {
   2209 						time_t off;
   2210 						if (sp->ttis[j].tt_isdst ==
   2211 						    sp->ttis[i].tt_isdst)
   2212 							continue;
   2213 						if (ttunspecified(sp, j))
   2214 							continue;
   2215 						off = sp->ttis[j].tt_utoff -
   2216 						    sp->ttis[i].tt_utoff;
   2217 						yourtm.tm_sec += off < 0 ?
   2218 						    -off : off;
   2219 						goto again;
   2220 					}
   2221 				}
   2222 			}
   2223 #endif
   2224 			if (lo > hi)
   2225 				goto invalid;
   2226 			if (dir > 0)
   2227 				hi = t;
   2228 			else	lo = t;
   2229 			continue;
   2230 		}
   2231 #if defined TM_GMTOFF && ! UNINIT_TRAP
   2232 		if (mytm.TM_GMTOFF != yourtm.TM_GMTOFF
   2233 		    && (yourtm.TM_GMTOFF < 0
   2234 			? (-SECSPERDAY <= yourtm.TM_GMTOFF
   2235 			   && (mytm.TM_GMTOFF <=
   2236 			       (/*CONSTCOND*/SMALLEST(INT_FAST32_MAX, LONG_MAX)
   2237 				+ yourtm.TM_GMTOFF)))
   2238 			: (yourtm.TM_GMTOFF <= SECSPERDAY
   2239 			   && ((/*CONSTCOND*/BIGGEST(INT_FAST32_MIN, LONG_MIN)
   2240 				+ yourtm.TM_GMTOFF)
   2241 			       <= mytm.TM_GMTOFF)))) {
   2242 		  /* MYTM matches YOURTM except with the wrong UT offset.
   2243 		     YOURTM.TM_GMTOFF is plausible, so try it instead.
   2244 		     It's OK if YOURTM.TM_GMTOFF contains uninitialized data,
   2245 		     since the guess gets checked.  */
   2246 		  __time_t altt = t;
   2247 		  int_fast32_t diff = (int_fast32_t)
   2248 		      (mytm.TM_GMTOFF - yourtm.TM_GMTOFF);
   2249 		  if (!increment_overflow_time(&altt, diff)) {
   2250 		    struct tm alttm;
   2251 		    time_t xaltt = (time_t)altt;
   2252 		    if (funcp(sp, &xaltt, offset, &alttm)
   2253 			&& alttm.tm_isdst == mytm.tm_isdst
   2254 			&& alttm.TM_GMTOFF == yourtm.TM_GMTOFF
   2255 			&& tmcomp(&alttm, &yourtm) == 0) {
   2256 		      t = xaltt;
   2257 		      mytm = alttm;
   2258 		    }
   2259 		  }
   2260 		}
   2261 #endif
   2262 		if (yourtm.tm_isdst < 0 || mytm.tm_isdst == yourtm.tm_isdst)
   2263 			break;
   2264 		/*
   2265 		** Right time, wrong type.
   2266 		** Hunt for right time, right type.
   2267 		** It's okay to guess wrong since the guess
   2268 		** gets checked.
   2269 		*/
   2270 		if (sp == NULL)
   2271 			goto invalid;
   2272 		for (i = sp->typecnt - 1; i >= 0; --i) {
   2273 			if (sp->ttis[i].tt_isdst != yourtm.tm_isdst)
   2274 				continue;
   2275 			for (j = sp->typecnt - 1; j >= 0; --j) {
   2276 				if (sp->ttis[j].tt_isdst == yourtm.tm_isdst)
   2277 					continue;
   2278 				newt = (time_t)(t + sp->ttis[j].tt_utoff -
   2279 				    sp->ttis[i].tt_utoff);
   2280 				if (! funcp(sp, &newt, offset, &mytm))
   2281 					continue;
   2282 				if (tmcomp(&mytm, &yourtm) != 0)
   2283 					continue;
   2284 				if (mytm.tm_isdst != yourtm.tm_isdst)
   2285 					continue;
   2286 				/*
   2287 				** We have a match.
   2288 				*/
   2289 				t = newt;
   2290 				goto label;
   2291 			}
   2292 		}
   2293 		goto invalid;
   2294 	}
   2295 label:
   2296 	newt = t + saved_seconds;
   2297 	if ((newt < t) != (saved_seconds < 0))
   2298 		goto out_of_range;
   2299 	t = newt;
   2300 	if (funcp(sp, &t, offset, tmp)) {
   2301 		*okayp = true;
   2302 		return t;
   2303 	}
   2304 out_of_range:
   2305 	errno = EOVERFLOW;
   2306 	return WRONG;
   2307 invalid:
   2308 	errno = EINVAL;
   2309 	return WRONG;
   2310 }
   2311 
   2312 static time_t
   2313 time2(struct tm * const	tmp,
   2314       struct tm *(*funcp)(struct state const *, time_t const *,
   2315 			  int_fast32_t, struct tm *),
   2316       struct state const *sp,
   2317       const int_fast32_t offset,
   2318       bool *okayp)
   2319 {
   2320 	time_t	t;
   2321 
   2322 	/*
   2323 	** First try without normalization of seconds
   2324 	** (in case tm_sec contains a value associated with a leap second).
   2325 	** If that fails, try with normalization of seconds.
   2326 	*/
   2327 	t = time2sub(tmp, funcp, sp, offset, okayp, false);
   2328 	return *okayp ? t : time2sub(tmp, funcp, sp, offset, okayp, true);
   2329 }
   2330 
   2331 static time_t
   2332 time1(struct tm *const tmp,
   2333       struct tm *(*funcp)(struct state const *, time_t const *,
   2334 			  int_fast32_t, struct tm *),
   2335       struct state const *sp,
   2336       const int_fast32_t offset)
   2337 {
   2338 	register time_t			t;
   2339 	register int			samei, otheri;
   2340 	register int			sameind, otherind;
   2341 	register int			i;
   2342 	register int			nseen;
   2343 	int				save_errno;
   2344 	char				seen[TZ_MAX_TYPES];
   2345 	unsigned char			types[TZ_MAX_TYPES];
   2346 	bool				okay;
   2347 
   2348 	if (tmp == NULL) {
   2349 		errno = EINVAL;
   2350 		return WRONG;
   2351 	}
   2352 	if (tmp->tm_isdst > 1)
   2353 		tmp->tm_isdst = 1;
   2354 	save_errno = errno;
   2355 	t = time2(tmp, funcp, sp, offset, &okay);
   2356 	if (okay) {
   2357 		errno = save_errno;
   2358 		return t;
   2359 	}
   2360 	if (tmp->tm_isdst < 0)
   2361 #ifdef PCTS
   2362 		/*
   2363 		** POSIX Conformance Test Suite code courtesy Grant Sullivan.
   2364 		*/
   2365 		tmp->tm_isdst = 0;	/* reset to std and try again */
   2366 #else
   2367 		return t;
   2368 #endif /* !defined PCTS */
   2369 	/*
   2370 	** We're supposed to assume that somebody took a time of one type
   2371 	** and did some math on it that yielded a "struct tm" that's bad.
   2372 	** We try to divine the type they started from and adjust to the
   2373 	** type they need.
   2374 	*/
   2375 	if (sp == NULL) {
   2376 		errno = EINVAL;
   2377 		return WRONG;
   2378 	}
   2379 	for (i = 0; i < sp->typecnt; ++i)
   2380 		seen[i] = false;
   2381 	nseen = 0;
   2382 	for (i = sp->timecnt - 1; i >= 0; --i)
   2383 		if (!seen[sp->types[i]] && !ttunspecified(sp, sp->types[i])) {
   2384 			seen[sp->types[i]] = true;
   2385 			types[nseen++] = sp->types[i];
   2386 		}
   2387 	for (sameind = 0; sameind < nseen; ++sameind) {
   2388 		samei = types[sameind];
   2389 		if (sp->ttis[samei].tt_isdst != tmp->tm_isdst)
   2390 			continue;
   2391 		for (otherind = 0; otherind < nseen; ++otherind) {
   2392 			otheri = types[otherind];
   2393 			if (sp->ttis[otheri].tt_isdst == tmp->tm_isdst)
   2394 				continue;
   2395 			tmp->tm_sec += (int)(sp->ttis[otheri].tt_utoff
   2396 					- sp->ttis[samei].tt_utoff);
   2397 			tmp->tm_isdst = !tmp->tm_isdst;
   2398 			t = time2(tmp, funcp, sp, offset, &okay);
   2399 			if (okay) {
   2400 				errno = save_errno;
   2401 				return t;
   2402 			}
   2403 			tmp->tm_sec -= (int)(sp->ttis[otheri].tt_utoff
   2404 					- sp->ttis[samei].tt_utoff);
   2405 			tmp->tm_isdst = !tmp->tm_isdst;
   2406 		}
   2407 	}
   2408 	errno = EOVERFLOW;
   2409 	return WRONG;
   2410 }
   2411 
   2412 static time_t
   2413 mktime_tzname(timezone_t sp, struct tm *tmp, bool setname)
   2414 {
   2415   if (sp)
   2416     return time1(tmp, localsub, sp, setname);
   2417   else {
   2418     gmtcheck();
   2419     return time1(tmp, gmtsub, gmtptr, 0);
   2420   }
   2421 }
   2422 
   2423 #if NETBSD_INSPIRED
   2424 
   2425 time_t
   2426 mktime_z(timezone_t sp, struct tm *const tmp)
   2427 {
   2428   return mktime_tzname(sp, tmp, false);
   2429 }
   2430 
   2431 #endif
   2432 
   2433 time_t
   2434 mktime(struct tm *tmp)
   2435 {
   2436   time_t t;
   2437 
   2438   rwlock_wrlock(&__lcl_lock);
   2439   tzset_unlocked();
   2440   t = mktime_tzname(__lclptr, tmp, true);
   2441   rwlock_unlock(&__lcl_lock);
   2442   return t;
   2443 }
   2444 
   2445 #ifdef STD_INSPIRED
   2446 
   2447 time_t
   2448 timelocal_z(const timezone_t sp, struct tm *const tmp)
   2449 {
   2450 	if (tmp != NULL)
   2451 		tmp->tm_isdst = -1;	/* in case it wasn't initialized */
   2452 	return mktime_z(sp, tmp);
   2453 }
   2454 
   2455 time_t
   2456 timelocal(struct tm *tmp)
   2457 {
   2458 	if (tmp != NULL)
   2459 		tmp->tm_isdst = -1;	/* in case it wasn't initialized */
   2460 	return mktime(tmp);
   2461 }
   2462 
   2463 time_t
   2464 timegm(struct tm *tmp)
   2465 {
   2466   return timeoff(tmp, 0);
   2467 }
   2468 
   2469 time_t
   2470 timeoff(struct tm *tmp, long offset)
   2471 {
   2472   if (tmp)
   2473     tmp->tm_isdst = 0;
   2474   gmtcheck();
   2475   return time1(tmp, gmtsub, gmtptr, (int_fast32_t)offset);
   2476 }
   2477 
   2478 #endif /* defined STD_INSPIRED */
   2479 
   2480 static int_fast32_t
   2481 leapcorr(struct state const *sp, time_t t)
   2482 {
   2483 	register struct lsinfo const *	lp;
   2484 	register int			i;
   2485 
   2486 	i = sp->leapcnt;
   2487 	while (--i >= 0) {
   2488 		lp = &sp->lsis[i];
   2489 		if (t >= lp->ls_trans)
   2490 			return lp->ls_corr;
   2491 	}
   2492 	return 0;
   2493 }
   2494 
   2495 /* NETBSD_INSPIRED_EXTERN functions are exported to callers if
   2496    NETBSD_INSPIRED is defined, and are private otherwise.  */
   2497 # if NETBSD_INSPIRED
   2498 #  define NETBSD_INSPIRED_EXTERN
   2499 # else
   2500 #  define NETBSD_INSPIRED_EXTERN static
   2501 # endif
   2502 
   2503 /*
   2504 ** IEEE Std 1003.1 (POSIX) says that 536457599
   2505 ** shall correspond to "Wed Dec 31 23:59:59 UTC 1986", which
   2506 ** is not the case if we are accounting for leap seconds.
   2507 ** So, we provide the following conversion routines for use
   2508 ** when exchanging timestamps with POSIX conforming systems.
   2509 */
   2510 
   2511 NETBSD_INSPIRED_EXTERN time_t
   2512 time2posix_z(timezone_t sp, time_t t)
   2513 {
   2514   return (time_t)(t - leapcorr(sp, t));
   2515 }
   2516 
   2517 time_t
   2518 time2posix(time_t t)
   2519 {
   2520   rwlock_wrlock(&__lcl_lock);
   2521   if (!lcl_is_set)
   2522     tzset_unlocked();
   2523   if (__lclptr)
   2524     t = (time_t)(t - leapcorr(__lclptr, t));
   2525   rwlock_unlock(&__lcl_lock);
   2526   return t;
   2527 }
   2528 
   2529 /*
   2530 ** XXX--is the below the right way to conditionalize??
   2531 */
   2532 
   2533 #ifdef STD_INSPIRED
   2534 
   2535 NETBSD_INSPIRED_EXTERN time_t
   2536 posix2time_z(timezone_t sp, time_t t)
   2537 {
   2538 	time_t	x;
   2539 	time_t	y;
   2540 	/*
   2541 	** For a positive leap second hit, the result
   2542 	** is not unique. For a negative leap second
   2543 	** hit, the corresponding time doesn't exist,
   2544 	** so we return an adjacent second.
   2545 	*/
   2546 	x = (time_t)(t + leapcorr(sp, t));
   2547 	y = (time_t)(x - leapcorr(sp, x));
   2548 	if (y < t) {
   2549 		do {
   2550 			x++;
   2551 			y = (time_t)(x - leapcorr(sp, x));
   2552 		} while (y < t);
   2553 		x -= y != t;
   2554 	} else if (y > t) {
   2555 		do {
   2556 			--x;
   2557 			y = (time_t)(x - leapcorr(sp, x));
   2558 		} while (y > t);
   2559 		x += y != t;
   2560 	}
   2561 	return x;
   2562 }
   2563 
   2564 time_t
   2565 posix2time(time_t t)
   2566 {
   2567   rwlock_wrlock(&__lcl_lock);
   2568   if (!lcl_is_set)
   2569     tzset_unlocked();
   2570   if (__lclptr)
   2571     t = posix2time_z(__lclptr, t);
   2572   rwlock_unlock(&__lcl_lock);
   2573   return t;
   2574 }
   2575 
   2576 #endif /* defined STD_INSPIRED */
   2577