#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include "private.h"
#include "tzfile.h"
#include "asterisk/lock.h"
#include "asterisk/localtime.h"
Go to the source code of this file.
Data Structures | |
struct | lsinfo |
leap second information More... | |
struct | rule |
struct | state |
struct | ttinfo |
Defines | |
#define | BIGGEST(a, b) (((a) > (b)) ? (a) : (b)) |
#define | DAY_OF_YEAR 1 |
#define | JULIAN_DAY 0 |
#define | LEAPS_THRU_END_OF(y) ((y) / 4 - (y) / 100 + (y) / 400) |
#define | MONTH_NTH_DAY_OF_WEEK 2 |
#define | MY_TZNAME_MAX 255 |
#define | OPEN_MODE O_RDONLY |
#define | TZ_STRLEN_MAX 255 |
#define | WILDABBR " " |
#define | WRONG (-1) |
Functions | |
char * | ast_ctime (time_t *const timep) const |
char * | ast_ctime_r (time_t *const timep, char *buf) const |
tm * | ast_localtime (time_t *const timep, struct tm *p_tm, const char *const zone) const |
time_t | ast_mktime (struct tm *const tmp, const char *const zone) |
AST_MUTEX_DEFINE_STATIC (gmt_mutex) | |
AST_MUTEX_DEFINE_STATIC (tzsetwall_mutex) | |
AST_MUTEX_DEFINE_STATIC (tzset_mutex) | |
AST_MUTEX_DEFINE_STATIC (lcl_mutex) | |
long | detzcode (const char *const codep) |
const char * | getnum (register const char *strp, int *const nump, const int min, const int max) |
Given a pointer into a time zone string, extract a number from that string. | |
const char * | getoffset (register const char *strp, long *const offsetp) |
Given a pointer into a time zone string, extract an offset, in [+-]hh[:mm[:ss]] form, from the string. | |
const char * | getrule (const char *strp, register struct rule *const rulep) |
Given a pointer into a time zone string, extract a rule in the form date[/time]. See POSIX section 8 for the format of "date" and "time". | |
const char * | getsecs (register const char *strp, long *const secsp) |
Given a pointer into a time zone string, extract a number of seconds, in hh[:mm[:ss]] form, from the string. | |
void | gmtload (struct state *const sp) |
void | gmtsub (time_t *const timep, const long offset, struct tm *const tmp, const char *const zone) const |
int | increment_overflow (int *number, int delta) |
void | localsub (time_t *const timep, const long offset, struct tm *const tmp, const char *const zone) const |
int | normalize_overflow (int *const tensptr, int *const unitsptr, const int base) |
int ast_tzset_basic | P ((const char *name)) |
int ast_tzsetwall_basic | P ((void)) |
int tzparse | P ((const char *name, struct state *sp, int lastditch)) |
int tzload | P ((const char *name, struct state *sp)) |
time_t transtime | P ((time_t janfirst, int year, const struct rule *rulep, long offset)) |
int tmcomp | P ((const struct tm *atmp, const struct tm *btmp)) |
void timesub | P ((const time_t *timep, long offset, const struct state *sp, struct tm *tmp)) |
time_t time2 | P ((struct tm *tmp, void(*funcp) P((const time_t *, long, struct tm *, const char *)), long offset, int *okayp, const char *zone)) |
time_t time1 | P ((struct tm *tmp, void(*funcp) P((const time_t *, long, struct tm *, const char *)), long offset, const char *zone)) |
int normalize_overflow | P ((int *tensptr, int *unitsptr, int base)) |
int increment_overflow | P ((int *number, int delta)) |
void gmtsub | P ((const time_t *timep, long offset, struct tm *tmp, const char *zone)) |
void gmtload | P ((struct state *sp)) |
const char *getrule | P ((const char *strp, struct rule *rulep)) |
const char *getoffset | P ((const char *strp, long *offsetp)) |
const char *getsecs | P ((const char *strp, long *secsp)) |
const char *getnum | P ((const char *strp, int *nump, int min, int max)) |
long detzcode | P ((const char *codep)) |
time_t | time1 (struct tm *const tmp, funcp, const long offset, const char *const zone) |
time_t | time2 (struct tm *const tmp, funcp, const long offset, int *const okayp, const char *const zone) |
void | timesub (time_t *const timep, const long offset, const struct state *const sp, struct tm *const tmp) const |
int | tmcomp (const struct tm *const atmp, const struct tm *const btmp) |
time_t | transtime (time_t janfirst, const int year, const struct rule *const rulep, const long offset) const |
Given the Epoch-relative time of January 1, 00:00:00 GMT, in a year, the year, a rule, and the offset from GMT at the time that rule takes effect, calculate the Epoch-relative time that rule takes effect. | |
int | tzload (register const char *name, register struct state *const sp) |
int | tzparse (char *name, struct state *const sp, const int lastditch) const |
Variables | |
const char | elsieid [] = "@(#)localtime.c 7.57" |
char | gmt [] = "GMT" |
time type information | |
int | gmt_is_set |
state * | gmtptr = NULL |
state * | last_lclptr = NULL |
state * | lclptr = NULL |
const int | mon_lengths [2][MONSPERYEAR] |
char | wildabbr [] = "WILDABBR" |
const int | year_lengths [2] |
POSIX-style TZ environment variable handling from Guy Harris (guy@auspex.com).
Definition in file localtime.c.
|
Definition at line 131 of file localtime.c. |
|
n - day of year Definition at line 164 of file localtime.c. Referenced by transtime(). |
|
Jn - Julian day Definition at line 163 of file localtime.c. Referenced by transtime(). |
|
Referenced by timesub(). |
|
Mm.n.d - month, week, day of week Definition at line 165 of file localtime.c. Referenced by transtime(). |
|
Definition at line 137 of file localtime.c. |
|
Definition at line 77 of file localtime.c. Referenced by tzload(). |
|
Definition at line 43 of file localtime.c. |
|
Definition at line 106 of file localtime.c. |
|
Definition at line 1233 of file localtime.c. |
|
Definition at line 1197 of file localtime.c. 01199 { 01200 /* 01201 ** Section 4.12.3.2 of X3.159-1989 requires that 01202 ** The ctime funciton converts the calendar time pointed to by timer 01203 ** to local time in the form of a string. It is equivalent to 01204 ** asctime(localtime(timer)) 01205 */ 01206 return asctime(localtime(timep)); 01207 }
|
|
Definition at line 1210 of file localtime.c. 01213 { 01214 struct tm tm; 01215 #ifdef SOLARIS 01216 return asctime_r(localtime_r(timep, &tm), buf, 256); 01217 #else 01218 return asctime_r(localtime_r(timep, &tm), buf); 01219 #endif 01220 }
|
|
Definition at line 1046 of file localtime.c. References ast_mutex_lock(), ast_mutex_unlock(), ast_tzset(), and localsub(). Referenced by acf_strftime(), ast_say_date_da(), ast_say_date_de(), ast_say_date_en(), ast_say_date_fr(), ast_say_date_gr(), ast_say_date_nl(), ast_say_date_pt(), ast_say_date_with_format_da(), ast_say_date_with_format_de(), ast_say_date_with_format_en(), ast_say_date_with_format_es(), ast_say_date_with_format_fr(), ast_say_date_with_format_gr(), ast_say_date_with_format_he(), ast_say_date_with_format_it(), ast_say_date_with_format_nl(), ast_say_date_with_format_pt(), ast_say_date_with_format_tw(), iax2_datetime(), main(), sendmail(), sendpage(), and write_metadata(). 01050 { 01051 #ifdef _THREAD_SAFE 01052 ast_mutex_lock(&lcl_mutex); 01053 #endif 01054 ast_tzset(zone); 01055 localsub(timep, 0L, p_tm, zone); 01056 #ifdef _THREAD_SAFE 01057 ast_mutex_unlock(&lcl_mutex); 01058 #endif 01059 return(p_tm); 01060 }
|
|
Definition at line 1490 of file localtime.c. References ast_mutex_lock(), ast_mutex_unlock(), ast_tzset(), localsub(), and time1(). 01493 { 01494 time_t mktime_return_value; 01495 #ifdef _THREAD_SAFE 01496 ast_mutex_lock(&lcl_mutex); 01497 #endif 01498 ast_tzset(zone); 01499 mktime_return_value = time1(tmp, localsub, 0L, zone); 01500 #ifdef _THREAD_SAFE 01501 ast_mutex_unlock(&lcl_mutex); 01502 #endif 01503 return(mktime_return_value); 01504 }
|
|
|
|
|
|
|
|
|
|
Definition at line 227 of file localtime.c. References result. Referenced by tzload(). 00228 { 00229 register long result; 00230 register int i; 00231 00232 result = (codep[0] & 0x80) ? ~0L : 0L; 00233 for (i = 0; i < 4; ++i) 00234 result = (result << 8) | (codep[i] & 0xff); 00235 return result; 00236 }
|
|
Given a pointer into a time zone string, extract a number from that string.
Definition at line 407 of file localtime.c. References is_digit. Referenced by getrule(), and getsecs(). 00408 { 00409 register char c; 00410 register int num; 00411 00412 if (strp == NULL || !is_digit(c = *strp)) 00413 return NULL; 00414 num = 0; 00415 do { 00416 num = num * 10 + (c - '0'); 00417 if (num > max) 00418 return NULL; /* illegal value */ 00419 c = *++strp; 00420 } while (is_digit(c)); 00421 if (num < min) 00422 return NULL; /* illegal value */ 00423 *nump = num; 00424 return strp; 00425 }
|
|
Given a pointer into a time zone string, extract an offset, in [+-]hh[:mm[:ss]] form, from the string.
Definition at line 474 of file localtime.c. References getsecs(). Referenced by tzparse(). 00475 { 00476 register int neg = 0; 00477 00478 if (*strp == '-') { 00479 neg = 1; 00480 ++strp; 00481 } else if (*strp == '+') 00482 ++strp; 00483 strp = getsecs(strp, offsetp); 00484 if (strp == NULL) 00485 return NULL; /* illegal time */ 00486 if (neg) 00487 *offsetp = -*offsetp; 00488 return strp; 00489 }
|
|
Given a pointer into a time zone string, extract a rule in the form date[/time]. See POSIX section 8 for the format of "date" and "time".
Definition at line 498 of file localtime.c. References DAYSPERLYEAR, DAYSPERNYEAR, DAYSPERWEEK, getnum(), getsecs(), is_digit, and MONSPERYEAR. Referenced by tzparse(). 00499 { 00500 if (*strp == 'J') { 00501 /* 00502 ** Julian day. 00503 */ 00504 rulep->r_type = JULIAN_DAY; 00505 ++strp; 00506 strp = getnum(strp, &rulep->r_day, 1, DAYSPERNYEAR); 00507 } else if (*strp == 'M') { 00508 /* 00509 ** Month, week, day. 00510 */ 00511 rulep->r_type = MONTH_NTH_DAY_OF_WEEK; 00512 ++strp; 00513 strp = getnum(strp, &rulep->r_mon, 1, MONSPERYEAR); 00514 if (strp == NULL) 00515 return NULL; 00516 if (*strp++ != '.') 00517 return NULL; 00518 strp = getnum(strp, &rulep->r_week, 1, 5); 00519 if (strp == NULL) 00520 return NULL; 00521 if (*strp++ != '.') 00522 return NULL; 00523 strp = getnum(strp, &rulep->r_day, 0, DAYSPERWEEK - 1); 00524 } else if (is_digit(*strp)) { 00525 /* 00526 ** Day of year. 00527 */ 00528 rulep->r_type = DAY_OF_YEAR; 00529 strp = getnum(strp, &rulep->r_day, 0, DAYSPERLYEAR - 1); 00530 } else return NULL; /* invalid format */ 00531 if (strp == NULL) 00532 return NULL; 00533 if (*strp == '/') { 00534 /* 00535 ** Time specified. 00536 */ 00537 ++strp; 00538 strp = getsecs(strp, &rulep->r_time); 00539 } else rulep->r_time = 2 * SECSPERHOUR; /* default = 2:00:00 */ 00540 return strp; 00541 }
|
|
Given a pointer into a time zone string, extract a number of seconds, in hh[:mm[:ss]] form, from the string.
Definition at line 435 of file localtime.c. References DAYSPERWEEK, getnum(), HOURSPERDAY, MINSPERHOUR, and SECSPERMIN. Referenced by getoffset(), and getrule(). 00436 { 00437 int num; 00438 00439 /* 00440 ** `HOURSPERDAY * DAYSPERWEEK - 1' allows quasi-Posix rules like 00441 ** "M10.4.6/26", which does not conform to Posix, 00442 ** but which specifies the equivalent of 00443 ** ``02:00 on the first Sunday on or after 23 Oct''. 00444 */ 00445 strp = getnum(strp, &num, 0, HOURSPERDAY * DAYSPERWEEK - 1); 00446 if (strp == NULL) 00447 return NULL; 00448 *secsp = num * (long) SECSPERHOUR; 00449 if (*strp == ':') { 00450 ++strp; 00451 strp = getnum(strp, &num, 0, MINSPERHOUR - 1); 00452 if (strp == NULL) 00453 return NULL; 00454 *secsp += num * SECSPERMIN; 00455 if (*strp == ':') { 00456 ++strp; 00457 /* `SECSPERMIN' allows for leap seconds. */ 00458 strp = getnum(strp, &num, 0, SECSPERMIN); 00459 if (strp == NULL) 00460 return NULL; 00461 *secsp += num; 00462 } 00463 } 00464 return strp; 00465 }
|
|
Definition at line 835 of file localtime.c. References gmt, TRUE, tzload(), and tzparse(). Referenced by gmtsub(), and P().
|
|
Definition at line 1067 of file localtime.c. References ast_mutex_lock(), ast_mutex_unlock(), state::chars, gmt_is_set, gmtload(), gmtptr, malloc, and timesub(). Referenced by localsub(). 01072 { 01073 #ifdef _THREAD_SAFE 01074 ast_mutex_lock(&gmt_mutex); 01075 #endif 01076 if (!gmt_is_set) { 01077 gmt_is_set = TRUE; 01078 gmtptr = (struct state *) malloc(sizeof *gmtptr); 01079 if (gmtptr != NULL) 01080 gmtload(gmtptr); 01081 } 01082 ast_mutex_unlock(&gmt_mutex); 01083 timesub(timep, offset, gmtptr, tmp); 01084 #ifdef TM_ZONE 01085 /* 01086 ** Could get fancy here and deliver something such as 01087 ** "GMT+xxxx" or "GMT-xxxx" if offset is non-zero, 01088 ** but this is no time for a treasure hunt. 01089 */ 01090 if (offset != 0) 01091 tmp->TM_ZONE = wildabbr; 01092 else { 01093 if (gmtptr == NULL) 01094 tmp->TM_ZONE = gmt; 01095 else tmp->TM_ZONE = gmtptr->chars; 01096 } 01097 #endif /* defined TM_ZONE */ 01098 }
|
|
Definition at line 1241 of file localtime.c. Referenced by normalize_overflow(), and time2(). 01244 { 01245 int number0; 01246 01247 number0 = *number; 01248 *number += delta; 01249 return (*number < number0) != (delta < 0); 01250 }
|
|
Definition at line 979 of file localtime.c. References ast_tzsetwall(), state::ats, state::chars, gmtsub(), state::name, state::next, state::timecnt, timesub(), ttinfo::tt_abbrind, ttinfo::tt_gmtoff, ttinfo::tt_isdst, state::ttis, state::typecnt, and state::types. Referenced by ast_localtime(), and ast_mktime(). 00984 { 00985 register struct state * sp; 00986 register const struct ttinfo * ttisp; 00987 register int i; 00988 const time_t t = *timep; 00989 00990 sp = lclptr; 00991 /* Find the right zone record */ 00992 if (zone == NULL) 00993 sp = NULL; 00994 else 00995 while (sp != NULL) { 00996 if (!strcmp(sp->name,zone)) 00997 break; 00998 sp = sp->next; 00999 } 01000 01001 if (sp == NULL) { 01002 ast_tzsetwall(); 01003 sp = lclptr; 01004 /* Find the default zone record */ 01005 while (sp != NULL) { 01006 if (sp->name[0] == '\0') 01007 break; 01008 sp = sp->next; 01009 } 01010 } 01011 01012 /* Last ditch effort, use GMT */ 01013 if (sp == NULL) { 01014 gmtsub(timep, offset, tmp, zone); 01015 return; 01016 } 01017 if (sp->timecnt == 0 || t < sp->ats[0]) { 01018 i = 0; 01019 while (sp->ttis[i].tt_isdst) 01020 if (++i >= sp->typecnt) { 01021 i = 0; 01022 break; 01023 } 01024 } else { 01025 for (i = 1; i < sp->timecnt; ++i) 01026 if (t < sp->ats[i]) 01027 break; 01028 i = sp->types[i - 1]; 01029 } 01030 ttisp = &sp->ttis[i]; 01031 /* 01032 ** To get (wrong) behavior that's compatible with System V Release 2.0 01033 ** you'd replace the statement below with 01034 ** t += ttisp->tt_gmtoff; 01035 ** timesub(&t, 0L, sp, tmp); 01036 */ 01037 timesub(&t, ttisp->tt_gmtoff, sp, tmp); 01038 tmp->tm_isdst = ttisp->tt_isdst; 01039 tzname[tmp->tm_isdst] = &sp->chars[ttisp->tt_abbrind]; 01040 #ifdef TM_ZONE 01041 tmp->TM_ZONE = &sp->chars[ttisp->tt_abbrind]; 01042 #endif /* defined TM_ZONE */ 01043 }
|
|
Definition at line 1253 of file localtime.c. References increment_overflow(). Referenced by time2(). 01257 { 01258 register int tensdelta; 01259 01260 tensdelta = (*unitsptr >= 0) ? 01261 (*unitsptr / base) : 01262 (-1 - (-1 - *unitsptr) / base); 01263 *unitsptr -= tensdelta * base; 01264 return increment_overflow(tensptr, tensdelta); 01265 }
|
|
Definition at line 901 of file localtime.c. References ast_tzset(), ast_tzsetwall(), FALSE, gmt, gmtload(), last_lclptr, lclptr, state::leapcnt, malloc, state::name, name, state::next, state::timecnt, ttinfo::tt_abbrind, ttinfo::tt_gmtoff, state::ttis, tzload(), and tzparse(). 00906 { 00907 struct state *cur_state = lclptr; 00908 00909 /* Not set at all */ 00910 if (name == NULL) { 00911 return ast_tzsetwall(); 00912 } 00913 00914 /* Find the appropriate structure, if already parsed */ 00915 while (cur_state != NULL) { 00916 if (!strcmp(cur_state->name,name)) 00917 break; 00918 cur_state = cur_state->next; 00919 } 00920 if (cur_state != NULL) 00921 return 0; 00922 00923 cur_state = malloc(sizeof(struct state)); 00924 if (cur_state == NULL) { 00925 return -1; 00926 } 00927 memset(cur_state,0,sizeof(*cur_state)); 00928 00929 /* Name is set, but set to the empty string == no adjustments */ 00930 if (name[0] == '\0') { 00931 /* 00932 ** User wants it fast rather than right. 00933 */ 00934 cur_state->leapcnt = 0; /* so, we're off a little */ 00935 cur_state->timecnt = 0; 00936 cur_state->ttis[0].tt_gmtoff = 0; 00937 cur_state->ttis[0].tt_abbrind = 0; 00938 (void) strncpy(cur_state->chars, gmt, sizeof(cur_state->chars) - 1); 00939 } else if (tzload(name, cur_state) != 0) { 00940 if (name[0] == ':') { 00941 (void) gmtload(cur_state); 00942 } else if (tzparse(name, cur_state, FALSE) != 0) { 00943 /* If not found, load localtime */ 00944 if (tzload("/etc/localtime", cur_state) != 0) 00945 /* Last ditch, get GMT */ 00946 (void) gmtload(cur_state); 00947 } 00948 } 00949 strncpy(cur_state->name, name, sizeof(cur_state->name) - 1); 00950 if (last_lclptr) 00951 last_lclptr->next = cur_state; 00952 else 00953 lclptr = cur_state; 00954 last_lclptr = cur_state; 00955 return 0; 00956 }
|
|
Definition at line 849 of file localtime.c. References ast_tzsetwall(), gmtload(), last_lclptr, lclptr, malloc, state::name, state::next, and tzload(). 00854 { 00855 struct state *cur_state = lclptr; 00856 00857 /* Find the appropriate structure, if already parsed */ 00858 while (cur_state != NULL) { 00859 if (cur_state->name[0] == '\0') 00860 break; 00861 cur_state = cur_state->next; 00862 } 00863 if (cur_state != NULL) 00864 return 0; 00865 cur_state = malloc(sizeof(struct state)); 00866 if (cur_state == NULL) { 00867 return -1; 00868 } 00869 memset(cur_state,0,sizeof(struct state)); 00870 if (tzload((char *) NULL, cur_state) != 0) 00871 #ifdef DEBUG 00872 { 00873 fprintf(stderr, "ast_tzsetwall: calling gmtload()\n"); 00874 #endif 00875 gmtload(cur_state); 00876 #ifdef DEBUG 00877 } 00878 #endif 00879 00880 if (last_lclptr) 00881 last_lclptr->next = cur_state; 00882 else 00883 lclptr = cur_state; 00884 last_lclptr = cur_state; 00885 return 0; 00886 }
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Definition at line 1429 of file localtime.c. References lclptr, time2(), ttinfo::tt_gmtoff, ttinfo::tt_isdst, state::ttis, and state::typecnt. Referenced by ast_mktime(). 01434 { 01435 register time_t t; 01436 register const struct state * sp; 01437 register int samei, otheri; 01438 int okay; 01439 01440 if (tmp->tm_isdst > 1) 01441 tmp->tm_isdst = 1; 01442 t = time2(tmp, funcp, offset, &okay, zone); 01443 #ifdef PCTS 01444 /* 01445 ** PCTS code courtesy Grant Sullivan (grant@osf.org). 01446 */ 01447 if (okay) 01448 return t; 01449 if (tmp->tm_isdst < 0) 01450 tmp->tm_isdst = 0; /* reset to std and try again */ 01451 #endif /* defined PCTS */ 01452 #ifndef PCTS 01453 if (okay || tmp->tm_isdst < 0) 01454 return t; 01455 #endif /* !defined PCTS */ 01456 /* 01457 ** We're supposed to assume that somebody took a time of one type 01458 ** and did some math on it that yielded a "struct tm" that's bad. 01459 ** We try to divine the type they started from and adjust to the 01460 ** type they need. 01461 */ 01462 /* 01463 ** The (void *) casts are the benefit of SunOS 3.3 on Sun 2's. 01464 */ 01465 sp = (const struct state *) (((void *) funcp == (void *) localsub) ? 01466 lclptr : gmtptr); 01467 if (sp == NULL) 01468 return WRONG; 01469 for (samei = sp->typecnt - 1; samei >= 0; --samei) { 01470 if (sp->ttis[samei].tt_isdst != tmp->tm_isdst) 01471 continue; 01472 for (otheri = sp->typecnt - 1; otheri >= 0; --otheri) { 01473 if (sp->ttis[otheri].tt_isdst == tmp->tm_isdst) 01474 continue; 01475 tmp->tm_sec += sp->ttis[otheri].tt_gmtoff - 01476 sp->ttis[samei].tt_gmtoff; 01477 tmp->tm_isdst = !tmp->tm_isdst; 01478 t = time2(tmp, funcp, offset, &okay, zone); 01479 if (okay) 01480 return t; 01481 tmp->tm_sec -= sp->ttis[otheri].tt_gmtoff - 01482 sp->ttis[samei].tt_gmtoff; 01483 tmp->tm_isdst = !tmp->tm_isdst; 01484 } 01485 } 01486 return WRONG; 01487 }
|
|
Definition at line 1284 of file localtime.c. References HOURSPERDAY, increment_overflow(), isleap, lclptr, MINSPERHOUR, mon_lengths, MONSPERYEAR, normalize_overflow(), SECSPERMIN, TM_YEAR_BASE, tmcomp(), ttinfo::tt_gmtoff, ttinfo::tt_isdst, state::ttis, TYPE_BIT, TYPE_SIGNED, state::typecnt, and year_lengths. Referenced by time1(). 01290 { 01291 register const struct state * sp; 01292 register int dir; 01293 register int bits; 01294 register int i, j ; 01295 register int saved_seconds; 01296 time_t newt; 01297 time_t t; 01298 struct tm yourtm, mytm; 01299 01300 *okayp = FALSE; 01301 yourtm = *tmp; 01302 if (normalize_overflow(&yourtm.tm_hour, &yourtm.tm_min, MINSPERHOUR)) 01303 return WRONG; 01304 if (normalize_overflow(&yourtm.tm_mday, &yourtm.tm_hour, HOURSPERDAY)) 01305 return WRONG; 01306 if (normalize_overflow(&yourtm.tm_year, &yourtm.tm_mon, MONSPERYEAR)) 01307 return WRONG; 01308 /* 01309 ** Turn yourtm.tm_year into an actual year number for now. 01310 ** It is converted back to an offset from TM_YEAR_BASE later. 01311 */ 01312 if (increment_overflow(&yourtm.tm_year, TM_YEAR_BASE)) 01313 return WRONG; 01314 while (yourtm.tm_mday <= 0) { 01315 if (increment_overflow(&yourtm.tm_year, -1)) 01316 return WRONG; 01317 i = yourtm.tm_year + (1 < yourtm.tm_mon); 01318 yourtm.tm_mday += year_lengths[isleap(i)]; 01319 } 01320 while (yourtm.tm_mday > DAYSPERLYEAR) { 01321 i = yourtm.tm_year + (1 < yourtm.tm_mon); 01322 yourtm.tm_mday -= year_lengths[isleap(i)]; 01323 if (increment_overflow(&yourtm.tm_year, 1)) 01324 return WRONG; 01325 } 01326 for ( ; ; ) { 01327 i = mon_lengths[isleap(yourtm.tm_year)][yourtm.tm_mon]; 01328 if (yourtm.tm_mday <= i) 01329 break; 01330 yourtm.tm_mday -= i; 01331 if (++yourtm.tm_mon >= MONSPERYEAR) { 01332 yourtm.tm_mon = 0; 01333 if (increment_overflow(&yourtm.tm_year, 1)) 01334 return WRONG; 01335 } 01336 } 01337 if (increment_overflow(&yourtm.tm_year, -TM_YEAR_BASE)) 01338 return WRONG; 01339 if (yourtm.tm_year + TM_YEAR_BASE < EPOCH_YEAR) { 01340 /* 01341 ** We can't set tm_sec to 0, because that might push the 01342 ** time below the minimum representable time. 01343 ** Set tm_sec to 59 instead. 01344 ** This assumes that the minimum representable time is 01345 ** not in the same minute that a leap second was deleted from, 01346 ** which is a safer assumption than using 58 would be. 01347 */ 01348 if (increment_overflow(&yourtm.tm_sec, 1 - SECSPERMIN)) 01349 return WRONG; 01350 saved_seconds = yourtm.tm_sec; 01351 yourtm.tm_sec = SECSPERMIN - 1; 01352 } else { 01353 saved_seconds = yourtm.tm_sec; 01354 yourtm.tm_sec = 0; 01355 } 01356 /* 01357 ** Divide the search space in half 01358 ** (this works whether time_t is signed or unsigned). 01359 */ 01360 bits = TYPE_BIT(time_t) - 1; 01361 /* 01362 ** If time_t is signed, then 0 is just above the median, 01363 ** assuming two's complement arithmetic. 01364 ** If time_t is unsigned, then (1 << bits) is just above the median. 01365 */ 01366 t = TYPE_SIGNED(time_t) ? 0 : (((time_t) 1) << bits); 01367 for ( ; ; ) { 01368 (*funcp)(&t, offset, &mytm, zone); 01369 dir = tmcomp(&mytm, &yourtm); 01370 if (dir != 0) { 01371 if (bits-- < 0) 01372 return WRONG; 01373 if (bits < 0) 01374 --t; /* may be needed if new t is minimal */ 01375 else if (dir > 0) 01376 t -= ((time_t) 1) << bits; 01377 else t += ((time_t) 1) << bits; 01378 continue; 01379 } 01380 if (yourtm.tm_isdst < 0 || mytm.tm_isdst == yourtm.tm_isdst) 01381 break; 01382 /* 01383 ** Right time, wrong type. 01384 ** Hunt for right time, right type. 01385 ** It's okay to guess wrong since the guess 01386 ** gets checked. 01387 */ 01388 /* 01389 ** The (void *) casts are the benefit of SunOS 3.3 on Sun 2's. 01390 */ 01391 sp = (const struct state *) 01392 (((void *) funcp == (void *) localsub) ? 01393 lclptr : gmtptr); 01394 if (sp == NULL) 01395 return WRONG; 01396 for (i = sp->typecnt - 1; i >= 0; --i) { 01397 if (sp->ttis[i].tt_isdst != yourtm.tm_isdst) 01398 continue; 01399 for (j = sp->typecnt - 1; j >= 0; --j) { 01400 if (sp->ttis[j].tt_isdst == yourtm.tm_isdst) 01401 continue; 01402 newt = t + sp->ttis[j].tt_gmtoff - 01403 sp->ttis[i].tt_gmtoff; 01404 (*funcp)(&newt, offset, &mytm, zone); 01405 if (tmcomp(&mytm, &yourtm) != 0) 01406 continue; 01407 if (mytm.tm_isdst != yourtm.tm_isdst) 01408 continue; 01409 /* 01410 ** We have a match. 01411 */ 01412 t = newt; 01413 goto label; 01414 } 01415 } 01416 return WRONG; 01417 } 01418 label: 01419 newt = t + saved_seconds; 01420 if ((newt < t) != (saved_seconds < 0)) 01421 return WRONG; 01422 t = newt; 01423 (*funcp)(&t, offset, tmp, zone); 01424 *okayp = TRUE; 01425 return t; 01426 }
|
|
Definition at line 1101 of file localtime.c. References DAYSPERNYEAR, EPOCH_WDAY, isleap, state::leapcnt, LEAPS_THRU_END_OF, lsinfo::ls_corr, lsinfo::ls_trans, mon_lengths, and year_lengths. Referenced by gmtsub(), and localsub(). 01106 { 01107 register const struct lsinfo * lp; 01108 register long days; 01109 register long rem; 01110 register int y; 01111 register int yleap; 01112 register const int * ip; 01113 register long corr; 01114 register int hit; 01115 register int i; 01116 01117 corr = 0; 01118 hit = 0; 01119 i = (sp == NULL) ? 0 : sp->leapcnt; 01120 while (--i >= 0) { 01121 lp = &sp->lsis[i]; 01122 if (*timep >= lp->ls_trans) { 01123 if (*timep == lp->ls_trans) { 01124 hit = ((i == 0 && lp->ls_corr > 0) || 01125 lp->ls_corr > sp->lsis[i - 1].ls_corr); 01126 if (hit) 01127 while (i > 0 && 01128 sp->lsis[i].ls_trans == 01129 sp->lsis[i - 1].ls_trans + 1 && 01130 sp->lsis[i].ls_corr == 01131 sp->lsis[i - 1].ls_corr + 1) { 01132 ++hit; 01133 --i; 01134 } 01135 } 01136 corr = lp->ls_corr; 01137 break; 01138 } 01139 } 01140 days = *timep / SECSPERDAY; 01141 rem = *timep % SECSPERDAY; 01142 #ifdef mc68k 01143 if (*timep == 0x80000000) { 01144 /* 01145 ** A 3B1 muffs the division on the most negative number. 01146 */ 01147 days = -24855; 01148 rem = -11648; 01149 } 01150 #endif /* defined mc68k */ 01151 rem += (offset - corr); 01152 while (rem < 0) { 01153 rem += SECSPERDAY; 01154 --days; 01155 } 01156 while (rem >= SECSPERDAY) { 01157 rem -= SECSPERDAY; 01158 ++days; 01159 } 01160 tmp->tm_hour = (int) (rem / SECSPERHOUR); 01161 rem = rem % SECSPERHOUR; 01162 tmp->tm_min = (int) (rem / SECSPERMIN); 01163 /* 01164 ** A positive leap second requires a special 01165 ** representation. This uses "... ??:59:60" et seq. 01166 */ 01167 tmp->tm_sec = (int) (rem % SECSPERMIN) + hit; 01168 tmp->tm_wday = (int) ((EPOCH_WDAY + days) % DAYSPERWEEK); 01169 if (tmp->tm_wday < 0) 01170 tmp->tm_wday += DAYSPERWEEK; 01171 y = EPOCH_YEAR; 01172 #define LEAPS_THRU_END_OF(y) ((y) / 4 - (y) / 100 + (y) / 400) 01173 while (days < 0 || days >= (long) year_lengths[yleap = isleap(y)]) { 01174 register int newy; 01175 01176 newy = y + days / DAYSPERNYEAR; 01177 if (days < 0) 01178 --newy; 01179 days -= (newy - y) * DAYSPERNYEAR + 01180 LEAPS_THRU_END_OF(newy - 1) - 01181 LEAPS_THRU_END_OF(y - 1); 01182 y = newy; 01183 } 01184 tmp->tm_year = y - TM_YEAR_BASE; 01185 tmp->tm_yday = (int) days; 01186 ip = mon_lengths[yleap]; 01187 for (tmp->tm_mon = 0; days >= (long) ip[tmp->tm_mon]; ++(tmp->tm_mon)) 01188 days = days - (long) ip[tmp->tm_mon]; 01189 tmp->tm_mday = (int) (days + 1); 01190 tmp->tm_isdst = 0; 01191 #ifdef TM_GMTOFF 01192 tmp->TM_GMTOFF = offset; 01193 #endif /* defined TM_GMTOFF */ 01194 }
|
|
Definition at line 1268 of file localtime.c. References result. Referenced by time2(). 01271 { 01272 register int result; 01273 01274 if ((result = (atmp->tm_year - btmp->tm_year)) == 0 && 01275 (result = (atmp->tm_mon - btmp->tm_mon)) == 0 && 01276 (result = (atmp->tm_mday - btmp->tm_mday)) == 0 && 01277 (result = (atmp->tm_hour - btmp->tm_hour)) == 0 && 01278 (result = (atmp->tm_min - btmp->tm_min)) == 0) 01279 result = atmp->tm_sec - btmp->tm_sec; 01280 return result; 01281 }
|
|
Given the Epoch-relative time of January 1, 00:00:00 GMT, in a year, the year, a rule, and the offset from GMT at the time that rule takes effect, calculate the Epoch-relative time that rule takes effect.
Definition at line 549 of file localtime.c. References DAY_OF_YEAR, DAYSPERWEEK, isleap, JULIAN_DAY, m1, mon_lengths, and MONTH_NTH_DAY_OF_WEEK. Referenced by tzparse(). 00554 { 00555 register int leapyear; 00556 register time_t value = 0; 00557 register int i; 00558 int d, m1, yy0, yy1, yy2, dow; 00559 00560 leapyear = isleap(year); 00561 switch (rulep->r_type) { 00562 00563 case JULIAN_DAY: 00564 /* 00565 ** Jn - Julian day, 1 == January 1, 60 == March 1 even in leap 00566 ** years. 00567 ** In non-leap years, or if the day number is 59 or less, just 00568 ** add SECSPERDAY times the day number-1 to the time of 00569 ** January 1, midnight, to get the day. 00570 */ 00571 value = janfirst + (rulep->r_day - 1) * SECSPERDAY; 00572 if (leapyear && rulep->r_day >= 60) 00573 value += SECSPERDAY; 00574 break; 00575 00576 case DAY_OF_YEAR: 00577 /* 00578 ** n - day of year. 00579 ** Just add SECSPERDAY times the day number to the time of 00580 ** January 1, midnight, to get the day. 00581 */ 00582 value = janfirst + rulep->r_day * SECSPERDAY; 00583 break; 00584 00585 case MONTH_NTH_DAY_OF_WEEK: 00586 /* 00587 ** Mm.n.d - nth "dth day" of month m. 00588 */ 00589 value = janfirst; 00590 for (i = 0; i < rulep->r_mon - 1; ++i) 00591 value += mon_lengths[leapyear][i] * SECSPERDAY; 00592 00593 /* 00594 ** Use Zeller's Congruence to get day-of-week of first day of 00595 ** month. 00596 */ 00597 m1 = (rulep->r_mon + 9) % 12 + 1; 00598 yy0 = (rulep->r_mon <= 2) ? (year - 1) : year; 00599 yy1 = yy0 / 100; 00600 yy2 = yy0 % 100; 00601 dow = ((26 * m1 - 2) / 10 + 00602 1 + yy2 + yy2 / 4 + yy1 / 4 - 2 * yy1) % 7; 00603 if (dow < 0) 00604 dow += DAYSPERWEEK; 00605 00606 /* 00607 ** "dow" is the day-of-week of the first day of the month. Get 00608 ** the day-of-month (zero-origin) of the first "dow" day of the 00609 ** month. 00610 */ 00611 d = rulep->r_day - dow; 00612 if (d < 0) 00613 d += DAYSPERWEEK; 00614 for (i = 1; i < rulep->r_week; ++i) { 00615 if (d + DAYSPERWEEK >= 00616 mon_lengths[leapyear][rulep->r_mon - 1]) 00617 break; 00618 d += DAYSPERWEEK; 00619 } 00620 00621 /* 00622 ** "d" is the day-of-month (zero-origin) of the day we want. 00623 */ 00624 value += d * SECSPERDAY; 00625 break; 00626 } 00627 00628 /* 00629 ** "value" is the Epoch-relative time of 00:00:00 GMT on the day in 00630 ** question. To get the Epoch-relative time of the specified local 00631 ** time on that day, add the transition time and the current offset 00632 ** from GMT. 00633 */ 00634 return value + rulep->r_time + offset; 00635 }
|
|
Definition at line 238 of file localtime.c. References state::ats, state::charcnt, detzcode(), FILENAME_MAX, state::leapcnt, lsinfo::ls_corr, lsinfo::ls_trans, name, OPEN_MODE, state::timecnt, TRUE, ttinfo::tt_abbrind, ttinfo::tt_gmtoff, ttinfo::tt_isdst, ttinfo::tt_ttisgmt, ttinfo::tt_ttisstd, state::typecnt, state::types, TZ_MAX_CHARS, TZ_MAX_LEAPS, TZ_MAX_TIMES, TZ_MAX_TYPES, tzhead::tzh_magic, and tzhead::tzh_reserved. Referenced by gmtload(), P(), and tzparse(). 00239 { 00240 register const char * p; 00241 register int i; 00242 register int fid; 00243 00244 #ifdef DEBUG 00245 fprintf(stderr,"tzload called with name=%s, sp=%d\n", name, sp); 00246 #endif 00247 if (name == NULL && (name = TZDEFAULT) == NULL) 00248 return -1; 00249 { 00250 register int doaccess; 00251 struct stat stab; 00252 /* 00253 ** Section 4.9.1 of the C standard says that 00254 ** "FILENAME_MAX expands to an integral constant expression 00255 ** that is the size needed for an array of char large enough 00256 ** to hold the longest file name string that the implementation 00257 ** guarantees can be opened." 00258 */ 00259 char fullname[FILENAME_MAX + 1] = ""; 00260 00261 if (name[0] == ':') 00262 ++name; 00263 doaccess = name[0] == '/'; 00264 if (!doaccess) { 00265 if ((p = TZDIR) == NULL) 00266 return -1; 00267 if ((strlen(p) + 1 + strlen(name) + 1) >= sizeof fullname) 00268 return -1; 00269 (void) strncpy(fullname, p, sizeof(fullname) - 1); 00270 (void) strncat(fullname, "/", sizeof(fullname) - strlen(fullname) - 1); 00271 (void) strncat(fullname, name, sizeof(fullname) - strlen(fullname) - 1); 00272 /* 00273 ** Set doaccess if '.' (as in "../") shows up in name. 00274 */ 00275 if (strchr(name, '.') != NULL) 00276 doaccess = TRUE; 00277 name = fullname; 00278 } 00279 if (doaccess && access(name, R_OK) != 0) 00280 return -1; 00281 if ((fid = open(name, OPEN_MODE)) == -1) 00282 return -1; 00283 if ((fstat(fid, &stab) < 0) || !S_ISREG(stab.st_mode)) { 00284 close(fid); 00285 return -1; 00286 } 00287 } 00288 { 00289 struct tzhead * tzhp; 00290 char buf[sizeof *sp + sizeof *tzhp]; 00291 int ttisstdcnt; 00292 int ttisgmtcnt; 00293 00294 i = read(fid, buf, sizeof buf); 00295 if (close(fid) != 0) 00296 return -1; 00297 p = buf; 00298 p += (sizeof tzhp->tzh_magic) + (sizeof tzhp->tzh_reserved); 00299 ttisstdcnt = (int) detzcode(p); 00300 p += 4; 00301 ttisgmtcnt = (int) detzcode(p); 00302 p += 4; 00303 sp->leapcnt = (int) detzcode(p); 00304 p += 4; 00305 sp->timecnt = (int) detzcode(p); 00306 p += 4; 00307 sp->typecnt = (int) detzcode(p); 00308 p += 4; 00309 sp->charcnt = (int) detzcode(p); 00310 p += 4; 00311 if (sp->leapcnt < 0 || sp->leapcnt > TZ_MAX_LEAPS || 00312 sp->typecnt <= 0 || sp->typecnt > TZ_MAX_TYPES || 00313 sp->timecnt < 0 || sp->timecnt > TZ_MAX_TIMES || 00314 sp->charcnt < 0 || sp->charcnt > TZ_MAX_CHARS || 00315 (ttisstdcnt != sp->typecnt && ttisstdcnt != 0) || 00316 (ttisgmtcnt != sp->typecnt && ttisgmtcnt != 0)) 00317 return -1; 00318 if (i - (p - buf) < sp->timecnt * 4 + /* ats */ 00319 sp->timecnt + /* types */ 00320 sp->typecnt * (4 + 2) + /* ttinfos */ 00321 sp->charcnt + /* chars */ 00322 sp->leapcnt * (4 + 4) + /* lsinfos */ 00323 ttisstdcnt + /* ttisstds */ 00324 ttisgmtcnt) /* ttisgmts */ 00325 return -1; 00326 for (i = 0; i < sp->timecnt; ++i) { 00327 sp->ats[i] = detzcode(p); 00328 p += 4; 00329 } 00330 for (i = 0; i < sp->timecnt; ++i) { 00331 sp->types[i] = (unsigned char) *p++; 00332 if (sp->types[i] >= sp->typecnt) 00333 return -1; 00334 } 00335 for (i = 0; i < sp->typecnt; ++i) { 00336 register struct ttinfo * ttisp; 00337 00338 ttisp = &sp->ttis[i]; 00339 ttisp->tt_gmtoff = detzcode(p); 00340 p += 4; 00341 ttisp->tt_isdst = (unsigned char) *p++; 00342 if (ttisp->tt_isdst != 0 && ttisp->tt_isdst != 1) 00343 return -1; 00344 ttisp->tt_abbrind = (unsigned char) *p++; 00345 if (ttisp->tt_abbrind < 0 || 00346 ttisp->tt_abbrind > sp->charcnt) 00347 return -1; 00348 } 00349 for (i = 0; i < sp->charcnt; ++i) 00350 sp->chars[i] = *p++; 00351 sp->chars[i] = '\0'; /* ensure '\0' at end */ 00352 for (i = 0; i < sp->leapcnt; ++i) { 00353 register struct lsinfo * lsisp; 00354 00355 lsisp = &sp->lsis[i]; 00356 lsisp->ls_trans = detzcode(p); 00357 p += 4; 00358 lsisp->ls_corr = detzcode(p); 00359 p += 4; 00360 } 00361 for (i = 0; i < sp->typecnt; ++i) { 00362 register struct ttinfo * ttisp; 00363 00364 ttisp = &sp->ttis[i]; 00365 if (ttisstdcnt == 0) 00366 ttisp->tt_ttisstd = FALSE; 00367 else { 00368 ttisp->tt_ttisstd = *p++; 00369 if (ttisp->tt_ttisstd != TRUE && 00370 ttisp->tt_ttisstd != FALSE) 00371 return -1; 00372 } 00373 } 00374 for (i = 0; i < sp->typecnt; ++i) { 00375 register struct ttinfo * ttisp; 00376 00377 ttisp = &sp->ttis[i]; 00378 if (ttisgmtcnt == 0) 00379 ttisp->tt_ttisgmt = FALSE; 00380 else { 00381 ttisp->tt_ttisgmt = *p++; 00382 if (ttisp->tt_ttisgmt != TRUE && 00383 ttisp->tt_ttisgmt != FALSE) 00384 return -1; 00385 } 00386 } 00387 } 00388 return 0; 00389 }
|
|
Definition at line 643 of file localtime.c. References EPOCH_YEAR, getoffset(), getrule(), isleap, name, transtime(), TZDEFRULES, tzload(), and year_lengths. Referenced by gmtload(), and P(). 00647 { 00648 const char * stdname; 00649 const char * dstname = NULL; 00650 size_t stdlen = 0; 00651 size_t dstlen = 0; 00652 long stdoffset = 0L; 00653 long dstoffset = 0L; 00654 register time_t * atp; 00655 register unsigned char * typep; 00656 register char * cp; 00657 register int load_result; 00658 00659 stdname = name; 00660 #ifdef DEBUG 00661 fprintf(stderr, "tzparse(): loading default rules\n"); 00662 #endif 00663 load_result = tzload(TZDEFRULES, sp); 00664 if (load_result != 0) 00665 sp->leapcnt = 0; /* so, we're off a little */ 00666 if (*name != '\0') { 00667 if (*name != '\0' && *name != ',' && *name != ';') { 00668 name = getoffset(name, &dstoffset); 00669 if (name == NULL) 00670 return -1; 00671 } else dstoffset = stdoffset - SECSPERHOUR; 00672 if (*name == ',' || *name == ';') { 00673 struct rule start; 00674 struct rule end; 00675 register int year; 00676 register time_t janfirst; 00677 time_t starttime; 00678 time_t endtime; 00679 00680 ++name; 00681 if ((name = getrule(name, &start)) == NULL) 00682 return -1; 00683 if (*name++ != ',') 00684 return -1; 00685 if ((name = getrule(name, &end)) == NULL) 00686 return -1; 00687 if (*name != '\0') 00688 return -1; 00689 sp->typecnt = 2; /* standard time and DST */ 00690 /* 00691 ** Two transitions per year, from EPOCH_YEAR to 2037. 00692 */ 00693 sp->timecnt = 2 * (2037 - EPOCH_YEAR + 1); 00694 if (sp->timecnt > TZ_MAX_TIMES) 00695 return -1; 00696 sp->ttis[0].tt_gmtoff = -dstoffset; 00697 sp->ttis[0].tt_isdst = 1; 00698 sp->ttis[0].tt_abbrind = stdlen + 1; 00699 sp->ttis[1].tt_gmtoff = -stdoffset; 00700 sp->ttis[1].tt_isdst = 0; 00701 sp->ttis[1].tt_abbrind = 0; 00702 atp = sp->ats; 00703 typep = sp->types; 00704 janfirst = 0; 00705 for (year = EPOCH_YEAR; year <= 2037; ++year) { 00706 starttime = transtime(janfirst, year, &start, 00707 stdoffset); 00708 endtime = transtime(janfirst, year, &end, 00709 dstoffset); 00710 if (starttime > endtime) { 00711 *atp++ = endtime; 00712 *typep++ = 1; /* DST ends */ 00713 *atp++ = starttime; 00714 *typep++ = 0; /* DST begins */ 00715 } else { 00716 *atp++ = starttime; 00717 *typep++ = 0; /* DST begins */ 00718 *atp++ = endtime; 00719 *typep++ = 1; /* DST ends */ 00720 } 00721 janfirst += year_lengths[isleap(year)] * 00722 SECSPERDAY; 00723 } 00724 } else { 00725 register long theirstdoffset; 00726 register long theirdstoffset; 00727 register long theiroffset; 00728 register int isdst; 00729 register int i; 00730 register int j; 00731 00732 if (*name != '\0') 00733 return -1; 00734 if (load_result != 0) 00735 return -1; 00736 /* 00737 ** Initial values of theirstdoffset and theirdstoffset. 00738 */ 00739 theirstdoffset = 0; 00740 for (i = 0; i < sp->timecnt; ++i) { 00741 j = sp->types[i]; 00742 if (!sp->ttis[j].tt_isdst) { 00743 theirstdoffset = 00744 -sp->ttis[j].tt_gmtoff; 00745 break; 00746 } 00747 } 00748 theirdstoffset = 0; 00749 for (i = 0; i < sp->timecnt; ++i) { 00750 j = sp->types[i]; 00751 if (sp->ttis[j].tt_isdst) { 00752 theirdstoffset = 00753 -sp->ttis[j].tt_gmtoff; 00754 break; 00755 } 00756 } 00757 /* 00758 ** Initially we're assumed to be in standard time. 00759 */ 00760 isdst = FALSE; 00761 theiroffset = theirstdoffset; 00762 /* 00763 ** Now juggle transition times and types 00764 ** tracking offsets as you do. 00765 */ 00766 for (i = 0; i < sp->timecnt; ++i) { 00767 j = sp->types[i]; 00768 sp->types[i] = sp->ttis[j].tt_isdst; 00769 if (sp->ttis[j].tt_ttisgmt) { 00770 /* No adjustment to transition time */ 00771 } else { 00772 /* 00773 ** If summer time is in effect, and the 00774 ** transition time was not specified as 00775 ** standard time, add the summer time 00776 ** offset to the transition time; 00777 ** otherwise, add the standard time 00778 ** offset to the transition time. 00779 */ 00780 /* 00781 ** Transitions from DST to DDST 00782 ** will effectively disappear since 00783 ** POSIX provides for only one DST 00784 ** offset. 00785 */ 00786 if (isdst && !sp->ttis[j].tt_ttisstd) { 00787 sp->ats[i] += dstoffset - 00788 theirdstoffset; 00789 } else { 00790 sp->ats[i] += stdoffset - 00791 theirstdoffset; 00792 } 00793 } 00794 theiroffset = -sp->ttis[j].tt_gmtoff; 00795 if (sp->ttis[j].tt_isdst) 00796 theirdstoffset = theiroffset; 00797 else theirstdoffset = theiroffset; 00798 } 00799 /* 00800 ** Finally, fill in ttis. 00801 ** ttisstd and ttisgmt need not be handled. 00802 */ 00803 sp->ttis[0].tt_gmtoff = -stdoffset; 00804 sp->ttis[0].tt_isdst = FALSE; 00805 sp->ttis[0].tt_abbrind = 0; 00806 sp->ttis[1].tt_gmtoff = -dstoffset; 00807 sp->ttis[1].tt_isdst = TRUE; 00808 sp->ttis[1].tt_abbrind = stdlen + 1; 00809 } 00810 } else { 00811 dstlen = 0; 00812 sp->typecnt = 1; /* only standard time */ 00813 sp->timecnt = 0; 00814 sp->ttis[0].tt_gmtoff = -stdoffset; 00815 sp->ttis[0].tt_isdst = 0; 00816 sp->ttis[0].tt_abbrind = 0; 00817 } 00818 sp->charcnt = stdlen + 1; 00819 if (dstlen != 0) 00820 sp->charcnt += dstlen + 1; 00821 if (sp->charcnt > sizeof sp->chars) 00822 return -1; 00823 cp = sp->chars; 00824 (void) strncpy(cp, stdname, stdlen); 00825 cp += stdlen; 00826 *cp++ = '\0'; 00827 if (dstlen != 0) { 00828 (void) strncpy(cp, dstname, dstlen); 00829 *(cp + dstlen) = '\0'; 00830 } 00831 return 0; 00832 }
|
|
Definition at line 63 of file localtime.c. |
|
time type information
Definition at line 114 of file localtime.c. |
|
Definition at line 211 of file localtime.c. Referenced by gmtsub(). |
|
Definition at line 205 of file localtime.c. Referenced by gmtsub(). |
|
Definition at line 204 of file localtime.c. Referenced by P(). |
|
Definition at line 203 of file localtime.c. |
|
Initial value: { { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }, { 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 } } Definition at line 391 of file localtime.c. Referenced by time2(), timesub(), and transtime(). |
|
Definition at line 109 of file localtime.c. |
|
Initial value: { DAYSPERNYEAR, DAYSPERLYEAR } Definition at line 396 of file localtime.c. |