update CLib

git-svn-id: svn://kolibrios.org@614 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
Sergey Semyonov (Serge)
2007-08-28 10:31:46 +00:00
parent 52facee6d5
commit 3be3768ce0
98 changed files with 9908 additions and 0 deletions

View File

@@ -0,0 +1,34 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: prototypes for internal time related functions
*
****************************************************************************/
extern int __DontCacheOSTZ( void );
extern int __CacheOSTZ( void );
extern void __parse_tz( char * tz );

View File

@@ -0,0 +1,141 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: __brktime() is an internal function to convert time to struct tm
*
****************************************************************************/
#include "variety.h"
#include <time.h>
#include "thetime.h"
#include "timedata.h"
// #define DAYS_IN_4_YRS ( 365 + 365 + 365 + 366 )
// #define DAYS_IN_400_YRS ( ( 100 * DAYS_IN_4_YRS ) - 3 )
// #define SECONDS_PER_DAY ( 24 * 60 * 60 )
// extern short __diyr[], __dilyr[];
/*
The number of leap years from year 1 to year 1900 is 460.
The number of leap years from year 1 to current year is
expressed by "years/4 - years/100 + years/400". To determine
the number of leap years from current year to 1900, we subtract
460 from the formula result. We do this since "days" is the
number of days since 1900.
*/
static unsigned long __DaysToJan1( unsigned year )
{
unsigned years = 1900 + year - 1;
unsigned leap_days = years / 4 - years / 100 + years / 400 - 460;
return( year * 365UL + leap_days );
}
/* __brktime breaks down a calendar time (clock) into a struct tm t */
struct tm *__brktime( unsigned long days,
time_t wallclock,
long gmtdelta, // localtime - gmtime
struct tm *t )
{
unsigned long secs;
unsigned year;
int day_of_year;
int month;
short const *month_start;
/*
If date is Jan 1, 1970 0:00 to 12:00 UTC and we are west of UTC
then add a day to wallclock, subtract the gmtdelta value, and
decrement the calculated days. This prevents local times
such as "Wed Dec 31 19:00:00 1969 (EST)" from being
erroneously reported as "Sun Feb 6 01:28:16 2106 (EST)"
since (wallclock - gmtdelta) wraps (i.e., wallclock < gmtdelta).
*/
if( wallclock < 12 * 60 * 60UL && gmtdelta > 0 )
wallclock += SECONDS_PER_DAY, days--; /* days compensated for wallclock one day ahead */
wallclock -= ( time_t ) gmtdelta;
days += wallclock / SECONDS_PER_DAY;
secs = wallclock % SECONDS_PER_DAY;
t->tm_hour = ( int ) ( secs / 3600 ) ;
secs = secs % 3600;
t->tm_min = ( int ) ( secs / 60 );
t->tm_sec = secs % 60;
// The following two lines are not needed in the current implementation
// because the range of values for days does not exceed DAYS_IN_400_YRS.
// Even if it did, the algorithm still computes the correct values.
//
// unsigned year400s;
//
// year400s = (days / DAYS_IN_400_YRS) * 400;
// days %= DAYS_IN_400_YRS;
//
// It is OK to reduce days to a value less than DAYS_IN_400_YRS, because
// DAYS_IN_400_YRS is exactly divisible by 7. If it wasn't divisible by 7,
// then the following line which appears at the bottom, should be computed
// before the value of days is range reduced.
// t->tm_wday = (days + 1) % 7; /* 24-sep-92 */
//
year = days / 365;
day_of_year = ( int ) ( days - __DaysToJan1( year ) );
while( day_of_year < 0 ) {
--year;
day_of_year += __leapyear( year + 1900 ) + 365;
}
// year += year400s;
t->tm_yday = day_of_year;
t->tm_year = ( int ) year;
month_start = __diyr;
if( __leapyear( year + 1900 ) )
month_start = __dilyr;
month = day_of_year / 31; /* approximate month */
if( day_of_year >= month_start[month + 1] )
++month;
t->tm_mon = month;
t->tm_mday = day_of_year - month_start[month] + 1;
/* Calculate the day of the week */
/* Jan 1,1900 is a Monday */
t->tm_wday = ( days + 1 ) % 7; /* 24-sep-92 */
return( t );
}
_WCRTLINK struct tm *_gmtime( const time_t *timer, struct tm *tm )
{
tm->tm_isdst = 0; /* assume not */
return __brktime( DAYS_FROM_1900_TO_1970, *timer, 0L, tm );
}
_WCRTLINK struct tm *gmtime( const time_t *timer )
{
_INITTHETIME;
return( _gmtime( timer, &_THE_TIME ) );
}

