Ejemplo n.º 1
0
PHOTON_COMMON_EXPORT
struct tm *
localtime_r( const time_t * 	timep,
             struct tm *	tm )
{
	localsub(timep, 0L, tm);
	return tm;
}
Ejemplo n.º 2
0
struct tm *
localtime_r(const time_t * const timep, struct tm *p_tm)
{
	_RWLOCK_RDLOCK(&lcl_rwlock);
	tzset_basic(1);
	localsub(timep, 0L, p_tm);
	_RWLOCK_UNLOCK(&lcl_rwlock);
	return(p_tm);
}
Ejemplo n.º 3
0
struct tm *
localtime(const time_t * const timep)
{
	static pthread_mutex_t localtime_mutex = PTHREAD_MUTEX_INITIALIZER;
	static pthread_key_t localtime_key = -1;
	struct tm *p_tm;

	if (__isthreaded != 0) {
		if (localtime_key < 0) {
			_pthread_mutex_lock(&localtime_mutex);
			if (localtime_key < 0) {
				if (_pthread_key_create(&localtime_key, free) < 0) {
					_pthread_mutex_unlock(&localtime_mutex);
					return(NULL);
				}
			}
			_pthread_mutex_unlock(&localtime_mutex);
		}
		p_tm = _pthread_getspecific(localtime_key);
		if (p_tm == NULL) {
			if ((p_tm = (struct tm *)malloc(sizeof(struct tm)))
			    == NULL)
				return(NULL);
			_pthread_setspecific(localtime_key, p_tm);
		}
		_RWLOCK_RDLOCK(&lcl_rwlock);
		tzset_basic(1);
		localsub(timep, 0L, p_tm);
		_RWLOCK_UNLOCK(&lcl_rwlock);
		return(p_tm);
	} else {
		tzset_basic(0);
		localsub(timep, 0L, &tm);
		return(&tm);
	}
}
Ejemplo n.º 4
0
/* data is here so we can use this as a callback for IPC */
static int
timezone_get_time(const char *timezone, struct tm *tm, double *diff, void *data)
{
    time_t now;
    struct tm *tm_tmp;
#ifdef PRIVATE_TZLIB
    struct state *tzinfo = timezone_load(timezone);

    if(!tzinfo)
        return -1;

    time(&now);
    localsub(&now, 0, tm, tzinfo);
    free(tzinfo);
#else
    const gchar *old_tz;

    /* Store the current TZ value. */
    old_tz = g_getenv("TZ");

    g_setenv("TZ", timezone, TRUE);

    time(&now);
    tm_tmp = localtime(&now);
    *tm = *tm_tmp;              /* Must copy, localtime uses local buffer */

    /* Reset the old TZ value. */
    if (old_tz == NULL)
        g_unsetenv("TZ");
    else
        g_setenv("TZ", old_tz, TRUE);
#endif

    /* Calculate user's localtime, and compare. If same, no output */
    tm_tmp = localtime(&now);

    if (tm_tmp->tm_hour == tm->tm_hour && tm_tmp->tm_min == tm->tm_min)
        return 1;

    *diff = timezone_calc_difference(tm, tm_tmp);
    return 0;
}
Ejemplo n.º 5
0
/*
 * The easy way to behave "as if no library function calls" localtime
 * is to not call it--so we drop its guts into "localsub", which can be
 * freely called. (And no, the PANS doesn't require the above behavior--
 * but it *is* desirable.)
 *
 * The unused offset argument is for the benefit of mktime variants.
 */
static struct pg_tm *
localsub(const pg_time_t *timep, long offset,
		 struct pg_tm * tmp, const pg_tz *tz)
{
	const struct state *sp;
	const struct ttinfo *ttisp;
	int			i;
	struct pg_tm *result;
	const pg_time_t t = *timep;

