summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authortadf <tadf@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2011-06-29 14:47:04 +0000
committertadf <tadf@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2011-06-29 14:47:04 +0000
commit23658b355c1c62771945cfa86e098ba8dd618779 (patch)
tree5f996bbb4f88675e72195fe674c4527a9149340d
parent64263ddeb6b925866bc4ad2d5c74300af178b896 (diff)
* ext/date/date_core.c: avoided using timev.
* ext/date/date_strftime.c: ditto. * ext/date/date_tmx.h: ditto. git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@32294 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog6
-rw-r--r--ext/date/date_core.c68
-rw-r--r--ext/date/date_strftime.c14
-rw-r--r--ext/date/date_tmx.h8
-rw-r--r--test/date/test_date_strftime.rb9
5 files changed, 79 insertions, 26 deletions
diff --git a/ChangeLog b/ChangeLog
index 096755b016..8aa21e112a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,9 @@
+Wed Jun 29 23:42:51 2011 Tadayoshi Funaba <tadf@dotrb.org>
+
+ * ext/date/date_core.c: avoided using timev.
+ * ext/date/date_strftime.c: ditto.
+ * ext/date/date_tmx.h: ditto.
+
Wed Jun 29 23:17:57 2011 WATANABE Hirofumi <eban@ruby-lang.org>
* ext/openssl/ossl.h (OPENSSL_SYS_WIN32): support for mingw(msys).
diff --git a/ext/date/date_core.c b/ext/date/date_core.c
index d129f232e6..89fa4761c9 100644
--- a/ext/date/date_core.c
+++ b/ext/date/date_core.c
@@ -172,6 +172,7 @@ f_negative_p(VALUE x)
#define MINUTE_IN_SECONDS 60
#define HOUR_IN_SECONDS 3600
#define DAY_IN_SECONDS 86400
+#define SECOND_IN_MILLISECONDS 1000
#define SECOND_IN_NANOSECONDS 1000000000
#define JC_PERIOD0 1461 /* 365.25 * 4 */
@@ -932,6 +933,14 @@ ns_to_day(VALUE n)
return f_quo(n, day_in_nanoseconds);
}
+#ifndef NDEBUG
+static VALUE
+ms_to_sec(VALUE n)
+{
+ return f_quo(n, INT2FIX(SECOND_IN_MILLISECONDS));
+}
+#endif
+
static VALUE
ns_to_sec(VALUE n)
{
@@ -976,6 +985,14 @@ day_to_ns(VALUE d)
#endif
static VALUE
+sec_to_ms(VALUE s)
+{
+ if (safe_mul_p(s, SECOND_IN_MILLISECONDS))
+ return LONG2FIX(FIX2LONG(s) * SECOND_IN_MILLISECONDS);
+ return f_mul(s, INT2FIX(SECOND_IN_MILLISECONDS));
+}
+
+static VALUE
sec_to_ns(VALUE s)
{
if (safe_mul_p(s, SECOND_IN_NANOSECONDS))
@@ -6596,6 +6613,38 @@ date_strftime_alloc(char **buf, const char *format,
}
static VALUE
+tmx_m_secs(union DateData *x)
+{
+ VALUE s;
+ int df;
+
+ s = day_to_sec(f_sub(m_real_jd(x),
+ UNIX_EPOCH_IN_CJD));
+ if (simple_dat_p(x))
+ return s;
+ df = m_df(x);
+ if (df)
+ s = f_add(s, INT2FIX(df));
+ return s;
+}
+
+#define MILLISECOND_IN_NANOSECONDS 1000000
+
+static VALUE
+tmx_m_msecs(union DateData *x)
+{
+ VALUE s, sf;
+
+ s = sec_to_ms(tmx_m_secs(x));
+ if (simple_dat_p(x))
+ return s;
+ sf = m_sf(x);
+ if (f_nonzero_p(sf))
+ s = f_add(s, f_div(sf, INT2FIX(MILLISECOND_IN_NANOSECONDS)));
+ return s;
+}
+
+static VALUE
tmx_m_of(union DateData *x)
{
return INT2FIX(m_of(x));
@@ -6607,17 +6656,6 @@ tmx_m_zone(union DateData *x)
return RSTRING_PTR(m_zone(x));
}
-static VALUE
-tmx_m_timev(union DateData *x)
-{
- if (simple_dat_p(x))
- return day_to_sec(f_sub(m_real_jd(x),
- UNIX_EPOCH_IN_CJD));
- else
- return day_to_sec(f_sub(m_ajd(x),
- UNIX_EPOCH_IN_AJD));
-}
-
static struct tmx_funcs tmx_funcs = {
(VALUE (*)(void *))m_real_year,
(int (*)(void *))m_yday,
@@ -6632,9 +6670,11 @@ static struct tmx_funcs tmx_funcs = {
(int (*)(void *))m_hour,
(int (*)(void *))m_min,
(int (*)(void *))m_sec,
+ (VALUE (*)(void *))m_sf_in_sec,
+ (VALUE (*)(void *))tmx_m_secs,
+ (VALUE (*)(void *))tmx_m_msecs,
(VALUE (*)(void *))tmx_m_of,
- (char *(*)(void *))tmx_m_zone,
- (VALUE (*)(void *))tmx_m_timev
+ (char *(*)(void *))tmx_m_zone
};
static void
@@ -8870,6 +8910,8 @@ date_s_test_unit_conv(VALUE klass)
{
if (!test_unit_v2v_iter(sec_to_day, day_to_sec))
return Qfalse;
+ if (!test_unit_v2v_iter(ms_to_sec, sec_to_ms))
+ return Qfalse;
if (!test_unit_v2v_iter(ns_to_day, day_to_ns))
return Qfalse;
if (!test_unit_v2v_iter(ns_to_sec, sec_to_ns))
diff --git a/ext/date/date_strftime.c b/ext/date/date_strftime.c
index 5781d3b795..02ad9a47ae 100644
--- a/ext/date/date_strftime.c
+++ b/ext/date/date_strftime.c
@@ -406,19 +406,11 @@ date_strftime_with_tmx(char *s, size_t maxsize, const char *format,
break;
case 's':
- {
- VALUE sec = div(tmx_timev, INT2FIX(1));
- FMTV('0', 1, "d", sec);
- }
+ FMTV('0', 1, "d", tmx_secs);
continue;
case 'Q':
- {
- VALUE sec = div(tmx_timev,
- rb_rational_new2(INT2FIX(1),
- INT2FIX(1000)));
- FMTV('0', 1, "d", sec);
- }
+ FMTV('0', 1, "d", tmx_msecs);
continue;
case 'S': /* second, 00 - 59 */
@@ -697,7 +689,7 @@ date_strftime_with_tmx(char *s, size_t maxsize, const char *format,
NEEDS(precision);
{
- VALUE subsec = mod(tmx_timev, INT2FIX(1));
+ VALUE subsec = tmx_sec_fraction;
int ww;
long n;
diff --git a/ext/date/date_tmx.h b/ext/date/date_tmx.h
index 2bdb80c316..0e56c9b4f0 100644
--- a/ext/date/date_tmx.h
+++ b/ext/date/date_tmx.h
@@ -15,9 +15,11 @@ struct tmx_funcs {
int (*hour)(void *dat);
int (*min)(void *dat);
int (*sec)(void *dat);
+ VALUE (*sec_fraction)(void *dat);
+ VALUE (*secs)(void *dat);
+ VALUE (*msecs)(void *dat);
VALUE (*offset)(void *dat);
char *(*zone)(void *dat);
- VALUE (*timev)(void *dat);
};
struct tmx {
void *dat;
@@ -39,9 +41,11 @@ struct tmx {
#define tmx_hour tmx_attr(hour)
#define tmx_min tmx_attr(min)
#define tmx_sec tmx_attr(sec)
+#define tmx_sec_fraction tmx_attr(sec_fraction)
+#define tmx_secs tmx_attr(secs)
+#define tmx_msecs tmx_attr(msecs)
#define tmx_offset tmx_attr(offset)
#define tmx_zone tmx_attr(zone)
-#define tmx_timev tmx_attr(timev)
#endif
diff --git a/test/date/test_date_strftime.rb b/test/date/test_date_strftime.rb
index 61a82a17f5..8b96f16049 100644
--- a/test/date/test_date_strftime.rb
+++ b/test/date/test_date_strftime.rb
@@ -194,6 +194,15 @@ class TestDateStrftime < Test::Unit::TestCase
end
end
+ def test_strftime_milli
+ s = '1970-01-01T00:00:00.123456789'
+ d = DateTime.parse(s)
+ assert_equal('123', d.strftime('%Q'))
+ s = '1970-01-02T02:03:04.123456789'
+ d = DateTime.parse(s)
+ assert_equal('93784123', d.strftime('%Q'))
+ end
+
def test_strftime__minus
d = DateTime.new(1969, 12, 31, 23, 59, 59)
assert_equal('-1', d.strftime('%s'))