View File

@@ -0,0 +1,77 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: Check if a year is a leap year + associated arrays
*
****************************************************************************/
#include "variety.h"
#include <time.h>
#include "rtdata.h"
#include "timedata.h"
short const __based(__segname("_CONST")) __diyr[] = { /* days in normal year array */
0, /* Jan */
31, /* Feb */
31 + 28, /* Mar */
31 + 28 + 31, /* Apr */
31 + 28 + 31 + 30, /* May */
31 + 28 + 31 + 30 + 31, /* Jun */
31 + 28 + 31 + 30 + 31 + 30, /* Jul */
31 + 28 + 31 + 30 + 31 + 30 + 31, /* Aug */
31 + 28 + 31 + 30 + 31 + 30 + 31 + 31, /* Sep */
31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30, /* Oct */
31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31, /* Nov */
31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30, /* Dec */
31 + 28 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30 + 31 /* Jan, next year */
};
short const __based(__segname("_CONST")) __dilyr[] = { /* days in leap year array */
0, /* Jan */
31, /* Feb */
31 + 29, /* Mar */
31 + 29 + 31, /* Apr */
31 + 29 + 31 + 30, /* May */
31 + 29 + 31 + 30 + 31, /* Jun */
31 + 29 + 31 + 30 + 31 + 30, /* Jul */
31 + 29 + 31 + 30 + 31 + 30 + 31, /* Aug */
31 + 29 + 31 + 30 + 31 + 30 + 31 + 31, /* Sep */
31 + 29 + 31 + 30 + 31 + 30 + 31 + 31 + 30, /* Oct */
31 + 29 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31, /* Nov */
31 + 29 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30, /* Dec */
31 + 29 + 31 + 30 + 31 + 30 + 31 + 31 + 30 + 31 + 30 + 31 /* Jan, next year */
};
int __leapyear( unsigned year )
{
if( year & 3 )
return( 0 );
if( ( year % 100 ) != 0 )
return( 1 );
if( ( year % 400 ) == 0 )
return( 1 );
return( 0 );
}

View File

@@ -0,0 +1,59 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: _localtime() converts time_t to struct tm
*
****************************************************************************/
#include "variety.h"
#include <time.h>
#include "rtdata.h"
#include "thetime.h"
#include "timedata.h"
_WCRTLINK struct tm *_localtime( const time_t *timer, struct tm *t )
{
time_t tod;
tzset();
tod = *timer;
t->tm_isdst = -1;
#ifdef __LINUX__
__check_tzfile( tod, t );
#endif
__brktime( DAYS_FROM_1900_TO_1970, tod, _RWD_timezone, t );
if( __isindst( t ) )
__brktime( DAYS_FROM_1900_TO_1970, tod,
_RWD_timezone - _RWD_dst_adjust, t );
return( t );
}
_WCRTLINK struct tm *localtime( const time_t *timer )
{
_INITTHETIME;
return _localtime( timer, &_THE_TIME );
}

View File

