From a5e1f60b3167e0057e64166df06424f1fb96bec3 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 21 Sep 2017 20:08:59 +0200 Subject: bugfix: ALTER TABLE and TIMESTAMPs around DST change time Implement a special Copy_func function for timestamps, that copies timestamps without converting them to MYSQL_TIME (the conversion is lossy around DST change time). This fixes ALTER TABLE part of main.old-mode test. This is 10.2 version of f4f48e06215 --- sql/field_conv.cc | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) (limited to 'sql/field_conv.cc') diff --git a/sql/field_conv.cc b/sql/field_conv.cc index 85101fd5f0a..15df2c398a3 100644 --- a/sql/field_conv.cc +++ b/sql/field_conv.cc @@ -417,6 +417,16 @@ void Field::do_field_decimal(Copy_field *copy) } +void Field::do_field_timestamp(Copy_field *copy) +{ + Field_timestamp *f= static_cast(copy->from_field); + Field_timestamp *t= static_cast(copy->to_field); + ulong sec_part; + my_time_t ts= f->get_timestamp(&sec_part); + t->store_TIME(ts, sec_part); +} + + void Field::do_field_temporal(Copy_field *copy) { MYSQL_TIME ltime; @@ -706,6 +716,16 @@ void Copy_field::set(Field *to,Field *from,bool save) } +Field::Copy_func *Field_timestamp::get_copy_func(const Field *from) const +{ + Field::Copy_func *copy= Field_temporal::get_copy_func(from); + if (copy == do_field_temporal && from->type() == MYSQL_TYPE_TIMESTAMP) + return do_field_timestamp; + else + return copy; +} + + Field::Copy_func *Field_temporal::get_copy_func(const Field *from) const { /* If types are not 100 % identical then convert trough get_date() */ -- cgit v1.2.1 From 68d1a598bcda36d375fd295e3e65cdf8aef027f1 Mon Sep 17 00:00:00 2001 From: Sergei Golubchik Date: Thu, 21 Sep 2017 21:21:36 +0200 Subject: bugfix: copy timestamps correctly in INSERT...SELECT Implement Field_timestamp::save_in_field(timestamp_field) that stores timestamp values without converting them to MYSQL_TIME and back, because this conversion is lossy around DST change time. This fixes main.old-mode test. This is 10.2 version of f8a800bec81 --- sql/field_conv.cc | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) (limited to 'sql/field_conv.cc') diff --git a/sql/field_conv.cc b/sql/field_conv.cc index 15df2c398a3..c3ad0c878b5 100644 --- a/sql/field_conv.cc +++ b/sql/field_conv.cc @@ -419,11 +419,8 @@ void Field::do_field_decimal(Copy_field *copy) void Field::do_field_timestamp(Copy_field *copy) { - Field_timestamp *f= static_cast(copy->from_field); - Field_timestamp *t= static_cast(copy->to_field); - ulong sec_part; - my_time_t ts= f->get_timestamp(&sec_part); - t->store_TIME(ts, sec_part); + // XXX why couldn't we do it everywhere? + copy->from_field->save_in_field(copy->to_field); } -- cgit v1.2.1