cvs commit: src/sys/sys time.h src/sys/kern kern_time.c
Robert Watson
rwatson at FreeBSD.org
Sun Nov 27 01:04:15 GMT 2005
On Sun, 27 Nov 2005, Robert Watson wrote:
> Add experimental low-precision clockid_t names corresponding to these
> clocks, but implemented using cached timestamps in kernel rather than
> a full time counter query. This offers a minimum update rate of 1/HZ,
> but in practice will often be more frequent due to the frequency of
> time stamping in the kernel:
>
> New clockid_t name Approximates existing clockid_t
>
> CLOCK_REALTIME_FAST CLOCK_REALTIME
> CLOCK_MONOTONIC_FAST CLOCK_MONOTONIC
> CLOCK_UPTIME_FAST CLOCK_UPTIME
>
> Add one additional new clockid_t, CLOCK_SECOND, which returns the
> current second without performing a full time counter query or cache
> lookup overhead to make sure the cached timestamp is stable. This is
> intended to support very low granularity consumers, such as time(3).
These changes are primarily intended to support the identification of
time-associated bottlenecks and allow experimentation with application
scoped reduction in quality of time use. Attached is a small LD_PRELOAD
library to allow applications to be switched to the _FAST variants for
gettimeofday(). Build and install, then set:
LD_PRELOAD=/usr/lib/libwrapper.so ; export LD_PRELOAD
This is not intended to be the last word in how this should be done --
more, to facilitate some experimentation by providing some framework for
experimentation (i.e., a sample API and code to tweak applications). I
expect that the details will be subject to substantial change. :-)
Robert N M Watson
-------------- next part --------------
# $FreeBSD$
LIB= wrapper
SHLIB_MAJOR= 1
SRCS= wrapper.c
NO_MAN=
.include <bsd.lib.mk>
-------------- next part --------------
/*-
* Copyright (c) 2005 Robert N. M. Watson
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* $FreeBSD$
*/
/*
* Small wrapper library to substitute implementations of gettimeofday(2) and
* time(3) with lower resolution variations. time(3) is unconditionally
* degraded, since it will return a truncated time anyway. gettimeofday(3)
* checks the TIMEWRAPPER environmental variable, which can be set to either
* "PRECISE" or "FAST".
*/
#include <sys/time.h>
#include <stdlib.h>
#include <string.h>
static int timewrapper_initialized;
static clockid_t timewrapper_clock;
/*
* Select whatever system default is present for CLOCK_REALTIME as the
* default if the environmental variable is unset, or set to an invalid
* value.
*/
#define TIMEWRAPPER_ENV "TIMEWRAPPER"
#define TIMEWRAPPER_DEFAULT CLOCK_REALTIME
#define TIMEWRAPPER_STRPRECISE "PRECISE"
#define TIMEWRAPPER_STRFAST "FAST"
static void
timewrapper_initialize(void)
{
const char *whichclock_env;
whichclock_env = getenv(TIMEWRAPPER_ENV);
if (whichclock_env == NULL) {
timewrapper_clock = TIMEWRAPPER_DEFAULT;
timewrapper_initialized = 1;
return;
}
if (strcmp(whichclock_env, TIMEWRAPPER_STRPRECISE) == 0)
timewrapper_clock = CLOCK_REALTIME_PRECISE;
else if (strcmp(whichclock_env, TIMEWRAPPER_STRFAST) == 0)
timewrapper_clock = CLOCK_REALTIME_FAST;
else
timewrapper_clock = TIMEWRAPPER_DEFAULT;
timewrapper_initialized = 1;
}
int
gettimeofday(struct timeval *tp, struct timezone *tzp)
{
struct timespec ts;
if (!timewrapper_initialized)
timewrapper_initialize();
/*
* XXXRW: Not ideal, since returning EINVAL from gettimeofday() isn't
* expected. Fall back to the gettimeofday() system call instead?
*/
if (clock_gettime(timewrapper_clock, &ts) < 0)
return (-1);
tp->tv_sec = ts.tv_sec;
tp->tv_usec = ts.tv_nsec / 1000;
return (0);
}
time_t
time(time_t *tloc)
{
struct timespec ts;
if (clock_gettime(CLOCK_SECOND, &ts) < 0) {
if (tloc != NULL)
*tloc = -1;
return (-1);
}
if (tloc != NULL)
*tloc = ts.tv_sec;
return (ts.tv_sec);
}
More information about the cvs-src
mailing list