@@ -0,0 +1,103 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: mktime() without timezone and struct tm fields adjustment.
* used by mktime() and DOS clock()
*
****************************************************************************/
#include "variety.h"
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <limits.h>
#include "rtdata.h"
#include "timedata.h"
#define MONTH_YR ( 12 )
#define DAY_YR ( 365 )
#define HOUR_YR ( DAY_YR * 24 )
#define MINUTE_YR ( HOUR_YR * 60 )
#define SECOND_YR ( MINUTE_YR * 60 )
#define __MONTHS ( INT_MIN / MONTH_YR )
#define __DAYS ( INT_MIN / DAY_YR )
// these ones can underflow in 16bit environments,
// so check the relative values first
#if ( HOUR_YR ) < ( INT_MAX / 60 )
#define __MINUTES ( INT_MIN / MINUTE_YR )
#if ( MINUTE_YR ) < ( INT_MAX / 60 )
#define __SECONDS ( INT_MIN / SECOND_YR )
#else
#define __SECONDS ( 0 )
#endif
#else
#define __MINUTES ( 0 )
#define __SECONDS ( 0 )
#endif
#define SMALLEST_YEAR_VALUE ( __MONTHS + __DAYS + __MINUTES + __SECONDS )
time_t __local_mktime( const struct tm *t, long *pdays, long *pseconds )
{
int month;
int year;
long days;
long seconds;
short const *month_start;
month_start = __diyr;
month = t->tm_mon % 12; /* put tm_mon into range */
year = t->tm_year;
if( year < SMALLEST_YEAR_VALUE )
return( ( time_t ) -1 );
year += t->tm_mon / 12;
while( month < 0 )
--year, month += 12;
if( year < 0 )
return( ( time_t ) -1 );
if( __leapyear( ( unsigned ) ( year + 1900 ) ) )
month_start = __dilyr;
days = year * 365L /* # of days in the years */
+ ( ( year + 3 ) / 4 ) /* add # of leap years before year */
- ( ( year + 99 ) / 100 ) /* sub # of leap centuries */
+ ( ( year + 399 - 100 ) / 400 ) /* add # of leap 4 centuries */
/* adjust for 1900 offset */
/* note: -100 == 300 (mod 400) */
+ month_start[month] /* # of days to 1st of month*/
+ t->tm_mday - 1; /* day of the month */
seconds = ( ( ( long ) ( t->tm_hour ) ) *60L + ( long ) ( t->tm_min ) ) *60L + t->tm_sec;
/* seconds needs to be positive for __brktime */
while( seconds < 0 )
days -= 1, seconds += ( long ) SECONDS_PER_DAY;
while( seconds >= ( long ) SECONDS_PER_DAY )
days += 1, seconds -= ( long ) SECONDS_PER_DAY;
if( days < ( DAYS_FROM_1900_TO_1970 - 1 ) )
return( ( time_t ) -1 );
if ( pdays ) *pdays = days;
if ( pseconds ) *pseconds = seconds;
return( seconds + ( days - DAYS_FROM_1900_TO_1970 ) * ( long ) SECONDS_PER_DAY );
}

View File

@@ -0,0 +1,69 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: Platform independent mktime() implementation.
*
****************************************************************************/
#include "variety.h"
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <limits.h>
#include "rtdata.h"
#include "timedata.h"
_WCRTLINK time_t mktime( struct tm *t )
{
long days;
long seconds;
long day_seconds;
seconds = __local_mktime( t, &days, &day_seconds );
__brktime( (unsigned long) days, (time_t) day_seconds, 0L, t );
tzset();
seconds += _RWD_timezone; /* add in seconds from GMT */
#ifdef __LINUX__
if( t->tm_isdst < 0 )
__check_tzfile( seconds, t );
#endif
/* if we are in d.s.t. then subtract __dst_adjust from seconds */
if( __isindst( t ) ) /* - determine if we are in d.s.t. */
seconds -= _RWD_dst_adjust;
#ifdef __UNIX__ /* time_t is signed */
if( seconds < 0 )
return( ( time_t ) -1 );
#else /* time_t is unsigned, special day check needed for 31 dec 1969 */
/* check for overflow; days == 75277 && seconds == 23296 returns 0, but
adjusted for dst may still be fine */
if( days >= 75279 ||
( seconds >= 0 && days >= 75276 ) ||
( seconds < 0 && days <= DAYS_FROM_1900_TO_1970 ) )
return( (time_t) -1 );
/* 0 is year = 206, mon = 1, mday = 7, hour = 6, min = 28, sec = 16 */
#endif
return( ( time_t ) seconds );
}

View File

@@ -0,0 +1,59 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: WHEN YOU FIGURE OUT WHAT THIS FILE DOES, PLEASE
* DESCRIBE IT HERE!
*
****************************************************************************/
#include "variety.h"
#if defined(__OS2__) || defined(__NT__)
// the OS/2 and NT files are identical
#if defined(__SW_BM)
#include "thread.h"
#define _INITTHETIME
#define _THE_TIME (__THREADDATAPTR->__The_timeP)
#else
static struct tm The_time;
#define _INITTHETIME
#define _THE_TIME The_time
#endif
#else
#ifdef __NETWARE__
#define _INITTHETIME
#define _THE_TIME (__THREADDATAPTR->__The_timeP)
#else
#define _INITTHETIME
static struct tm The_time;
#define _THE_TIME The_time
#endif
#endif

