Feature #8809 » clock_getres.patch
process.c (working copy) | ||
---|---|---|
return make_clock_result(&ts, unit);
|
||
}
|
||
/*
|
||
* call-seq:
|
||
* Process.clock_getres(clock_id [, unit]) -> number
|
||
*
|
||
* Returns a time resolution returned by POSIX clock_getres() function.
|
||
*
|
||
* +clock_id+ specifies a kind of clock.
|
||
* See the document of +Process.clock_gettime+ for details.
|
||
*
|
||
* +clock_id+ can be a symbol as +Process.clock_gettime+.
|
||
* However the result may not be accurate.
|
||
* For example, +Process.clock_getres(:SUS_GETTIMEOFDAY_BASED_CLOCK_REALTIME, :nanosecond)+
|
||
* returns 1000, always.
|
||
*
|
||
* If the given +clock_id+ is not supported, Errno::EINVAL is raised.
|
||
*
|
||
* +unit+ specifies a type of the return value.
|
||
* +Process.clock_getres+ accepts +unit+ as +Process.clock_gettime+.
|
||
* The default value, +:float_second+, is also same as
|
||
* +Process.clock_gettime+.
|
||
*
|
||
* +Process.clock_getres+ also accepts +:hertz+ as +unit+.
|
||
* +:hertz+ means a the reciprocal of +:float_second+.
|
||
*
|
||
* +:hertz+ can be used to obtain the exact value of
|
||
* the clock ticks per second for times() function and
|
||
* CLOCK_PER_SEC for clock() function.
|
||
*
|
||
* +Process.clock_getres(:POSIX_TIMES_BASED_CLOCK_PROCESS_CPUTIME_ID, :hertz)+
|
||
* returns the clock ticks per second.
|
||
*
|
||
* +Process.clock_getres(:ISO_C_CLOCK_BASED_CLOCK_PROCESS_CPUTIME_ID, :hertz)+
|
||
* returns CLOCK_PER_SEC.
|
||
*
|
||
* p Process.clock_getres(Process::CLOCK_MONOTONIC)
|
||
* #=> 1.0e-09
|
||
*
|
||
*/
|
||
VALUE
|
||
rb_clock_getres(int argc, VALUE *argv)
|
||
{
|
||
struct timespec ts;
|
||
VALUE clk_id, unit;
|
||
int ret;
|
||
double hertz;
|
||
rb_scan_args(argc, argv, "11", &clk_id, &unit);
|
||
if (SYMBOL_P(clk_id)) {
|
||
#ifdef RUBY_SUS_GETTIMEOFDAY_BASED_CLOCK_REALTIME
|
||
if (clk_id == RUBY_SUS_GETTIMEOFDAY_BASED_CLOCK_REALTIME) {
|
||
ts.tv_sec = 0;
|
||
ts.tv_nsec = 1000;
|
||
goto success;
|
||
}
|
||
#endif
|
||
#ifdef RUBY_ISO_C_TIME_BASED_CLOCK_REALTIME
|
||
if (clk_id == RUBY_ISO_C_TIME_BASED_CLOCK_REALTIME) {
|
||
ts.tv_sec = 1;
|
||
ts.tv_nsec = 0;
|
||
goto success;
|
||
}
|
||
#endif
|
||
#ifdef RUBY_SUS_GETRUSAGE_BASED_CLOCK_PROCESS_CPUTIME_ID
|
||
if (clk_id == RUBY_SUS_GETRUSAGE_BASED_CLOCK_PROCESS_CPUTIME_ID) {
|
||
ts.tv_sec = 0;
|
||
ts.tv_nsec = 1000;
|
||
goto success;
|
||
}
|
||
#endif
|
||
#ifdef RUBY_POSIX_TIMES_BASED_CLOCK_PROCESS_CPUTIME_ID
|
||
if (clk_id == RUBY_POSIX_TIMES_BASED_CLOCK_PROCESS_CPUTIME_ID) {
|
||
hertz = get_clk_tck();
|
||
goto success_hertz;
|
||
}
|
||
#endif
|
||
#ifdef RUBY_ISO_C_CLOCK_BASED_CLOCK_PROCESS_CPUTIME_ID
|
||
if (clk_id == RUBY_ISO_C_CLOCK_BASED_CLOCK_PROCESS_CPUTIME_ID) {
|
||
hertz = CLOCKS_PER_SEC;
|
||
goto success_hertz;
|
||
}
|
||
#endif
|
||
#ifdef RUBY_MACH_ABSOLUTE_TIME_BASED_CLOCK_MONOTONIC
|
||
/* not yet */
|
||
#endif
|
||
}
|
||
else {
|
||
#if defined(HAVE_CLOCK_GETTIME)
|
||
clockid_t c;
|
||
c = NUM2CLOCKID(clk_id);
|
||
ret = clock_getres(c, &ts);
|
||
if (ret == -1)
|
||
rb_sys_fail("clock_getres");
|
||
goto success;
|
||
#endif
|
||
}
|
||
/* EINVAL emulates clock_getres behavior when clock_id is invalid. */
|
||
errno = EINVAL;
|
||
rb_sys_fail(0);
|
||
success_hertz:
|
||
if (unit == ID2SYM(rb_intern("hertz"))) {
|
||
return DBL2NUM(hertz);
|
||
}
|
||
else {
|
||
double ns;
|
||
ns = 1e9 / hertz;
|
||
ts.tv_sec = (time_t)(ns*1e-9);
|
||
ts.tv_nsec = ns - ts.tv_sec*1e9;
|
||
return make_clock_result(&ts, unit);
|
||
}
|
||
success:
|
||
if (unit == ID2SYM(rb_intern("hertz"))) {
|
||
hertz = 1e9 / (ts.tv_sec * 1e9 + ts.tv_nsec);
|
||
return DBL2NUM(hertz);
|
||
}
|
||
else {
|
||
return make_clock_result(&ts, unit);
|
||
}
|
||
}
|
||
VALUE rb_mProcess;
|
||
VALUE rb_mProcUID;
|
||
VALUE rb_mProcGID;
|
||
... | ... | |
rb_define_const(rb_mProcess, "CLOCK_SECOND", CLOCKID2NUM(CLOCK_SECOND));
|
||
#endif
|
||
rb_define_module_function(rb_mProcess, "clock_gettime", rb_clock_gettime, -1);
|
||
rb_define_module_function(rb_mProcess, "clock_getres", rb_clock_getres, -1);
|
||
#if defined(HAVE_TIMES) || defined(_WIN32)
|
||
rb_cProcessTms = rb_struct_define("Tms", "utime", "stime", "cutime", "cstime", NULL);
|