3548 Alexander Barkov 2011-11-03
WL#946 clean-ups
- Introducing new class MYSQL_TIME_cache.
- minor other improvements
modified:
sql/field.cc
sql/item_timefunc.cc
sql/item_timefunc.h
sql/sql_class.h
sql/sql_time.cc
sql/tztime.h
3547 Alexander Barkov 2011-11-02
WL#946 clean-ups
modified:
mysys/my_getsystime.c
sql/item_timefunc.h
=== modified file 'sql/field.cc'
--- a/sql/field.cc 2011-11-01 11:52:24 +0000
+++ b/sql/field.cc 2011-11-03 09:33:45 +0000
@@ -5344,7 +5344,6 @@ bool Field_timestamp::get_date_internal(
ASSERT_COLUMN_MARKED_FOR_READ;
uint32 temp;
THD *thd= table ? table->in_use : current_thd;
- thd->time_zone_used= 1;
#ifdef WORDS_BIGENDIAN
if (table && table->s->db_low_byte_first)
temp= uint4korr(ptr);
@@ -5353,7 +5352,7 @@ bool Field_timestamp::get_date_internal(
longget(temp, ptr);
if (!temp)
return true;
- thd->variables.time_zone->gmt_sec_to_TIME(ltime, (my_time_t) temp);
+ thd->time_zone()->gmt_sec_to_TIME(ltime, (my_time_t) temp);
return false;
}
@@ -5564,11 +5563,9 @@ Field_timestampf::get_date_internal(MYSQ
THD *thd= table ? table->in_use : current_thd;
struct timeval tm;
my_timestamp_from_binary(&tm, ptr, dec);
- thd->time_zone_used= 1;
if (tm.tv_sec == 0)
return true;
- thd->variables.time_zone->gmt_sec_to_TIME(ltime, (my_time_t) tm.tv_sec);
- ltime->second_part= tm.tv_usec;
+ thd->time_zone()->gmt_sec_to_TIME(ltime, tm);
return false;
}
=== modified file 'sql/item_timefunc.cc'
--- a/sql/item_timefunc.cc 2011-11-02 11:21:10 +0000
+++ b/sql/item_timefunc.cc 2011-11-03 09:33:45 +0000
@@ -1028,16 +1028,14 @@ bool Item_date_literal::eq(const Item *i
return
item->basic_const_item() && type() == item->type() &&
func_name() == ((Item_func *) item)->func_name() &&
- ctime_as_temporal == ((Item_date_literal *) item)->ctime_as_temporal;
+ cached_time.eq(((Item_date_literal *) item)->cached_time);
}
void Item_date_literal::print(String *str, enum_query_type query_type)
{
- char buff[MAX_DATE_STRING_REP_LENGTH];
str->append("DATE'");
- my_date_to_str(&ctime, buff);
- str->append(buff);
+ str->append(cached_time.cptr());
str->append('\'');
}
@@ -1047,16 +1045,14 @@ bool Item_datetime_literal::eq(const Ite
return
item->basic_const_item() && type() == item->type() &&
func_name() == ((Item_func *) item)->func_name() &&
- ctime_as_temporal == ((Item_datetime_literal *) item)->ctime_as_temporal;
+ cached_time.eq(((Item_datetime_literal *) item)->cached_time);
}
void Item_datetime_literal::print(String *str, enum_query_type query_type)
{
- char buff[MAX_DATE_STRING_REP_LENGTH];
str->append("TIMESTAMP'");
- my_datetime_to_str(&ctime, buff, decimals);
- str->append(buff);
+ str->append(cached_time.cptr());
str->append('\'');
}
@@ -1066,16 +1062,14 @@ bool Item_time_literal::eq(const Item *i
return
item->basic_const_item() && type() == item->type() &&
func_name() == ((Item_func *) item)->func_name() &&
- ctime_as_temporal == ((Item_time_literal *) item)->ctime_as_temporal;
+ cached_time.eq(((Item_time_literal *) item)->cached_time);
}
void Item_time_literal::print(String *str, enum_query_type query_type)
{
- char buff[MAX_DATE_STRING_REP_LENGTH];
str->append("TIME'");
- my_time_to_str(&ctime, buff, decimals);
- str->append(buff);
+ str->append(cached_time.cptr());
str->append('\'');
}
@@ -1804,191 +1798,194 @@ bool Item_func_from_days::get_date(MYSQL
}
-void Item_func_curdate::fix_length_and_dec()
+/**
+ Set time and time_packed from a TIME value.
+*/
+void MYSQL_TIME_cache::set_time(MYSQL_TIME *ltime, uint8 dec_arg)
{
- Item_date_func::fix_length_and_dec();
-
- store_now_in_TIME(&ctime);
-
- /* We don't need to set second_part and neg because they already 0 */
- ctime.hour= ctime.minute= ctime.second= 0;
- ctime.time_type= MYSQL_TIMESTAMP_DATE;
- ctime_as_longlong= (longlong) TIME_to_longlong_date_packed(&ctime);
+ DBUG_ASSERT(ltime->time_type == MYSQL_TIMESTAMP_TIME);
+ time= *ltime;
+ time_packed= TIME_to_longlong_time_packed(&time);
+ dec= dec_arg;
}
-String *Item_func_curdate::val_str(String *str)
+/**
+ Set time and time_packed from a DATE value.
+*/
+void MYSQL_TIME_cache::set_date(MYSQL_TIME *ltime)
{
- DBUG_ASSERT(fixed == 1);
- if (str->alloc(MAX_DATE_STRING_REP_LENGTH))
- {
- null_value= 1;
- return (String *) 0;
- }
- make_date((DATE_TIME_FORMAT *) 0, &ctime, str);
- return str;
+ DBUG_ASSERT(ltime->time_type == MYSQL_TIMESTAMP_DATE);
+ time= *ltime;
+ time_packed= TIME_to_longlong_date_packed(&time);
}
/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for local
- time zone. Defines time zone (local) used for whole CURDATE function.
+ Set time and time_packed from a DATETIME value.
*/
-void Item_func_curdate_local::store_now_in_TIME(MYSQL_TIME *now_time)
+void MYSQL_TIME_cache::set_datetime(MYSQL_TIME *ltime, uint8 dec_arg)
{
- THD *thd= current_thd;
- thd->variables.time_zone->gmt_sec_to_TIME(now_time,
- (my_time_t) thd->query_start());
- thd->time_zone_used= 1;
+ DBUG_ASSERT(ltime->time_type == MYSQL_TIMESTAMP_DATETIME);
+ time= *ltime;
+ time_packed= TIME_to_longlong_datetime_packed(&time);
+ dec= dec_arg;
}
/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for UTC
- time zone. Defines time zone (UTC) used for whole UTC_DATE function.
+ Set time and time_packed according to DATETIME value
+ in "struct timeval" representation and its time zone.
*/
-void Item_func_curdate_utc::store_now_in_TIME(MYSQL_TIME *now_time)
+void MYSQL_TIME_cache::set_datetime(struct timeval tv, uint8 dec_arg,
+ Time_zone *tz)
{
- my_tz_UTC->gmt_sec_to_TIME(now_time,
- (my_time_t) (current_thd->query_start()));
- /*
- We are not flagging this query as using time zone, since it uses fixed
- UTC-SYSTEM time-zone.
- */
+ tz->gmt_sec_to_TIME(&time, tv);
+ time_packed= TIME_to_longlong_datetime_packed(&time);
+ dec= dec_arg;
}
-bool Item_func_curdate::get_date(MYSQL_TIME *res,
- uint fuzzy_date __attribute__((unused)))
+/**
+ Set time and time_packed according to DATE value
+ in "struct timeval" representation and its time zone.
+*/
+void MYSQL_TIME_cache::set_date(struct timeval tv, Time_zone *tz)
{
- *res= ctime;
- return 0;
+ tz->gmt_sec_to_TIME(&time, (my_time_t) tv.tv_sec);
+ time.time_type= MYSQL_TIMESTAMP_DATE;
+ /* We don't need to set second_part and neg because they are already 0 */
+ time.hour= time.minute= time.second= 0;
+ time_packed= TIME_to_longlong_date_packed(&time);
}
-String *Item_func_curtime::val_str(String *str)
+/**
+ Set time and time_packed according to TIME value
+ in "struct timeval" representation and its time zone.
+*/
+void MYSQL_TIME_cache::set_time(struct timeval tv, uint8 dec_arg,
+ Time_zone *tz)
{
- DBUG_ASSERT(fixed == 1);
- str_value.set(buff, buff_length, &my_charset_latin1);
- return &str_value;
+ tz->gmt_sec_to_TIME(&time, tv);
+ datetime_to_time(&time);
+ time_packed= TIME_to_longlong_time_packed(&time);
+ dec= dec_arg;
}
-bool Item_func_curtime::get_time(MYSQL_TIME *ltime)
+/**
+ Cache string representation from the cached MYSQL_TIME representation.
+ If string representation has already been cached, then nothing happens.
+*/
+void MYSQL_TIME_cache::cache_string()
{
- *ltime= ctime;
- return false;
+ DBUG_ASSERT(time.time_type != MYSQL_TIMESTAMP_NONE);
+ if (!string_length)
+ string_length= my_TIME_to_str(&time, string_buff, decimals());
}
-void Item_func_curtime::fix_length_and_dec()
+/**
+ Cache string representation (if needed) and return it as C string.
+*/
+const char *MYSQL_TIME_cache::cptr()
{
- if (check_precision())
- return;
- store_now_in_TIME(&ctime);
- ctime_as_temporal= TIME_to_longlong_time_packed(&ctime);
- buff_length= (uint) my_time_to_str(&ctime, buff, decimals);
- fix_length_and_charset_datetime(buff_length);
+ cache_string();
+ return string_buff;
}
-void Item_func_curtime::store_now_in_TIME_tz(THD *thd, Time_zone *tz,
- MYSQL_TIME *now_time)
+/**
+ Cache string representation (if needed) and return it as String.
+*/
+String *MYSQL_TIME_cache::val_str(String *str)
{
- struct timeval tv= thd->query_start_timeval_trunc(decimals);
- tz->gmt_sec_to_TIME(now_time, (my_time_t) tv.tv_sec);
- now_time->second_part= tv.tv_usec;
- datetime_to_time(now_time);
+ cache_string();
+ str->set(string_buff, string_length, &my_charset_latin1);
+ return str;
}
-/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for local
- time zone. Defines time zone (local) used for whole CURTIME function.
-*/
-void Item_func_curtime_local::store_now_in_TIME(MYSQL_TIME *now_time)
+
+/* CURDATE() and UTC_DATE() */
+void Item_func_curdate::fix_length_and_dec()
{
THD *thd= current_thd;
- store_now_in_TIME_tz(thd, thd->variables.time_zone, now_time);
- thd->time_zone_used= 1;
+ Item_date_func::fix_length_and_dec();
+ cached_time.set_date(thd->query_start_timeval_trunc(decimals), time_zone());
}
-/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for UTC
- time zone. Defines time zone (UTC) used for whole UTC_TIME function.
-*/
-void Item_func_curtime_utc::store_now_in_TIME(MYSQL_TIME *now_time)
+Time_zone *Item_func_curdate_local::time_zone()
{
- store_now_in_TIME_tz(current_thd, my_tz_UTC, now_time);
- /*
- We are not flagging this query as using time zone, since it uses fixed
- UTC-SYSTEM time-zone.
- */
+ return current_thd->time_zone();
}
-String *Item_func_now::val_str(String *str)
+Time_zone *Item_func_curdate_utc::time_zone()
{
- DBUG_ASSERT(fixed == 1);
- str_value.set(buff, buff_length, &my_charset_numeric);
- return &str_value;
+ return my_tz_UTC;
}
-void Item_func_now::fix_length_and_dec()
+/* CURTIME() and UTC_TIME() */
+void Item_func_curtime::fix_length_and_dec()
{
if (check_precision())
return;
- store_now_in_TIME(&ctime);
- ctime_as_longlong= (longlong) TIME_to_longlong_datetime_packed(&ctime);
- buff_length= (uint) my_datetime_to_str(&ctime, buff, decimals);
- fix_length_and_charset_datetime(buff_length);
+ THD *thd= current_thd;
+ cached_time.set_time(thd->query_start_timeval_trunc(decimals), decimals,
+ time_zone());
+ /*
+ We use 8 instead of MAX_TIME_WIDTH (which is 10) becase:
+ - there is no sign
+ - hour is in the 2-digit range
+ */
+ fix_length_and_dec_and_charset_datetime(8, decimals);
}
-/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for local
- time zone. Defines time zone (local) used for whole NOW function.
-*/
-void Item_func_now_local::store_now_in_TIME(MYSQL_TIME *now_time)
+Time_zone *Item_func_curtime_local::time_zone()
{
- THD *thd= current_thd;
- struct timeval tv= thd->query_start_timeval_trunc(decimals);
- thd->variables.time_zone->gmt_sec_to_TIME(now_time, (my_time_t) tv.tv_sec);
- now_time->second_part= tv.tv_usec;
- thd->time_zone_used= 1;
+ return current_thd->time_zone();
}
-/**
- Converts current time in my_time_t to MYSQL_TIME represenatation for UTC
- time zone. Defines time zone (UTC) used for whole UTC_TIMESTAMP function.
-*/
-void Item_func_now_utc::store_now_in_TIME(MYSQL_TIME *now_time)
+Time_zone *Item_func_curtime_utc::time_zone()
+{
+ return my_tz_UTC;
+}
+
+
+/* NOW() and UTC_TIMESTAMP () */
+
+void Item_func_now::fix_length_and_dec()
{
+ if (check_precision())
+ return;
THD *thd= current_thd;
- struct timeval tv= thd->query_start_timeval_trunc(decimals);
- my_tz_UTC->gmt_sec_to_TIME(now_time, (my_time_t) thd->query_start());
- now_time->second_part= tv.tv_usec;
- /*
- We are not flagging this query as using time zone, since it uses fixed
- UTC-SYSTEM time-zone.
- */
+ cached_time.set_datetime(thd->query_start_timeval_trunc(decimals), decimals,
+ time_zone());
+ fix_length_and_dec_and_charset_datetime(MAX_DATETIME_WIDTH, decimals);
}
-bool Item_func_now::get_date(MYSQL_TIME *res,
- uint fuzzy_date __attribute__((unused)))
+Time_zone *Item_func_now_local::time_zone()
{
- *res= ctime;
- return 0;
+ return current_thd->time_zone();
+}
+
+
+Time_zone *Item_func_now_utc::time_zone()
+{
+ return my_tz_UTC;
}
int Item_func_now::save_in_field(Field *to, bool no_conversions)
{
to->set_notnull();
- return to->store_time(&ctime, decimals);
+ return to->store_time(cached_time.get_TIME(), decimals);
}
@@ -2001,14 +1998,13 @@ bool Item_func_sysdate_local::get_date(M
{
THD *thd= current_thd;
ulonglong tmp= my_micro_time();
- thd->variables.time_zone->gmt_sec_to_TIME(now_time,
- (my_time_t) (tmp / 1000000));
+ thd->time_zone()->gmt_sec_to_TIME(now_time,
+ (my_time_t) (tmp / 1000000));
if (decimals)
{
now_time->second_part= tmp % 1000000;
my_datetime_trunc(now_time, decimals);
}
- thd->time_zone_used= 1;
return false;
}
=== modified file 'sql/item_timefunc.h'
--- a/sql/item_timefunc.h 2011-11-02 14:05:10 +0000
+++ b/sql/item_timefunc.h 2011-11-03 09:33:45 +0000
@@ -658,17 +658,100 @@ public:
/**
+ Cache for MYSQL_TIME value with various representations.
+
+ - MYSQL_TIME representation (time) is initialized during set_XXX().
+ - Packed representation (time_packed) is also initialized during set_XXX().
+ - String representation (string_buff) is not initialized during set_XXX(),
+ It's initialized only if val_str() or cptr() are called.
+*/
+class MYSQL_TIME_cache
+{
+ MYSQL_TIME time; // MYSQL_TIME representation
+ longlong time_packed; // packed representation
+ char string_buff[MAX_DATE_STRING_REP_LENGTH]; // string representation
+ uint string_length; // length of string
+ uint8 dec; // Number of decimals
+ void cache_string(); // Store string representation to string_buff
+public:
+ MYSQL_TIME_cache()
+ {
+ time.time_type= MYSQL_TIMESTAMP_NONE;
+ string_length= 0;
+ string_buff[0]= '\0';
+ dec= 0;
+ }
+ // Initialize time and time_packed from MYSQL_TIME parameter.
+ void set_date(MYSQL_TIME *ltime);
+ void set_time(MYSQL_TIME *ltime, uint8 dec_arg);
+ void set_datetime(MYSQL_TIME *ltime, uint8 dec_arg);
+ // Initialize time and time_packed from "struct timeval" and time zone.
+ void set_date(struct timeval tv, Time_zone *tz);
+ void set_time(struct timeval tv, uint8 dec_arg, Time_zone *tz);
+ void set_datetime(struct timeval tv, uint8 dec_arg, Time_zone *tz);
+
+ /**
+ Test if cached value is equal to another MYSQL_TIME_cache value.
+ */
+ bool eq(const MYSQL_TIME_cache &tm) const
+ {
+ return val_packed() == tm.val_packed();
+ }
+
+ /**
+ Return number of decimal digits.
+ */
+ uint8 decimals() const
+ {
+ DBUG_ASSERT(time.time_type != MYSQL_TIMESTAMP_NONE);
+ return dec;
+ }
+
+ /**
+ Return packed representation.
+ */
+ longlong val_packed() const
+ {
+ DBUG_ASSERT(time.time_type != MYSQL_TIMESTAMP_NONE);
+ return time_packed;
+ }
+ /**
+ Store MYSQL_TIME representation into the given MYSQL_TIME variable.
+ */
+ void get_TIME(MYSQL_TIME *ltime) const
+ {
+ DBUG_ASSERT(time.time_type != MYSQL_TIMESTAMP_NONE);
+ *ltime= time;
+ }
+ /**
+ Return pointer to MYSQL_TIME representation.
+ */
+ MYSQL_TIME *get_TIME()
+ {
+ DBUG_ASSERT(time.time_type != MYSQL_TIMESTAMP_NONE);
+ return &time;
+ }
+ /**
+ Store string representation into String.
+ */
+ String *val_str(String *str);
+ /**
+ Return C string representation.
+ */
+ const char *cptr();
+};
+
+
+/**
DATE'2010-01-01'
*/
class Item_date_literal :public Item_date_func
{
- MYSQL_TIME ctime; // Date value
- longlong ctime_as_temporal; // Cached packed representation of ctime
+ MYSQL_TIME_cache cached_time;
public:
Item_date_literal(MYSQL_TIME *ltime) :Item_date_func()
{
- ctime= *ltime;
- ctime_as_temporal= TIME_to_longlong_date_packed(&ctime);
+ cached_time.set_date(ltime);
fix_length_and_dec();
fixed= 1;
}
@@ -677,14 +760,19 @@ public:
longlong val_date_temporal()
{
DBUG_ASSERT(fixed);
- return ctime_as_temporal;
+ return cached_time.val_packed();
}
bool get_date(MYSQL_TIME *ltime, uint fuzzy_date)
{
DBUG_ASSERT(fixed);
- *ltime= ctime;
+ cached_time.get_TIME(ltime);
return false;
}
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed);
+ return cached_time.val_str(str);
+ }
void fix_length_and_dec()
{
fix_length_and_dec_and_charset_datetime(MAX_DATE_WIDTH, 0);
@@ -711,14 +799,12 @@ public:
*/
class Item_time_literal :public Item_time_func
{
- MYSQL_TIME ctime; // Time value
- longlong ctime_as_temporal; // Cached packed representation of ctime
+ MYSQL_TIME_cache cached_time;
public:
Item_time_literal(MYSQL_TIME *ltime, uint dec_arg) :Item_time_func()
{
- ctime= *ltime;
- ctime_as_temporal= TIME_to_longlong_time_packed(&ctime);
decimals= min(dec_arg, DATETIME_MAX_DECIMALS);
+ cached_time.set_time(ltime, decimals);
fix_length_and_dec();
fixed= 1;
}
@@ -727,14 +813,19 @@ public:
longlong val_time_temporal()
{
DBUG_ASSERT(fixed);
- return ctime_as_temporal;
+ return cached_time.val_packed();
}
bool get_time(MYSQL_TIME *ltime)
{
DBUG_ASSERT(fixed);
- *ltime= ctime;
+ cached_time.get_TIME(ltime);
return false;
}
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed);
+ return cached_time.val_str(str);
+ }
void fix_length_and_dec()
{
fix_length_and_dec_and_charset_datetime(MAX_TIME_WIDTH, decimals);
@@ -761,14 +852,12 @@ public:
*/
class Item_datetime_literal :public Item_datetime_func
{
- MYSQL_TIME ctime; // Datetime value
- longlong ctime_as_temporal; // Cached packed representation of ctime
+ MYSQL_TIME_cache cached_time;
public:
Item_datetime_literal(MYSQL_TIME *ltime, uint dec_arg) :Item_datetime_func()
{
- ctime= *ltime;
- ctime_as_temporal= TIME_to_longlong_datetime_packed(&ctime);
decimals= min(dec_arg, DATETIME_MAX_DECIMALS);
+ cached_time.set_datetime(ltime, decimals);
fix_length_and_dec();
fixed= 1;
}
@@ -777,14 +866,19 @@ public:
longlong val_date_temporal()
{
DBUG_ASSERT(fixed);
- return ctime_as_temporal;
+ return cached_time.val_packed();
}
bool get_date(MYSQL_TIME *ltime, uint fuzzy_date)
{
DBUG_ASSERT(fixed);
- *ltime= ctime;
+ cached_time.get_TIME(ltime);
return false;
}
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed);
+ return cached_time.val_str(str);
+ }
void fix_length_and_dec()
{
fix_length_and_dec_and_charset_datetime(MAX_DATETIME_WIDTH, decimals);
@@ -810,35 +904,36 @@ public:
class Item_func_curtime :public Item_time_func
{
- char buff[9*2+32];
- uint buff_length;
- MYSQL_TIME ctime; // TIME value
- longlong ctime_as_temporal; // Cached packed representation of ctime
-protected:
- void store_now_in_TIME_tz(THD *thd, Time_zone *tz, MYSQL_TIME *now_time);
- /*
- Abstract method that defines which time zone is used for conversion.
- Converts time current time in my_time_t representation to broken-down
- MYSQL_TIME representation using UTC-SYSTEM or per-thread time zone.
- */
- virtual void store_now_in_TIME(MYSQL_TIME *now_time)=0;
+ MYSQL_TIME_cache cached_time; // Initialized in fix_length_and_dec
+protected:
+ // Abstract method that defines which time zone is used for conversion.
+ virtual Time_zone *time_zone()= 0;
public:
Item_func_curtime(uint8 dec_arg) :Item_time_func() { decimals= dec_arg; }
+ void fix_length_and_dec();
longlong val_time_temporal()
{
DBUG_ASSERT(fixed == 1);
- return ctime_as_temporal;
+ return cached_time.val_packed();
+ }
+ bool get_time(MYSQL_TIME *ltime)
+ {
+ DBUG_ASSERT(fixed == 1);
+ cached_time.get_TIME(ltime);
+ return false;
+ }
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed == 1);
+ return cached_time.val_str(&str_value);
}
- String *val_str(String *str);
- void fix_length_and_dec();
- bool get_time(MYSQL_TIME *ltime);
};
class Item_func_curtime_local :public Item_func_curtime
{
protected:
- virtual void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_curtime_local(ulong dec_arg) :Item_func_curtime(dec_arg) {}
const char *func_name() const { return "curtime"; }
@@ -848,7 +943,7 @@ public:
class Item_func_curtime_utc :public Item_func_curtime
{
protected:
- virtual void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_curtime_utc(ulong dec_arg) :Item_func_curtime(dec_arg) {}
const char *func_name() const { return "utc_time"; }
@@ -859,27 +954,35 @@ public:
class Item_func_curdate :public Item_date_func
{
- MYSQL_TIME ctime; // Initialized in fix_length_and_dec
- longlong ctime_as_longlong; // Initialized in fix_length_and_dec
+ MYSQL_TIME_cache cached_time; // Initialized in fix_length_and_dec
protected:
- virtual void store_now_in_TIME(MYSQL_TIME *now_time)=0;
+ virtual Time_zone *time_zone()= 0;
public:
Item_func_curdate() :Item_date_func() {}
+ void fix_length_and_dec();
longlong val_date_temporal()
{
DBUG_ASSERT(fixed == 1);
- return (ctime_as_longlong) ;
+ return cached_time.val_packed();
+ }
+ bool get_date(MYSQL_TIME *res, uint fuzzy_date)
+ {
+ DBUG_ASSERT(fixed == 1);
+ cached_time.get_TIME(res);
+ return false;
+ }
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed == 1);
+ return cached_time.val_str(&str_value);
}
- String *val_str(String *str);
- void fix_length_and_dec();
- bool get_date(MYSQL_TIME *res, uint fuzzy_date);
};
class Item_func_curdate_local :public Item_func_curdate
{
protected:
- void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_curdate_local() :Item_func_curdate() {}
const char *func_name() const { return "curdate"; }
@@ -889,7 +992,7 @@ public:
class Item_func_curdate_utc :public Item_func_curdate
{
protected:
- void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_curdate_utc() :Item_func_curdate() {}
const char *func_name() const { return "utc_date"; }
@@ -900,30 +1003,36 @@ public:
class Item_func_now :public Item_datetime_func
{
+ MYSQL_TIME_cache cached_time;
protected:
- MYSQL_TIME ctime; // Datetime value
- longlong ctime_as_longlong; // Cached packed representation of ctime
- char buff[20*2+32]; // +32 to make my_snprintf_{8bit|ucs2} happy
- uint buff_length;
- virtual void store_now_in_TIME(MYSQL_TIME *now_time)=0;
+ virtual Time_zone *time_zone()= 0;
public:
Item_func_now(uint8 dec_arg) :Item_datetime_func() { decimals= dec_arg; }
+ void fix_length_and_dec();
+ int save_in_field(Field *to, bool no_conversions);
longlong val_date_temporal()
{
DBUG_ASSERT(fixed == 1);
- return ctime_as_longlong;
+ return cached_time.val_packed();
+ }
+ bool get_date(MYSQL_TIME *res, uint fuzzy_date)
+ {
+ DBUG_ASSERT(fixed == 1);
+ cached_time.get_TIME(res);
+ return false;
+ }
+ String *val_str(String *str)
+ {
+ DBUG_ASSERT(fixed == 1);
+ return cached_time.val_str(&str_value);
}
- int save_in_field(Field *to, bool no_conversions);
- String *val_str(String *str);
- void fix_length_and_dec();
- bool get_date(MYSQL_TIME *res, uint fuzzy_date);
};
class Item_func_now_local :public Item_func_now
{
protected:
- virtual void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_now_local(ulong dec_arg) :Item_func_now(dec_arg) {}
const char *func_name() const { return "now"; }
@@ -934,7 +1043,7 @@ public:
class Item_func_now_utc :public Item_func_now
{
protected:
- virtual void store_now_in_TIME(MYSQL_TIME *now_time);
+ Time_zone *time_zone();
public:
Item_func_now_utc(ulong dec_arg) :Item_func_now(dec_arg) {}
const char *func_name() const { return "utc_timestamp"; }
=== modified file 'sql/sql_class.h'
--- a/sql/sql_class.h 2011-11-02 11:21:10 +0000
+++ b/sql/sql_class.h 2011-11-03 09:33:45 +0000
@@ -2709,6 +2709,11 @@ public:
return variables.sql_mode &
(MODE_NO_ZERO_IN_DATE | MODE_NO_ZERO_DATE | MODE_INVALID_DATES);
}
+ inline Time_zone *time_zone()
+ {
+ time_zone_used= 1;
+ return variables.time_zone;
+ }
inline time_t query_start()
{
query_start_used= 1;
=== modified file 'sql/sql_time.cc'
--- a/sql/sql_time.cc 2011-11-02 11:21:10 +0000
+++ b/sql/sql_time.cc 2011-11-03 09:33:45 +0000
@@ -625,9 +625,8 @@ my_time_t TIME_to_timestamp(THD *thd, co
my_time_t timestamp;
*in_dst_time_gap= 0;
- thd->time_zone_used= 1;
- timestamp= thd->variables.time_zone->TIME_to_gmt_sec(t, in_dst_time_gap);
+ timestamp= thd->time_zone()->TIME_to_gmt_sec(t, in_dst_time_gap);
if (timestamp)
{
return timestamp;
=== modified file 'sql/tztime.h'
--- a/sql/tztime.h 2011-06-30 15:50:45 +0000
+++ b/sql/tztime.h 2011-11-03 09:33:45 +0000
@@ -52,6 +52,15 @@ public:
*/
virtual void gmt_sec_to_TIME(MYSQL_TIME *tmp, my_time_t t) const = 0;
/**
+ Comverts "struct timeval" to local time in
+ broken down MYSQL_TIME represendation.
+ */
+ void gmt_sec_to_TIME(MYSQL_TIME *tmp, struct timeval tv)
+ {
+ gmt_sec_to_TIME(tmp, (my_time_t) tv.tv_sec);
+ tmp->second_part= tv.tv_usec;
+ }
+ /**
Because of constness of String returned by get_name() time zone name
have to be already zeroended to be able to use String::ptr() instead
of c_ptr().
No bundle (reason: useless for push emails).
| Thread |
|---|
| • bzr push into mysql-trunk branch (alexander.barkov:3547 to 3548) WL#946 | Alexander Barkov | 7 Nov |