View File

@@ -0,0 +1,49 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: time() returns current time and date
*
****************************************************************************/
#include "variety.h"
#include <stdio.h>
#include <time.h>
#include "timedata.h"
_WCRTLINK time_t time( time_t *timer )
{
auto struct tm t;
time_t seconds;
int milliseconds;
milliseconds = __getctime( &t ); /* get raw time and date */
if( milliseconds >= 500 )
t.tm_sec++;
seconds = mktime( &t );
if( timer != NULL )
*timer = seconds;
return( seconds );
}

View File

@@ -0,0 +1,56 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: Specification of <time.h> internal interfaces.
*
****************************************************************************/
#ifndef TIMEDATA_H_INCLUDED
#define TIMEDATA_H_INCLUDED
#include "variety.h"
#include <time.h>
extern int __dst_adjust;
extern struct tm __start_dst; /* start of daylight savings */
extern struct tm __end_dst; /* end of daylight savings */
#define SECONDS_FROM_1900_TO_1970 2208988800UL
#define SECONDS_PER_DAY ( 24 * 60 * 60UL )
#define DAYS_FROM_1900_TO_1970 ( ( long ) ( SECONDS_FROM_1900_TO_1970 / SECONDS_PER_DAY ) )
extern struct tm *__brktime( unsigned long, time_t, long, struct tm * );
extern time_t __local_mktime( const struct tm *, long *, long * );
extern int __leapyear( unsigned );
extern int __isindst( struct tm * );
extern int __getctime( struct tm * );
extern int __read_tzfile( const char *tz );
extern void __check_tzfile( time_t t, struct tm *timep );
extern short const __based(__segname("_CONST")) __diyr[]; /* days in normal year array */
extern short const __based(__segname("_CONST")) __dilyr[]; /* days in leap year array */
#endif

View File

