From efa746c6bd61d6f327c6c1f0742284d768704d47 Mon Sep 17 00:00:00 2001 From: akr Date: Tue, 6 Apr 2004 08:02:56 +0000 Subject: * configure.in: check the size of time_t. * time.c (time_add): new function. (time_plus): use time_add. (time_minus): use time_add. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/branches/ruby_1_8@6110 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- ChangeLog | 8 +++++ MANIFEST | 1 + configure.in | 1 + time.c | 111 +++++++++++++++++++++++++++++------------------------------ 4 files changed, 64 insertions(+), 57 deletions(-) diff --git a/ChangeLog b/ChangeLog index 32b38611cd..fed94d9247 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +Tue Apr 6 16:46:09 2004 Tanaka Akira + + * configure.in: check the size of time_t. + + * time.c (time_add): new function. + (time_plus): use time_add. + (time_minus): use time_add. + Tue Apr 6 13:21:30 2004 NAKAMURA Usaku * ext/socket/socket.c (make_hostent): must return value. diff --git a/MANIFEST b/MANIFEST index a22544a690..2a0c1b5163 100644 --- a/MANIFEST +++ b/MANIFEST @@ -794,6 +794,7 @@ test/ruby/test_signal.rb test/ruby/test_stringchar.rb test/ruby/test_struct.rb test/ruby/test_system.rb +test/ruby/test_time.rb test/ruby/test_trace.rb test/ruby/test_variable.rb test/ruby/test_whileuntil.rb diff --git a/configure.in b/configure.in index be32dca473..26fc5d265e 100644 --- a/configure.in +++ b/configure.in @@ -205,6 +205,7 @@ AC_CHECK_SIZEOF(off_t, 0) AC_CHECK_SIZEOF(void*, 4) AC_CHECK_SIZEOF(float, 4) AC_CHECK_SIZEOF(double, 8) +AC_CHECK_SIZEOF(time_t, 0) AC_CACHE_CHECK(for prototypes, rb_cv_have_prototypes, [AC_TRY_COMPILE([int foo(int x) { return 0; }], [return foo(10);], diff --git a/time.c b/time.c index b6b16a1d05..a83ce748da 100644 --- a/time.c +++ b/time.c @@ -1254,6 +1254,57 @@ time_to_s(time) return rb_str_new(buf, len); } +#if SIZEOF_TIME_T == SIZEOF_LONG +typedef unsigned long unsigned_time_t; +#elif SIZEOF_TIME_T == SIZEOF_LONG_LONG +typedef unsigned long long unsigned_time_t; +#else +# error cannot find integer type which size is same as time_t. +#endif + +static VALUE +time_add(tobj, offset, sign) + struct time_object *tobj; + VALUE offset; + int sign; +{ + double v = NUM2DBL(offset); + double f, d; + unsigned_time_t sec_off; + time_t usec_off, sec, usec; + VALUE result; + + if (v < 0) { + v = -v; + sign = -sign; + } + d = modf(v, &f); + sec_off = (unsigned_time_t)f; + if (f != (double)sec_off) + rb_raise(rb_eRangeError, "time %s %f out of Time range", + sign < 0 ? "-" : "+", v); + usec_off = (time_t)(d*1e6); + + if (sign < 0) { + sec = tobj->tv.tv_sec - sec_off; + usec = tobj->tv.tv_usec - usec_off; + if (sec > tobj->tv.tv_sec) + rb_raise(rb_eRangeError, "time - %f out of Time range", v); + } + else { + sec = tobj->tv.tv_sec + sec_off; + usec = tobj->tv.tv_usec + usec_off; + if (sec < tobj->tv.tv_sec) + rb_raise(rb_eRangeError, "time + %f out of Time range", v); + } + result = rb_time_new(sec, usec); + if (tobj->gmt) { + GetTimeval(result, tobj); + tobj->gmt = 1; + } + return result; +} + /* * call-seq: * time + numeric => time @@ -1270,40 +1321,12 @@ time_plus(time1, time2) VALUE time1, time2; { struct time_object *tobj; - time_t sec, usec; - double f, d, v; - GetTimeval(time1, tobj); if (TYPE(time2) == T_DATA && RDATA(time2)->dfree == time_free) { rb_raise(rb_eTypeError, "time + time?"); } - v = NUM2DBL(time2); - d = modf(v, &f); - sec = (time_t)f; - if (f != (double)sec) { - rb_raise(rb_eRangeError, "time + %f out of Time range", v); - } -#ifndef NEGATIVE_TIME_T - if (f < 0 && -f >= tobj->tv.tv_sec) { - rb_raise(rb_eArgError, "time must be positive"); - } -#endif - usec = tobj->tv.tv_usec + (time_t)(d*1e6); - sec = tobj->tv.tv_sec + (time_t)f; - -#ifdef NEGATIVE_TIME_T - if ((tobj->tv.tv_sec >= 0 && f >= 0 && sec < 0) || - (tobj->tv.tv_sec <= 0 && f <= 0 && sec > 0)) { - rb_raise(rb_eRangeError, "time + %f out of Time range", v); - } -#endif - time2 = rb_time_new(sec, usec); - if (tobj->gmt) { - GetTimeval(time2, tobj); - tobj->gmt = 1; - } - return time2; + return time_add(tobj, time2, 1); } /* @@ -1326,12 +1349,11 @@ time_minus(time1, time2) VALUE time1, time2; { struct time_object *tobj; - time_t sec, usec; - double f, d, v; GetTimeval(time1, tobj); if (TYPE(time2) == T_DATA && RDATA(time2)->dfree == time_free) { struct time_object *tobj2; + double f; GetTimeval(time2, tobj2); f = (double)tobj->tv.tv_sec - (double)tobj2->tv.tv_sec; @@ -1340,32 +1362,7 @@ time_minus(time1, time2) return rb_float_new(f); } - v = NUM2DBL(time2); - d = modf(v, &f); - sec = (time_t)f; - if (f != (double)sec) { - rb_raise(rb_eRangeError, "time - %f out of Time range", v); - } -#ifndef NEGATIVE_TIME_T - if (f > 0 && f >= tobj->tv.tv_sec) { - rb_raise(rb_eArgError, "time must be positive"); - } -#endif - usec = tobj->tv.tv_usec - (time_t)(d*1e6); - sec = tobj->tv.tv_sec - (time_t)f; -#ifdef NEGATIVE_TIME_T - if ((tobj->tv.tv_sec <= 0 && f >= 0 && sec > 0) || - (tobj->tv.tv_sec >= 0 && f <= 0 && sec < 0)) { - rb_raise(rb_eRangeError, "time - %f out of Time range", v); - } -#endif - - time2 = rb_time_new(sec, usec); - if (tobj->gmt) { - GetTimeval(time2, tobj); - tobj->gmt = 1; - } - return time2; + return time_add(tobj, time2, -1); } /* -- cgit v1.2.3