	sp = &tz->state;
	if ((sp->goback && t < sp->ats[0]) ||
		(sp->goahead && t > sp->ats[sp->timecnt - 1]))
	{
		pg_time_t	newt = t;
		pg_time_t	seconds;
		pg_time_t	tcycles;
		int64		icycles;

		if (t < sp->ats[0])
			seconds = sp->ats[0] - t;
		else
			seconds = t - sp->ats[sp->timecnt - 1];
		--seconds;
		tcycles = seconds / YEARSPERREPEAT / AVGSECSPERYEAR;
		++tcycles;
		icycles = tcycles;
		if (tcycles - icycles >= 1 || icycles - tcycles >= 1)
			return NULL;
		seconds = icycles;
		seconds *= YEARSPERREPEAT;
		seconds *= AVGSECSPERYEAR;
		if (t < sp->ats[0])
			newt += seconds;
		else
			newt -= seconds;
		if (newt < sp->ats[0] ||
			newt > sp->ats[sp->timecnt - 1])
			return NULL;		/* "cannot happen" */
		result = localsub(&newt, offset, tmp, tz);
		if (result == tmp)
		{
			pg_time_t	newy;

			newy = tmp->tm_year;
			if (t < sp->ats[0])
				newy -= icycles * YEARSPERREPEAT;
			else
				newy += icycles * YEARSPERREPEAT;
			tmp->tm_year = newy;
			if (tmp->tm_year != newy)
				return NULL;
		}
		return result;
	}
	if (sp->timecnt == 0 || t < sp->ats[0])
	{
		i = 0;
		while (sp->ttis[i].tt_isdst)
			if (++i >= sp->typecnt)
			{
				i = 0;
				break;
			}
	}
	else
	{
		int			lo = 1;
		int			hi = sp->timecnt;

		while (lo < hi)
		{
			int			mid = (lo + hi) >> 1;

			if (t < sp->ats[mid])
				hi = mid;
			else
				lo = mid + 1;
		}
		i = (int) sp->types[lo - 1];
	}
	ttisp = &sp->ttis[i];

	result = timesub(&t, ttisp->tt_gmtoff, sp, tmp);
	tmp->tm_isdst = ttisp->tt_isdst;
	tmp->tm_zone = &sp->chars[ttisp->tt_abbrind];
	return result;
}
Ejemplo n.º 6
0
struct pg_tm *
pg_localtime(const pg_time_t *timep, const pg_tz *tz)
{
	return localsub(timep, 0L, &tm, tz);
}
Ejemplo n.º 7
0
struct pg_tm *
pg_localtime_r(const pg_time_t *timep, const pg_tz *tz, struct pg_tm* tm)
{
	return localsub(timep, 0L, tm, tz);
}
Ejemplo n.º 8
0
/*ARGSUSED*/
static struct tm *
localsub(const time_t * const timep, const long offset __unused,
	 struct tm * const tmp)
{
	struct state *		sp;
	const struct ttinfo *	ttisp;
	int			i;
	struct tm *		result;
	const time_t		t = *timep;

	sp = lclptr;

	if ((sp->goback && t < sp->ats[0]) ||
		(sp->goahead && t > sp->ats[sp->timecnt - 1])) {
			time_t		newt = t;
			time_t		seconds;
			time_t		tcycles;
			int_fast64_t	icycles;

			if (t < sp->ats[0])
				seconds = sp->ats[0] - t;
			else	seconds = t - sp->ats[sp->timecnt - 1];
			--seconds;
			tcycles = seconds / YEARSPERREPEAT / AVGSECSPERYEAR;
			++tcycles;
			icycles = tcycles;
			if (tcycles - icycles >= 1 || icycles - tcycles >= 1)
				return NULL;
			seconds = icycles;
			seconds *= YEARSPERREPEAT;
			seconds *= AVGSECSPERYEAR;
			if (t < sp->ats[0])
				newt += seconds;
			else	newt -= seconds;
			if (newt < sp->ats[0] ||
				newt > sp->ats[sp->timecnt - 1])
					return NULL;	/* "cannot happen" */
			result = localsub(&newt, offset, tmp);
			if (result == tmp) {
				time_t	newy;

				newy = tmp->tm_year;
				if (t < sp->ats[0])
					newy -= icycles * YEARSPERREPEAT;
				else	newy += icycles * YEARSPERREPEAT;
				tmp->tm_year = newy;
				if (tmp->tm_year != newy)
					return NULL;
			}
			return result;
	}
	if (sp->timecnt == 0 || t < sp->ats[0]) {
		i = 0;
		while (sp->ttis[i].tt_isdst)
			if (++i >= sp->typecnt) {
				i = 0;
				break;
			}
	} else {
		int	lo = 1;
		int	hi = sp->timecnt;

		while (lo < hi) {
			int	mid = (lo + hi) >> 1;

			if (t < sp->ats[mid])
				hi = mid;
			else	lo = mid + 1;
		}
		i = (int) sp->types[lo - 1];
	}
	ttisp = &sp->ttis[i];
	/*
	** To get (wrong) behavior that's compatible with System V Release 2.0
	** you'd replace the statement below with
	**	t += ttisp->tt_gmtoff;
	**	timesub(&t, 0L, sp, tmp);
	*/
	result = timesub(&t, ttisp->tt_gmtoff, sp, tmp);
	tmp->tm_isdst = ttisp->tt_isdst;
	tzname[tmp->tm_isdst] = &sp->chars[ttisp->tt_abbrind];
#ifdef TM_ZONE
	tmp->TM_ZONE = &sp->chars[ttisp->tt_abbrind];
#endif /* defined TM_ZONE */
	return result;
}