@@ -0,0 +1,250 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: time utility functions
*
****************************************************************************/
#include "variety.h"
#include <time.h>
#include "rtdata.h"
#include "timedata.h"
static int time_less( const struct tm *t1, const struct tm *t2 );
static int calc_yday( const struct tm *timetm, int year )
{
struct tm tmptm;
int month_days;
int first_wday;
int nth_week;
short const *diyr;
if( timetm->tm_isdst == 0 ) { // M.m.n.d form
diyr = ( __leapyear( ( unsigned ) year + 1900 ) ) ? __dilyr : __diyr;
month_days = diyr[timetm->tm_mon + 1] - diyr[timetm->tm_mon];
tmptm.tm_sec = 0;
tmptm.tm_min = 0;
tmptm.tm_hour = 0;
tmptm.tm_mday = 1;
tmptm.tm_mon = timetm->tm_mon;
tmptm.tm_year = year;
tmptm.tm_isdst = 0;
( void ) mktime( &tmptm );
first_wday = ( timetm->tm_wday - tmptm.tm_wday + 7 ) % 7;
if( timetm->tm_mday == 5 ) {
if( ( 1 + first_wday + ( timetm->tm_mday - 1 ) * 7 ) > month_days )
nth_week = timetm->tm_mday - 2; // fifth req. weekday does not exist
else
nth_week = timetm->tm_mday - 1;
} else
nth_week = timetm->tm_mday - 1;
return( tmptm.tm_yday + first_wday + nth_week * 7 );
}
if( timetm->tm_isdst == 1 ) /* if Jn form */
return( timetm->tm_yday - 1 );
return( timetm->tm_yday );
}
/* determine if in souther hemisphere -> start is after end */
static int check_order( const struct tm *start, const struct tm *end, int year )
{
int start_day;
int end_day;
/* these quick checks should always be enough */
if( ( start->tm_isdst == 0 ) && ( end->tm_isdst == 0 ) ) { // M.m.n.d form
if( start->tm_mon > end->tm_mon )
return( 1 );
if( start->tm_mon < end->tm_mon )
return( 0 );
}
/* start/end of daylight savings time is in the same month (rare case) */
/* these are *expensive* calculations under NT since 2 TZ checks must be done */
start_day = calc_yday( start, year );
end_day = calc_yday( end, year );
if( start_day > end_day )
return( 1 );
return( 0 );
}
/* determine if daylight savings time */
int __isindst( struct tm *t )
{
int month;
int dst;
int n1;
int n2;
int month_days;
int time_check;
int south;
struct tm const *start;
struct tm const *end;
short const *diyr;
// already determined -- if we are sure
if( t->tm_isdst >= 0 )
return( t->tm_isdst );
dst = 0;
// if zone doesn't have a daylight savings period
if( _RWD_daylight == 0 )
return( t->tm_isdst = dst );
// // check for no daylight savings time rule
// if( tzname[1][0] == '\0' ) { // doesn't work since Win32 says
// return( t->tm_isdst = dst );// daylight zone name = standard zone name
// }
south = check_order( &_RWD_start_dst, &_RWD_end_dst, t->tm_year );
if( south ) {
// if southern hemisphere
// invert start and end dates and then invert return value
start = &_RWD_end_dst;
end = &_RWD_start_dst;
} else {
start = &_RWD_start_dst;
end = &_RWD_end_dst;
}
month = t->tm_mon;
diyr = ( __leapyear( ( unsigned ) t->tm_year + 1900 ) ) ? __dilyr : __diyr;
month_days = diyr[month + 1] - diyr[month];
time_check = 0;
/*
* M.m.n.d form
* m = start->tm_mon (month 0-11)
* n = start->tm_mday (n'th week day 1-5)
* d = start->tm_wday (week day 0-6)
*/
if( start->tm_isdst == 0 ) { /* if Mm.n.d form */
if( month > start->tm_mon )
dst = 1; /* assume dst for now */
else if( month == start->tm_mon ) {
/* calculate for current day */
n1 = t->tm_mday - ( t->tm_wday + 7 - start->tm_wday ) % 7;
/* calculate for previous day */
n2 = t->tm_mday - 1 - ( t->tm_wday - 1 + 7 - start->tm_wday ) % 7;
// n_ stands for the day of the month that is past &&
// is closest to today && is the required weekday
if( start->tm_mday == 5 ) {
if( n1 > month_days - 7 ) {
dst = 1; /* assume dst for now */
if( n2 <= month_days - 7 )
time_check = 1;
}
} else {
if( n1 >= 7 * ( start->tm_mday - 1 ) + 1 ) {
dst = 1; /* assume dst for now */
if( n2 < 7 * ( start->tm_mday - 1 ) + 1 )
time_check = 1;
}
}
}
} else {
n1 = start->tm_yday;
if( start->tm_isdst == 1 ) { /* if Jn form */
if( __leapyear( ( unsigned ) t->tm_year + 1900 ) ) {
if( n1 > __diyr[2] )
n1++; /* past Feb 28 */
}
n1--;
}
if( t->tm_yday >= n1 ) {
dst = 1; /* assume dst for now */
if( t->tm_yday == n1 )
time_check = 1;
}
}
/* if it is the day for a switch-over then check the time too */
if( time_check )
dst = !time_less( t, start );
/* if we are certain that it is before daylight saving then return */
if( dst == 0 ) {
if( south )
dst = south - dst; /* invert value of dst */
return( t->tm_isdst = dst );
}
/* now see if it is after daylight saving */
time_check = 0;
if( end->tm_isdst == 0 ) { /* if Mm.n.d form */
if( month > end->tm_mon )
dst = 0; /* not dst */
else if( month == end->tm_mon ) {
dst = 0;
/* calculate for current day */
n1 = t->tm_mday - ( t->tm_wday + 7 - end->tm_wday ) % 7;
/* calculate for previous day */
n2 = t->tm_mday - 1 -
( t->tm_wday - 1 + 7 - end->tm_wday ) % 7;
if( end->tm_mday == 5 ) {
if( n1 <= month_days - 7 )
dst = 1;
else if( n2 <= month_days - 7 )
time_check = 1;
} else {
if( n1 < 7 * ( end->tm_mday - 1 ) + 1 )
dst = 1;
else if( n2 < 7 * ( end->tm_mday - 1 ) + 1 )
time_check = 1;
}
}
} else {
n1 = end->tm_yday;
if( end->tm_isdst == 1 ) { /* if Jn form */
if( __leapyear( ( unsigned ) t->tm_year + 1900 ) ) {
if( n1 > __diyr[2] )
n1++; /* past Feb 28 */
}
n1--;
}
if( t->tm_yday >= n1 ) {
dst = 0;
if( t->tm_yday == n1 )
time_check = 1;
}
}
/* if it is the day for a switch-over then check the time too */
if( time_check )
dst = time_less( t, end );
if( south )
dst = south - dst; /* invert value of dst */
return( t->tm_isdst = dst );
}
static int time_less( const struct tm *t1, const struct tm *t2 )
{
int before;
before = 0;
if( t1->tm_hour < t2->tm_hour )
before = 1;
else if( t1->tm_hour == t2->tm_hour ) {
if( t1->tm_min < t2->tm_min
|| t1->tm_min == t2->tm_min && t1->tm_sec < t2->tm_sec )
before = 1;
}
return( before );
}

