time.c revision df0f58959ed82a2a43ca8d816ce9592541df9f2f
/*
* Copyright (C) 1998-2001 Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
* DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
* INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
* INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
* FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
* NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
* WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/* $Id: time.c,v 1.31 2001/02/23 23:12:28 marka Exp $ */
#include <config.h>
#include <errno.h>
#include <limits.h>
#include <time.h>
/*
* All of the INSIST()s checks of nanoseconds < NS_PER_S are for
* consistency checking of the type. In lieu of magic numbers, it
* is the best we've got. The check is only performed on functions which
* need an initialized type.
*/
#ifndef ISC_FIX_TV_USEC
#define ISC_FIX_TV_USEC 1
#endif
/***
*** Intervals
***/
static isc_interval_t zero_interval = { 0, 0 };
void
unsigned int seconds, unsigned int nanoseconds)
{
/*
* Set 'i' to a value representing an interval of 'seconds' seconds
* and 'nanoseconds' nanoseconds, suitable for use in isc_time_add()
* and isc_time_subtract().
*/
i->nanoseconds = nanoseconds;
}
/*
* Returns ISC_TRUE iff. 'i' is the zero interval.
*/
if (i->seconds == 0 && i->nanoseconds == 0)
return (ISC_TRUE);
return (ISC_FALSE);
}
/***
*** Absolute Times
***/
static isc_time_t epoch = { 0, 0 };
void
/*
* Set 't' to a particular number of seconds + nanoseconds since the
* epoch.
*/
t->nanoseconds = nanoseconds;
}
void
/*
* Set 't' to the time of the epoch.
*/
t->seconds = 0;
t->nanoseconds = 0;
}
isc_time_isepoch(isc_time_t *t) {
/*
* Returns ISC_TRUE iff. 't' is the epoch ("time zero").
*/
if (t->seconds == 0 && t->nanoseconds == 0)
return (ISC_TRUE);
return (ISC_FALSE);
}
isc_time_now(isc_time_t *t) {
#if ISC_FIX_TV_USEC
#endif
/*
* Set *t to the current absolute time.
*/
return (ISC_R_UNEXPECTED);
}
/*
* Does POSIX guarantee the signedness of tv_sec and tv_usec? If not,
* then this test will generate warnings for platforms on which it is
* unsigned. In any event, the chances of any of these problems
* happening are pretty much zero, but since the libisc library ensures
* certain things to be true ...
*/
#if ISC_FIX_TV_USEC
do {
do {
return (ISC_R_UNEXPECTED);
if (fixed)
"gettimeofday returned bad tv_usec: corrected");
#else
return (ISC_R_UNEXPECTED);
#endif
/*
* Ensure the tv_sec value fits in t->seconds.
*/
return (ISC_R_RANGE);
return (ISC_R_SUCCESS);
}
/*
* Set *t to the current absolute time + i.
*/
return (ISC_R_UNEXPECTED);
}
/*
* Does POSIX guarantee the signedness of tv_sec and tv_usec? If not,
* then this test will generate warnings for platforms on which it is
* unsigned. In any event, the chances of any of these problems
* happening are pretty much zero, but since the libisc library ensures
* certain things to be true ...
*/
return (ISC_R_UNEXPECTED);
/*
* Ensure the resulting seconds value fits in the size of an
* unsigned int. (It is written this way as a slight optimization;
* note that even if both values == INT_MAX, then when added
* and getting another 1 added below the result is UINT_MAX.)
*/
return (ISC_R_RANGE);
if (t->nanoseconds > NS_PER_S) {
t->seconds++;
t->nanoseconds -= NS_PER_S;
}
return (ISC_R_SUCCESS);
}
int
/*
* Compare the times referenced by 't1' and 't2'
*/
return (-1);
return (1);
return (-1);
return (1);
return (0);
}
/*
* Add 't' to 'i', storing the result in 'result'.
*/
/*
* Ensure the resulting seconds value fits in the size of an
* unsigned int. (It is written this way as a slight optimization;
* note that even if both values == INT_MAX, then when added
* and getting another 1 added below the result is UINT_MAX.)
*/
return (ISC_R_RANGE);
}
return (ISC_R_SUCCESS);
}
/*
* Subtract 'i' from 't', storing the result in 'result'.
*/
t->nanoseconds < i->nanoseconds))
return (ISC_R_RANGE);
if (t->nanoseconds >= i->nanoseconds)
else {
t->nanoseconds;
}
return (ISC_R_SUCCESS);
}
return (0);
/*
* Convert to microseconds.
*/
return (i3);
}
isc_time_seconds(isc_time_t *t) {
return ((isc_uint32_t)t->seconds);
}
isc_uint64_t i;
/*
* Ensure that the number of seconds represented by t->seconds
* can be represented by a time_t. Since t->seconds is an unsigned
* int and since time_t is mostly opaque, this is trickier than
* it seems. (This standardized opaqueness of time_t is *very*
* frustrating; time_t is not even limited to being an integral
* type.)
*
* The mission, then, is to avoid generating any kind of warning
* about "signed versus unsigned" while trying to determine if the
* the unsigned int t->seconds is out range for tv_sec, which is
* pretty much only true if time_t is a signed integer of the same
* size as the return value of isc_time_seconds.
*
* The use of the 64 bit integer ``i'' takes advantage of C's
* conversion rules to either zero fill or sign extend the widened
* type.
*
* Solaris 5.6 gives this warning about the left shift:
* warning: integer overflow detected: op "<<"
* if the U(nsigned) qualifier is not on the 1.
*/
INSIST(sizeof(unsigned int) == sizeof(isc_uint32_t));
(seconds &
/*
* This UNUSED() is here to shut up the IRIX compiler:
* variable "i" was set but never used
* when the value of i *was* used in the third test.
* (Let's hope the compiler got the actual test right.)
*/
UNUSED(i);
return (ISC_R_RANGE);
}
return (ISC_R_SUCCESS);
}
return ((isc_uint32_t)t->nanoseconds);
}