View File

@@ -0,0 +1,285 @@
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: Platform independent tzset() implementation.
*
****************************************************************************/
#include "variety.h"
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <time.h>
#include "rtdata.h"
#include "timedata.h"
#include "exitwmsg.h"
#include "_time.h"
/*
* TZSET - sets the values of the variables 'timezone', 'daylight'
* and 'tzname' according to the setting of the environment
* variable "TZ". The "TZ" variable has the format
* :characters
* or
* <std><offset>[<dst>[<offset>]][,<start>[/<time>],<end>[/<time>]]]
*/
//#define TZNAME_MAX 128 /* defined in <limits.h> */
struct tm __start_dst = { /* start of daylight savings */
0, 0, 2, /* M4.1.0/02:00:00 default */
1, 3, 0, /* i.e., 1st Sunday of Apr */
0, 0, 0
};
struct tm __end_dst = { /* end of daylight savings */
0, 0, 1, /* M10.5.0/02:00:00 default */
5, 9, 0, /* i.e., last Sunday of Oct */
0, 0, 0 /* note that this is specified*/
}; /* in terms of EST */
/* i.e. 02:00 EDT == 01:00 EST*/
static char stzone[TZNAME_MAX + 1] = "EST"; /* place to store names */
static char dtzone[TZNAME_MAX + 1] = "EDT"; /* place to store names */
_WCRTLINKD char *tzname[2] = { stzone, dtzone };
_WCRTLINKD long timezone = 5L * 60L * 60L; /* seconds from GMT */
_WCRTLINKD int daylight = 1; /* d.s.t. indicator */
int __dst_adjust = 60 * 60; /* daylight adjustment */
static struct {
unsigned cache_OS_TZ : 1;
unsigned have_OS_TZ : 1;
} tzFlag = { 1, 0 };
int __DontCacheOSTZ( void )
/*************************/
{
int old_flag;
old_flag = tzFlag.cache_OS_TZ;
tzFlag.cache_OS_TZ = 0;
tzFlag.have_OS_TZ = 0;
return( old_flag );
}
int __CacheOSTZ( void )
/*********************/
{
int old_flag;
old_flag = tzFlag.cache_OS_TZ;
tzFlag.cache_OS_TZ = 1;
tzFlag.have_OS_TZ = 0;
return( old_flag );
}
static char *parse_time( char *tz, int *val )
/*******************************************/
{
int value;
value = 0;
while( *tz >= '0' && *tz <= '9' ) {
value = value * 10 + *tz - '0';
++tz;
}
*val = value;
return( tz );
}
static char *parse_offset( char *tz, char *name, long *offset )
/*************************************************************/
{
int hours;
int minutes;
int seconds;
int neg;
int len;
char ch;
char const *tzstart;
if( *tz == ':' )
tz++;
/* remember where time zone name string begins */
tzstart = tz;
/* parse time zone name (should be 3 or more characters) */
/* examples: PST8, EDT+6, Central Standard Time+7:00:00 */
for( ;; ) {
ch = *tz;
if( ch == '\0' )
break;
if( ch == ',' )
break;
if( ch == '-' )
break;
if( ch == '+' )
break;
if( ch >= '0' && ch <= '9' )
break;
++tz;
}
len = tz - tzstart;
if( len > TZNAME_MAX )
len = TZNAME_MAX;
memcpy( name, tzstart, ( size_t ) len );
name[len] = '\0';
neg = 0;
if( ch == '-' ) {
neg = 1;
++tz;
} else if( ch == '+' )
++tz;
ch = *tz;
if( ch >= '0' && ch <= '9' ) {
hours = minutes = seconds = 0;
tz = parse_time( tz, &hours );
if( *tz == ':' ) {
tz = parse_time( tz + 1, &minutes );
if( *tz == ':' )
tz = parse_time( tz + 1, &seconds );
}
*offset = seconds + ( ( minutes + ( hours * 60 ) ) * 60L );
if( neg )
*offset = -*offset;
}
return( tz );
}
static char *parse_rule( char *tz, struct tm *timeptr )
/*****************************************************/
{
int date_form;
int days;
int hours;
int minutes;
int seconds;
date_form = -1; /* n 0-365 */
if( *tz == 'J' ) { /* Jn 1-365 (no leap days) */
date_form = 1;
tz++;
}
if( *tz == 'M' ) { /* Mm.n.d n'th day of month */
date_form = 0;
tz++;
}
timeptr->tm_isdst = date_form;
tz = parse_time( tz, &days );
if( date_form != 0 )
timeptr->tm_yday = days;
else {
timeptr->tm_mon = days - 1; /* 1-12 for M form */
if( *tz == '.' ) {
tz = parse_time( tz + 1, &days ); /* 1-5 for M form */
timeptr->tm_mday = days;
if( *tz == '.' ) {
tz = parse_time( tz + 1, &days );/* 0-6 for M form */
timeptr->tm_wday = days;
}
}
timeptr->tm_yday = 0;
}
hours = 2;
minutes = seconds = 0;
if( *tz == '/' ) {
tz = parse_time( tz + 1, &hours );
if( *tz == ':' ) {
tz = parse_time( tz + 1, &minutes );
if( *tz == ':' )
tz = parse_time( tz + 1, &seconds );
}
}
timeptr->tm_sec = seconds;
timeptr->tm_min = minutes;
timeptr->tm_hour = hours;
return( tz );
}
void __parse_tz( char * tz )
/**************************/
{
long dayzone;
_RWD_daylight = 0;
tz = parse_offset( tz, stzone, &_RWD_timezone );
if( *tz == '\0' ) {
dtzone[0] = '\0';
return;
}
_RWD_daylight = 1;
dayzone = _RWD_timezone - ( 60*60 ); /* 16-aug-91 */
tz = parse_offset( tz, dtzone, &dayzone );
_RWD_dst_adjust = _RWD_timezone - dayzone;
/* parse daylight changing rules */
if( *tz == ',' )
tz = parse_rule( tz + 1, &__start_dst );
if( *tz == ',' ) {
tz = parse_rule( tz + 1, &__end_dst );
/* convert rule to be in terms of Standard Time */
/* rather than Daylight Time */
__end_dst.tm_hour -= _RWD_dst_adjust / 3600;
__end_dst.tm_min -= ( _RWD_dst_adjust / 60 ) % 60;
__end_dst.tm_sec -= _RWD_dst_adjust % 60;
}
}
static int tryOSTimeZone( const char *tz )
/****************************************/
{
if( tz == NULL ) {
/* calling OS can be expensive; many programs don't care */
if( tzFlag.cache_OS_TZ && tzFlag.have_OS_TZ )
return( 1 );
/* Assume that even if we end up not getting the TZ from OS,
we won't have any better luck if we try later. */
tzFlag.have_OS_TZ = 1;
} else {
tzFlag.have_OS_TZ = 0;
return( 0 );
}
// assume Eastern (North America) time zone
_RWD_timezone = 5L * 60L * 60L;
_RWD_dst_adjust = 60L * 60L;
return( 1 );
}
_WCRTLINK void tzset( void )
/**************************/
{
#ifndef __NETWARE__
char *tz;
tz = getenv( "TZ" );
if( !tryOSTimeZone( tz ) && tz != NULL )
__parse_tz( tz );
#endif
}