1 #ifndef ITEM_TIMEFUNC_INCLUDED 2 #define ITEM_TIMEFUNC_INCLUDED 3 /* Copyright (c) 2000, 2011, Oracle and/or its affiliates. 4 Copyright (c) 2009-2011, Monty Program Ab 5 6 This program is free software; you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as published by 8 the Free Software Foundation; version 2 of the License. 9 10 This program is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 GNU General Public License for more details. 14 15 You should have received a copy of the GNU General Public License 16 along with this program; if not, write to the Free Software 17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA */ 18 19 20 /* Function items used by mysql */ 21 22 #ifdef USE_PRAGMA_INTERFACE 23 #pragma interface /* gcc class implementation */ 24 #endif 25 26 class MY_LOCALE; 27 28 enum date_time_format_types 29 { 30 TIME_ONLY= 0, TIME_MICROSECOND, DATE_ONLY, DATE_TIME, DATE_TIME_MICROSECOND 31 }; 32 33 34 bool get_interval_value(Item *args,interval_type int_type, INTERVAL *interval); 35 36 37 class Item_long_func_date_field: public Item_long_func 38 { check_arguments()39 bool check_arguments() const 40 { return args[0]->check_type_can_return_date(func_name()); } 41 public: Item_long_func_date_field(THD * thd,Item * a)42 Item_long_func_date_field(THD *thd, Item *a) 43 :Item_long_func(thd, a) { } 44 }; 45 46 47 class Item_long_func_time_field: public Item_long_func 48 { check_arguments()49 bool check_arguments() const 50 { return args[0]->check_type_can_return_time(func_name()); } 51 public: Item_long_func_time_field(THD * thd,Item * a)52 Item_long_func_time_field(THD *thd, Item *a) 53 :Item_long_func(thd, a) { } 54 }; 55 56 57 class Item_func_period_add :public Item_long_func 58 { check_arguments()59 bool check_arguments() const 60 { return check_argument_types_can_return_int(0, 2); } 61 public: Item_func_period_add(THD * thd,Item * a,Item * b)62 Item_func_period_add(THD *thd, Item *a, Item *b): Item_long_func(thd, a, b) {} 63 longlong val_int(); func_name()64 const char *func_name() const { return "period_add"; } fix_length_and_dec()65 bool fix_length_and_dec() 66 { 67 max_length=6*MY_CHARSET_BIN_MB_MAXLEN; 68 return FALSE; 69 } get_copy(THD * thd)70 Item *get_copy(THD *thd) 71 { return get_item_copy<Item_func_period_add>(thd, this); } 72 }; 73 74 75 class Item_func_period_diff :public Item_long_func 76 { check_arguments()77 bool check_arguments() const 78 { return check_argument_types_can_return_int(0, 2); } 79 public: Item_func_period_diff(THD * thd,Item * a,Item * b)80 Item_func_period_diff(THD *thd, Item *a, Item *b): Item_long_func(thd, a, b) {} 81 longlong val_int(); func_name()82 const char *func_name() const { return "period_diff"; } fix_length_and_dec()83 bool fix_length_and_dec() 84 { 85 decimals=0; 86 max_length=6*MY_CHARSET_BIN_MB_MAXLEN; 87 return FALSE; 88 } get_copy(THD * thd)89 Item *get_copy(THD *thd) 90 { return get_item_copy<Item_func_period_diff>(thd, this); } 91 }; 92 93 94 class Item_func_to_days :public Item_long_func_date_field 95 { 96 public: Item_func_to_days(THD * thd,Item * a)97 Item_func_to_days(THD *thd, Item *a): Item_long_func_date_field(thd, a) {} 98 longlong val_int(); func_name()99 const char *func_name() const { return "to_days"; } fix_length_and_dec()100 bool fix_length_and_dec() 101 { 102 decimals=0; 103 max_length=6*MY_CHARSET_BIN_MB_MAXLEN; 104 maybe_null=1; 105 return FALSE; 106 } 107 enum_monotonicity_info get_monotonicity_info() const; 108 longlong val_int_endpoint(bool left_endp, bool *incl_endp); check_partition_func_processor(void * int_arg)109 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)110 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)111 bool check_valid_arguments_processor(void *int_arg) 112 { 113 return !has_date_args(); 114 } get_copy(THD * thd)115 Item *get_copy(THD *thd) 116 { return get_item_copy<Item_func_to_days>(thd, this); } 117 }; 118 119 120 class Item_func_to_seconds :public Item_longlong_func 121 { check_arguments()122 bool check_arguments() const 123 { return check_argument_types_can_return_date(0, arg_count); } 124 public: Item_func_to_seconds(THD * thd,Item * a)125 Item_func_to_seconds(THD *thd, Item *a): Item_longlong_func(thd, a) {} 126 longlong val_int(); func_name()127 const char *func_name() const { return "to_seconds"; } fix_length_and_dec()128 bool fix_length_and_dec() 129 { 130 decimals=0; 131 fix_char_length(12); 132 maybe_null= 1; 133 return FALSE; 134 } 135 enum_monotonicity_info get_monotonicity_info() const; 136 longlong val_int_endpoint(bool left_endp, bool *incl_endp); check_partition_func_processor(void * bool_arg)137 bool check_partition_func_processor(void *bool_arg) { return FALSE;} 138 139 /* Only meaningful with date part and optional time part */ check_valid_arguments_processor(void * int_arg)140 bool check_valid_arguments_processor(void *int_arg) 141 { 142 return !has_date_args(); 143 } get_copy(THD * thd)144 Item *get_copy(THD *thd) 145 { return get_item_copy<Item_func_to_seconds>(thd, this); } 146 }; 147 148 149 class Item_func_dayofmonth :public Item_long_func_date_field 150 { 151 public: Item_func_dayofmonth(THD * thd,Item * a)152 Item_func_dayofmonth(THD *thd, Item *a): Item_long_func_date_field(thd, a) {} 153 longlong val_int(); func_name()154 const char *func_name() const { return "dayofmonth"; } fix_length_and_dec()155 bool fix_length_and_dec() 156 { 157 decimals=0; 158 max_length=2*MY_CHARSET_BIN_MB_MAXLEN; 159 maybe_null=1; 160 return FALSE; 161 } check_partition_func_processor(void * int_arg)162 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)163 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)164 bool check_valid_arguments_processor(void *int_arg) 165 { 166 return !has_date_args(); 167 } get_copy(THD * thd)168 Item *get_copy(THD *thd) 169 { return get_item_copy<Item_func_dayofmonth>(thd, this); } 170 }; 171 172 173 class Item_func_month :public Item_long_func 174 { 175 public: Item_func_month(THD * thd,Item * a)176 Item_func_month(THD *thd, Item *a): Item_long_func(thd, a) 177 { } 178 longlong val_int(); func_name()179 const char *func_name() const { return "month"; } fix_length_and_dec()180 bool fix_length_and_dec() 181 { 182 decimals= 0; 183 fix_char_length(2); 184 maybe_null=1; 185 return FALSE; 186 } check_partition_func_processor(void * int_arg)187 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)188 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)189 bool check_valid_arguments_processor(void *int_arg) 190 { 191 return !has_date_args(); 192 } get_copy(THD * thd)193 Item *get_copy(THD *thd) 194 { return get_item_copy<Item_func_month>(thd, this); } 195 }; 196 197 198 class Item_func_monthname :public Item_str_func 199 { 200 MY_LOCALE *locale; 201 public: Item_func_monthname(THD * thd,Item * a)202 Item_func_monthname(THD *thd, Item *a): Item_str_func(thd, a) {} func_name()203 const char *func_name() const { return "monthname"; } 204 String *val_str(String *str); 205 bool fix_length_and_dec(); check_partition_func_processor(void * int_arg)206 bool check_partition_func_processor(void *int_arg) {return TRUE;} check_valid_arguments_processor(void * int_arg)207 bool check_valid_arguments_processor(void *int_arg) 208 { 209 return !has_date_args(); 210 } check_vcol_func_processor(void * arg)211 bool check_vcol_func_processor(void *arg) 212 { 213 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 214 } get_copy(THD * thd)215 Item *get_copy(THD *thd) 216 { return get_item_copy<Item_func_monthname>(thd, this); } 217 }; 218 219 220 class Item_func_dayofyear :public Item_long_func_date_field 221 { 222 public: Item_func_dayofyear(THD * thd,Item * a)223 Item_func_dayofyear(THD *thd, Item *a): Item_long_func_date_field(thd, a) {} 224 longlong val_int(); func_name()225 const char *func_name() const { return "dayofyear"; } fix_length_and_dec()226 bool fix_length_and_dec() 227 { 228 decimals= 0; 229 fix_char_length(3); 230 maybe_null=1; 231 return FALSE; 232 } check_partition_func_processor(void * int_arg)233 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)234 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)235 bool check_valid_arguments_processor(void *int_arg) 236 { 237 return !has_date_args(); 238 } get_copy(THD * thd)239 Item *get_copy(THD *thd) 240 { return get_item_copy<Item_func_dayofyear>(thd, this); } 241 }; 242 243 244 class Item_func_hour :public Item_long_func_time_field 245 { 246 public: Item_func_hour(THD * thd,Item * a)247 Item_func_hour(THD *thd, Item *a): Item_long_func_time_field(thd, a) {} 248 longlong val_int(); func_name()249 const char *func_name() const { return "hour"; } fix_length_and_dec()250 bool fix_length_and_dec() 251 { 252 decimals=0; 253 max_length=2*MY_CHARSET_BIN_MB_MAXLEN; 254 maybe_null=1; 255 return FALSE; 256 } check_partition_func_processor(void * int_arg)257 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)258 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)259 bool check_valid_arguments_processor(void *int_arg) 260 { 261 return !has_time_args(); 262 } get_copy(THD * thd)263 Item *get_copy(THD *thd) 264 { return get_item_copy<Item_func_hour>(thd, this); } 265 }; 266 267 268 class Item_func_minute :public Item_long_func_time_field 269 { 270 public: Item_func_minute(THD * thd,Item * a)271 Item_func_minute(THD *thd, Item *a): Item_long_func_time_field(thd, a) {} 272 longlong val_int(); func_name()273 const char *func_name() const { return "minute"; } fix_length_and_dec()274 bool fix_length_and_dec() 275 { 276 decimals=0; 277 max_length=2*MY_CHARSET_BIN_MB_MAXLEN; 278 maybe_null=1; 279 return FALSE; 280 } check_partition_func_processor(void * int_arg)281 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)282 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)283 bool check_valid_arguments_processor(void *int_arg) 284 { 285 return !has_time_args(); 286 } get_copy(THD * thd)287 Item *get_copy(THD *thd) 288 { return get_item_copy<Item_func_minute>(thd, this); } 289 }; 290 291 292 class Item_func_quarter :public Item_long_func_date_field 293 { 294 public: Item_func_quarter(THD * thd,Item * a)295 Item_func_quarter(THD *thd, Item *a): Item_long_func_date_field(thd, a) {} 296 longlong val_int(); func_name()297 const char *func_name() const { return "quarter"; } fix_length_and_dec()298 bool fix_length_and_dec() 299 { 300 decimals=0; 301 max_length=1*MY_CHARSET_BIN_MB_MAXLEN; 302 maybe_null=1; 303 return FALSE; 304 } check_partition_func_processor(void * int_arg)305 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)306 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)307 bool check_valid_arguments_processor(void *int_arg) 308 { 309 return !has_date_args(); 310 } get_copy(THD * thd)311 Item *get_copy(THD *thd) 312 { return get_item_copy<Item_func_quarter>(thd, this); } 313 }; 314 315 316 class Item_func_second :public Item_long_func_time_field 317 { 318 public: Item_func_second(THD * thd,Item * a)319 Item_func_second(THD *thd, Item *a): Item_long_func_time_field(thd, a) {} 320 longlong val_int(); func_name()321 const char *func_name() const { return "second"; } fix_length_and_dec()322 bool fix_length_and_dec() 323 { 324 decimals=0; 325 max_length=2*MY_CHARSET_BIN_MB_MAXLEN; 326 maybe_null=1; 327 return FALSE; 328 } check_partition_func_processor(void * int_arg)329 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)330 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)331 bool check_valid_arguments_processor(void *int_arg) 332 { 333 return !has_time_args(); 334 } get_copy(THD * thd)335 Item *get_copy(THD *thd) 336 { return get_item_copy<Item_func_second>(thd, this); } 337 }; 338 339 340 class Item_func_week :public Item_long_func 341 { check_arguments()342 bool check_arguments() const 343 { 344 return args[0]->check_type_can_return_date(func_name()) || 345 (arg_count > 1 && args[1]->check_type_can_return_int(func_name())); 346 } 347 public: Item_func_week(THD * thd,Item * a)348 Item_func_week(THD *thd, Item *a): Item_long_func(thd, a) {} Item_func_week(THD * thd,Item * a,Item * b)349 Item_func_week(THD *thd, Item *a, Item *b): Item_long_func(thd, a, b) {} 350 longlong val_int(); func_name()351 const char *func_name() const { return "week"; } fix_length_and_dec()352 bool fix_length_and_dec() 353 { 354 decimals=0; 355 max_length=2*MY_CHARSET_BIN_MB_MAXLEN; 356 maybe_null=1; 357 return FALSE; 358 } check_vcol_func_processor(void * arg)359 bool check_vcol_func_processor(void *arg) 360 { 361 if (arg_count == 2) 362 return FALSE; 363 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 364 } check_valid_arguments_processor(void * int_arg)365 bool check_valid_arguments_processor(void *int_arg) 366 { 367 return arg_count == 2; 368 } get_copy(THD * thd)369 Item *get_copy(THD *thd) 370 { return get_item_copy<Item_func_week>(thd, this); } 371 }; 372 373 class Item_func_yearweek :public Item_long_func 374 { check_arguments()375 bool check_arguments() const 376 { 377 return args[0]->check_type_can_return_date(func_name()) || 378 args[1]->check_type_can_return_int(func_name()); 379 } 380 public: Item_func_yearweek(THD * thd,Item * a,Item * b)381 Item_func_yearweek(THD *thd, Item *a, Item *b) 382 :Item_long_func(thd, a, b) {} 383 longlong val_int(); func_name()384 const char *func_name() const { return "yearweek"; } fix_length_and_dec()385 bool fix_length_and_dec() 386 { 387 decimals=0; 388 max_length=6*MY_CHARSET_BIN_MB_MAXLEN; 389 maybe_null=1; 390 return FALSE; 391 } check_partition_func_processor(void * int_arg)392 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)393 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)394 bool check_valid_arguments_processor(void *int_arg) 395 { 396 return !has_date_args(); 397 } get_copy(THD * thd)398 Item *get_copy(THD *thd) 399 { return get_item_copy<Item_func_yearweek>(thd, this); } 400 }; 401 402 403 class Item_func_year :public Item_long_func_date_field 404 { 405 public: Item_func_year(THD * thd,Item * a)406 Item_func_year(THD *thd, Item *a): Item_long_func_date_field(thd, a) {} 407 longlong val_int(); func_name()408 const char *func_name() const { return "year"; } 409 enum_monotonicity_info get_monotonicity_info() const; 410 longlong val_int_endpoint(bool left_endp, bool *incl_endp); fix_length_and_dec()411 bool fix_length_and_dec() 412 { 413 decimals=0; 414 max_length=4*MY_CHARSET_BIN_MB_MAXLEN; 415 maybe_null=1; 416 return FALSE; 417 } check_partition_func_processor(void * int_arg)418 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)419 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)420 bool check_valid_arguments_processor(void *int_arg) 421 { 422 return !has_date_args(); 423 } get_copy(THD * thd)424 Item *get_copy(THD *thd) 425 { return get_item_copy<Item_func_year>(thd, this); } 426 }; 427 428 429 class Item_func_weekday :public Item_long_func 430 { 431 bool odbc_type; 432 public: Item_func_weekday(THD * thd,Item * a,bool type_arg)433 Item_func_weekday(THD *thd, Item *a, bool type_arg): 434 Item_long_func(thd, a), odbc_type(type_arg) { } 435 longlong val_int(); func_name()436 const char *func_name() const 437 { 438 return (odbc_type ? "dayofweek" : "weekday"); 439 } get_date(MYSQL_TIME * ltime,ulonglong fuzzydate)440 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate) 441 { 442 return type_handler()->Item_get_date(this, ltime, fuzzydate); 443 } fix_length_and_dec()444 bool fix_length_and_dec() 445 { 446 decimals= 0; 447 fix_char_length(1); 448 maybe_null=1; 449 return FALSE; 450 } check_partition_func_processor(void * int_arg)451 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)452 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)453 bool check_valid_arguments_processor(void *int_arg) 454 { 455 return !has_date_args(); 456 } get_copy(THD * thd)457 Item *get_copy(THD *thd) 458 { return get_item_copy<Item_func_weekday>(thd, this); } 459 }; 460 461 class Item_func_dayname :public Item_str_func 462 { 463 MY_LOCALE *locale; 464 public: Item_func_dayname(THD * thd,Item * a)465 Item_func_dayname(THD *thd, Item *a): Item_str_func(thd, a) {} func_name()466 const char *func_name() const { return "dayname"; } 467 String *val_str(String *str); type_handler()468 const Type_handler *type_handler() const { return &type_handler_varchar; } 469 bool fix_length_and_dec(); check_partition_func_processor(void * int_arg)470 bool check_partition_func_processor(void *int_arg) {return TRUE;} check_vcol_func_processor(void * arg)471 bool check_vcol_func_processor(void *arg) 472 { 473 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 474 } check_valid_arguments_processor(void * int_arg)475 bool check_valid_arguments_processor(void *int_arg) 476 { 477 return !has_date_args(); 478 } get_copy(THD * thd)479 Item *get_copy(THD *thd) 480 { return get_item_copy<Item_func_dayname>(thd, this); } 481 }; 482 483 484 class Item_func_seconds_hybrid: public Item_func_numhybrid 485 { 486 public: Item_func_seconds_hybrid(THD * thd)487 Item_func_seconds_hybrid(THD *thd): Item_func_numhybrid(thd) {} Item_func_seconds_hybrid(THD * thd,Item * a)488 Item_func_seconds_hybrid(THD *thd, Item *a): Item_func_numhybrid(thd, a) {} fix_length_and_dec_generic(uint dec)489 void fix_length_and_dec_generic(uint dec) 490 { 491 DBUG_ASSERT(dec <= TIME_SECOND_PART_DIGITS); 492 decimals= dec; 493 max_length=17 + (decimals ? decimals + 1 : 0); 494 maybe_null= true; 495 if (decimals) 496 set_handler(&type_handler_newdecimal); 497 else 498 set_handler(type_handler_long_or_longlong()); 499 } real_op()500 double real_op() { DBUG_ASSERT(0); return 0; } str_op(String * str)501 String *str_op(String *str) { DBUG_ASSERT(0); return 0; } date_op(MYSQL_TIME * ltime,ulonglong fuzzydate)502 bool date_op(MYSQL_TIME *ltime, ulonglong fuzzydate) 503 { 504 DBUG_ASSERT(0); 505 return true; 506 } 507 }; 508 509 510 class Item_func_unix_timestamp :public Item_func_seconds_hybrid 511 { 512 bool get_timestamp_value(my_time_t *seconds, ulong *second_part); 513 public: Item_func_unix_timestamp(THD * thd)514 Item_func_unix_timestamp(THD *thd): Item_func_seconds_hybrid(thd) {} Item_func_unix_timestamp(THD * thd,Item * a)515 Item_func_unix_timestamp(THD *thd, Item *a): 516 Item_func_seconds_hybrid(thd, a) {} func_name()517 const char *func_name() const { return "unix_timestamp"; } 518 enum_monotonicity_info get_monotonicity_info() const; 519 longlong val_int_endpoint(bool left_endp, bool *incl_endp); check_partition_func_processor(void * int_arg)520 bool check_partition_func_processor(void *int_arg) {return FALSE;} 521 /* 522 UNIX_TIMESTAMP() depends on the current timezone 523 (and thus may not be used as a partitioning function) 524 when its argument is NOT of the TIMESTAMP type. 525 */ check_valid_arguments_processor(void * int_arg)526 bool check_valid_arguments_processor(void *int_arg) 527 { 528 return !has_timestamp_args(); 529 } check_vcol_func_processor(void * arg)530 bool check_vcol_func_processor(void *arg) 531 { 532 if (arg_count) 533 return FALSE; 534 return mark_unsupported_function(func_name(), "()", arg, VCOL_TIME_FUNC); 535 } fix_length_and_dec()536 bool fix_length_and_dec() 537 { 538 fix_length_and_dec_generic(arg_count ? args[0]->datetime_precision() : 0); 539 return FALSE; 540 } 541 longlong int_op(); 542 my_decimal *decimal_op(my_decimal* buf); get_copy(THD * thd)543 Item *get_copy(THD *thd) 544 { return get_item_copy<Item_func_unix_timestamp>(thd, this); } 545 }; 546 547 548 class Item_func_time_to_sec :public Item_func_seconds_hybrid 549 { 550 public: Item_func_time_to_sec(THD * thd,Item * item)551 Item_func_time_to_sec(THD *thd, Item *item): 552 Item_func_seconds_hybrid(thd, item) {} func_name()553 const char *func_name() const { return "time_to_sec"; } check_partition_func_processor(void * int_arg)554 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)555 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)556 bool check_valid_arguments_processor(void *int_arg) 557 { 558 return !has_time_args(); 559 } fix_length_and_dec()560 bool fix_length_and_dec() 561 { 562 fix_length_and_dec_generic(args[0]->time_precision()); 563 return FALSE; 564 } 565 longlong int_op(); 566 my_decimal *decimal_op(my_decimal* buf); get_copy(THD * thd)567 Item *get_copy(THD *thd) 568 { return get_item_copy<Item_func_time_to_sec>(thd, this); } 569 }; 570 571 572 class Item_temporal_func: public Item_func 573 { 574 public: Item_temporal_func(THD * thd)575 Item_temporal_func(THD *thd): Item_func(thd) {} Item_temporal_func(THD * thd,Item * a)576 Item_temporal_func(THD *thd, Item *a): Item_func(thd, a) {} Item_temporal_func(THD * thd,Item * a,Item * b)577 Item_temporal_func(THD *thd, Item *a, Item *b): Item_func(thd, a, b) {} Item_temporal_func(THD * thd,Item * a,Item * b,Item * c)578 Item_temporal_func(THD *thd, Item *a, Item *b, Item *c): Item_func(thd, a, b, c) {} 579 String *val_str(String *str); val_int()580 longlong val_int() { return val_int_from_date(); } val_real()581 double val_real() { return val_real_from_date(); } get_date(MYSQL_TIME * res,ulonglong fuzzy_date)582 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date) { DBUG_ASSERT(0); return 1; } val_decimal(my_decimal * decimal_value)583 my_decimal *val_decimal(my_decimal *decimal_value) 584 { return val_decimal_from_date(decimal_value); } 585 }; 586 587 588 /** 589 Abstract class for functions returning TIME, DATE, DATETIME or string values, 590 whose data type depends on parameters and is set at fix_fields time. 591 */ 592 class Item_temporal_hybrid_func: public Item_hybrid_func 593 { 594 protected: 595 String ascii_buf; // Conversion buffer 596 public: Item_temporal_hybrid_func(THD * thd,Item * a,Item * b)597 Item_temporal_hybrid_func(THD *thd, Item *a, Item *b): 598 Item_hybrid_func(thd, a, b) {} 599 val_int()600 longlong val_int() { return val_int_from_date(); } val_real()601 double val_real() { return val_real_from_date(); } 602 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date)= 0; val_decimal(my_decimal * decimal_value)603 my_decimal *val_decimal(my_decimal *decimal_value) 604 { return val_decimal_from_date(decimal_value); } 605 606 /** 607 Fix the returned timestamp to match field_type(), 608 which is important for val_str(). 609 */ 610 bool fix_temporal_type(MYSQL_TIME *ltime); 611 /** 612 Return string value in ASCII character set. 613 */ 614 String *val_str_ascii(String *str); 615 /** 616 Return string value in @@character_set_connection. 617 */ val_str(String * str)618 String *val_str(String *str) 619 { 620 return val_str_from_val_str_ascii(str, &ascii_buf); 621 } 622 }; 623 624 625 class Item_datefunc :public Item_temporal_func 626 { 627 public: Item_datefunc(THD * thd)628 Item_datefunc(THD *thd): Item_temporal_func(thd) { } Item_datefunc(THD * thd,Item * a)629 Item_datefunc(THD *thd, Item *a): Item_temporal_func(thd, a) { } Item_datefunc(THD * thd,Item * a,Item * b)630 Item_datefunc(THD *thd, Item *a, Item *b): Item_temporal_func(thd, a, b) { } type_handler()631 const Type_handler *type_handler() const { return &type_handler_newdate; } fix_length_and_dec()632 bool fix_length_and_dec() 633 { 634 fix_attributes_date(); 635 maybe_null= (arg_count > 0); 636 return FALSE; 637 } 638 }; 639 640 641 class Item_timefunc :public Item_temporal_func 642 { 643 public: Item_timefunc(THD * thd)644 Item_timefunc(THD *thd): Item_temporal_func(thd) {} Item_timefunc(THD * thd,Item * a)645 Item_timefunc(THD *thd, Item *a): Item_temporal_func(thd, a) {} Item_timefunc(THD * thd,Item * a,Item * b)646 Item_timefunc(THD *thd, Item *a, Item *b): Item_temporal_func(thd, a, b) {} Item_timefunc(THD * thd,Item * a,Item * b,Item * c)647 Item_timefunc(THD *thd, Item *a, Item *b, Item *c): 648 Item_temporal_func(thd, a, b ,c) {} type_handler()649 const Type_handler *type_handler() const { return &type_handler_time2; } 650 }; 651 652 653 class Item_datetimefunc :public Item_temporal_func 654 { 655 public: Item_datetimefunc(THD * thd)656 Item_datetimefunc(THD *thd): Item_temporal_func(thd) {} Item_datetimefunc(THD * thd,Item * a)657 Item_datetimefunc(THD *thd, Item *a): Item_temporal_func(thd, a) {} Item_datetimefunc(THD * thd,Item * a,Item * b,Item * c)658 Item_datetimefunc(THD *thd, Item *a, Item *b, Item *c): 659 Item_temporal_func(thd, a, b ,c) {} type_handler()660 const Type_handler *type_handler() const { return &type_handler_datetime2; } 661 }; 662 663 664 /* Abstract CURTIME function. Children should define what time zone is used */ 665 666 class Item_func_curtime :public Item_timefunc 667 { 668 MYSQL_TIME ltime; 669 query_id_t last_query_id; 670 public: Item_func_curtime(THD * thd,uint dec)671 Item_func_curtime(THD *thd, uint dec): Item_timefunc(thd), last_query_id(0) 672 { decimals= dec; } 673 bool fix_fields(THD *, Item **); fix_length_and_dec()674 bool fix_length_and_dec() { fix_attributes_time(decimals); return FALSE; } 675 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); 676 /* 677 Abstract method that defines which time zone is used for conversion. 678 Converts time current time in my_time_t representation to broken-down 679 MYSQL_TIME representation using UTC-SYSTEM or per-thread time zone. 680 */ 681 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time)=0; check_vcol_func_processor(void * arg)682 bool check_vcol_func_processor(void *arg) 683 { 684 return mark_unsupported_function(func_name(), "()", arg, VCOL_TIME_FUNC); 685 } 686 void print(String *str, enum_query_type query_type); 687 }; 688 689 690 class Item_func_curtime_local :public Item_func_curtime 691 { 692 public: Item_func_curtime_local(THD * thd,uint dec)693 Item_func_curtime_local(THD *thd, uint dec): Item_func_curtime(thd, dec) {} func_name()694 const char *func_name() const { return "curtime"; } 695 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); get_copy(THD * thd)696 Item *get_copy(THD *thd) 697 { return get_item_copy<Item_func_curtime_local>(thd, this); } 698 }; 699 700 701 class Item_func_curtime_utc :public Item_func_curtime 702 { 703 public: Item_func_curtime_utc(THD * thd,uint dec)704 Item_func_curtime_utc(THD *thd, uint dec): Item_func_curtime(thd, dec) {} func_name()705 const char *func_name() const { return "utc_time"; } 706 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); get_copy(THD * thd)707 Item *get_copy(THD *thd) 708 { return get_item_copy<Item_func_curtime_utc>(thd, this); } 709 }; 710 711 712 /* Abstract CURDATE function. See also Item_func_curtime. */ 713 714 class Item_func_curdate :public Item_datefunc 715 { 716 query_id_t last_query_id; 717 MYSQL_TIME ltime; 718 public: Item_func_curdate(THD * thd)719 Item_func_curdate(THD *thd): Item_datefunc(thd), last_query_id(0) {} 720 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); 721 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time)=0; check_vcol_func_processor(void * arg)722 bool check_vcol_func_processor(void *arg) 723 { 724 return mark_unsupported_function(func_name(), "()", arg, VCOL_TIME_FUNC); 725 } 726 }; 727 728 729 class Item_func_curdate_local :public Item_func_curdate 730 { 731 public: Item_func_curdate_local(THD * thd)732 Item_func_curdate_local(THD *thd): Item_func_curdate(thd) {} func_name()733 const char *func_name() const { return "curdate"; } 734 void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); get_copy(THD * thd)735 Item *get_copy(THD *thd) 736 { return get_item_copy<Item_func_curdate_local>(thd, this); } 737 }; 738 739 740 class Item_func_curdate_utc :public Item_func_curdate 741 { 742 public: Item_func_curdate_utc(THD * thd)743 Item_func_curdate_utc(THD *thd): Item_func_curdate(thd) {} func_name()744 const char *func_name() const { return "utc_date"; } 745 void store_now_in_TIME(THD* thd, MYSQL_TIME *now_time); get_copy(THD * thd)746 Item *get_copy(THD *thd) 747 { return get_item_copy<Item_func_curdate_utc>(thd, this); } 748 }; 749 750 751 /* Abstract CURRENT_TIMESTAMP function. See also Item_func_curtime */ 752 753 class Item_func_now :public Item_datetimefunc 754 { 755 MYSQL_TIME ltime; 756 query_id_t last_query_id; 757 public: Item_func_now(THD * thd,uint dec)758 Item_func_now(THD *thd, uint dec): Item_datetimefunc(thd), last_query_id(0) 759 { decimals= dec; } 760 bool fix_fields(THD *, Item **); fix_length_and_dec()761 bool fix_length_and_dec() 762 { fix_attributes_datetime(decimals); return FALSE;} 763 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); 764 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time)=0; check_vcol_func_processor(void * arg)765 bool check_vcol_func_processor(void *arg) 766 { 767 /* 768 NOW is safe for replication as slaves will run with same time as 769 master 770 */ 771 return mark_unsupported_function(func_name(), "()", arg, VCOL_TIME_FUNC); 772 } 773 void print(String *str, enum_query_type query_type); 774 }; 775 776 777 class Item_func_now_local :public Item_func_now 778 { 779 public: Item_func_now_local(THD * thd,uint dec)780 Item_func_now_local(THD *thd, uint dec): Item_func_now(thd, dec) {} func_name()781 const char *func_name() const { return "current_timestamp"; } 782 int save_in_field(Field *field, bool no_conversions); 783 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); functype()784 virtual enum Functype functype() const { return NOW_FUNC; } get_copy(THD * thd)785 Item *get_copy(THD *thd) 786 { return get_item_copy<Item_func_now_local>(thd, this); } 787 }; 788 789 790 class Item_func_now_utc :public Item_func_now 791 { 792 public: Item_func_now_utc(THD * thd,uint dec)793 Item_func_now_utc(THD *thd, uint dec): Item_func_now(thd, dec) {} func_name()794 const char *func_name() const { return "utc_timestamp"; } 795 virtual void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); functype()796 virtual enum Functype functype() const { return NOW_UTC_FUNC; } check_vcol_func_processor(void * arg)797 virtual bool check_vcol_func_processor(void *arg) 798 { 799 return mark_unsupported_function(func_name(), "()", arg, 800 VCOL_TIME_FUNC | VCOL_NON_DETERMINISTIC); 801 } get_copy(THD * thd)802 Item *get_copy(THD *thd) 803 { return get_item_copy<Item_func_now_utc>(thd, this); } 804 }; 805 806 807 /* 808 This is like NOW(), but always uses the real current time, not the 809 query_start(). This matches the Oracle behavior. 810 */ 811 class Item_func_sysdate_local :public Item_func_now 812 { 813 public: Item_func_sysdate_local(THD * thd,uint dec)814 Item_func_sysdate_local(THD *thd, uint dec): Item_func_now(thd, dec) {} const_item()815 bool const_item() const { return 0; } func_name()816 const char *func_name() const { return "sysdate"; } 817 void store_now_in_TIME(THD *thd, MYSQL_TIME *now_time); 818 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); used_tables()819 table_map used_tables() const { return RAND_TABLE_BIT; } check_vcol_func_processor(void * arg)820 bool check_vcol_func_processor(void *arg) 821 { 822 return mark_unsupported_function(func_name(), "()", arg, 823 VCOL_TIME_FUNC | VCOL_NON_DETERMINISTIC); 824 } functype()825 virtual enum Functype functype() const { return SYSDATE_FUNC; } get_copy(THD * thd)826 Item *get_copy(THD *thd) 827 { return get_item_copy<Item_func_sysdate_local>(thd, this); } 828 }; 829 830 831 class Item_func_from_days :public Item_datefunc 832 { check_arguments()833 bool check_arguments() const 834 { return args[0]->check_type_can_return_int(func_name()); } 835 public: Item_func_from_days(THD * thd,Item * a)836 Item_func_from_days(THD *thd, Item *a): Item_datefunc(thd, a) {} func_name()837 const char *func_name() const { return "from_days"; } 838 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); check_partition_func_processor(void * int_arg)839 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)840 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)841 bool check_valid_arguments_processor(void *int_arg) 842 { 843 return has_date_args() || has_time_args(); 844 } get_copy(THD * thd)845 Item *get_copy(THD *thd) 846 { return get_item_copy<Item_func_from_days>(thd, this); } 847 }; 848 849 850 class Item_func_date_format :public Item_str_func 851 { check_arguments()852 bool check_arguments() const 853 { 854 return args[0]->check_type_can_return_date(func_name()) || 855 check_argument_types_can_return_text(1, arg_count); 856 } 857 const MY_LOCALE *locale; 858 int fixed_length; 859 String value; 860 protected: 861 bool is_time_format; 862 public: Item_func_date_format(THD * thd,Item * a,Item * b)863 Item_func_date_format(THD *thd, Item *a, Item *b): 864 Item_str_func(thd, a, b), locale(0), is_time_format(false) {} Item_func_date_format(THD * thd,Item * a,Item * b,Item * c)865 Item_func_date_format(THD *thd, Item *a, Item *b, Item *c): 866 Item_str_func(thd, a, b, c), locale(0), is_time_format(false) {} 867 String *val_str(String *str); func_name()868 const char *func_name() const { return "date_format"; } 869 bool fix_length_and_dec(); 870 uint format_length(const String *format); 871 bool eq(const Item *item, bool binary_cmp) const; check_vcol_func_processor(void * arg)872 bool check_vcol_func_processor(void *arg) 873 { 874 if (arg_count > 2) 875 return false; 876 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 877 } get_copy(THD * thd)878 Item *get_copy(THD *thd) 879 { return get_item_copy<Item_func_date_format>(thd, this); } 880 }; 881 882 class Item_func_time_format: public Item_func_date_format 883 { 884 public: Item_func_time_format(THD * thd,Item * a,Item * b)885 Item_func_time_format(THD *thd, Item *a, Item *b): 886 Item_func_date_format(thd, a, b) { is_time_format= true; } func_name()887 const char *func_name() const { return "time_format"; } check_vcol_func_processor(void * arg)888 bool check_vcol_func_processor(void *arg) { return false; } get_copy(THD * thd)889 Item *get_copy(THD *thd) 890 { return get_item_copy<Item_func_time_format>(thd, this); } 891 }; 892 893 894 class Item_func_from_unixtime :public Item_datetimefunc 895 { check_arguments()896 bool check_arguments() const 897 { return args[0]->check_type_can_return_decimal(func_name()); } 898 Time_zone *tz; 899 public: Item_func_from_unixtime(THD * thd,Item * a)900 Item_func_from_unixtime(THD *thd, Item *a): Item_datetimefunc(thd, a) {} func_name()901 const char *func_name() const { return "from_unixtime"; } 902 bool fix_length_and_dec(); 903 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); check_vcol_func_processor(void * arg)904 bool check_vcol_func_processor(void *arg) 905 { 906 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 907 } get_copy(THD * thd)908 Item *get_copy(THD *thd) 909 { return get_item_copy<Item_func_from_unixtime>(thd, this); } 910 }; 911 912 913 /* 914 We need Time_zone class declaration for storing pointers in 915 Item_func_convert_tz. 916 */ 917 class Time_zone; 918 919 /* 920 This class represents CONVERT_TZ() function. 921 The important fact about this function that it is handled in special way. 922 When such function is met in expression time_zone system tables are added 923 to global list of tables to open, so later those already opened and locked 924 tables can be used during this function calculation for loading time zone 925 descriptions. 926 */ 927 class Item_func_convert_tz :public Item_datetimefunc 928 { check_arguments()929 bool check_arguments() const 930 { 931 return args[0]->check_type_can_return_date(func_name()) || 932 check_argument_types_can_return_text(1, arg_count); 933 } 934 /* 935 If time zone parameters are constants we are caching objects that 936 represent them (we use separate from_tz_cached/to_tz_cached members 937 to indicate this fact, since NULL is legal value for from_tz/to_tz 938 members. 939 */ 940 bool from_tz_cached, to_tz_cached; 941 Time_zone *from_tz, *to_tz; 942 public: Item_func_convert_tz(THD * thd,Item * a,Item * b,Item * c)943 Item_func_convert_tz(THD *thd, Item *a, Item *b, Item *c): 944 Item_datetimefunc(thd, a, b, c), from_tz_cached(0), to_tz_cached(0) {} func_name()945 const char *func_name() const { return "convert_tz"; } fix_length_and_dec()946 bool fix_length_and_dec() 947 { 948 fix_attributes_datetime(args[0]->datetime_precision()); 949 maybe_null= true; 950 return FALSE; 951 } 952 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); 953 void cleanup(); get_copy(THD * thd)954 Item *get_copy(THD *thd) 955 { return get_item_copy<Item_func_convert_tz>(thd, this); } 956 }; 957 958 959 class Item_func_sec_to_time :public Item_timefunc 960 { check_arguments()961 bool check_arguments() const 962 { return args[0]->check_type_can_return_decimal(func_name()); } 963 public: Item_func_sec_to_time(THD * thd,Item * item)964 Item_func_sec_to_time(THD *thd, Item *item): Item_timefunc(thd, item) {} 965 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); fix_length_and_dec()966 bool fix_length_and_dec() 967 { 968 fix_attributes_time(args[0]->decimals); 969 maybe_null= true; 970 return FALSE; 971 } func_name()972 const char *func_name() const { return "sec_to_time"; } get_copy(THD * thd)973 Item *get_copy(THD *thd) 974 { return get_item_copy<Item_func_sec_to_time>(thd, this); } 975 }; 976 977 978 class Item_date_add_interval :public Item_temporal_hybrid_func 979 { 980 public: 981 const interval_type int_type; // keep it public 982 const bool date_sub_interval; // keep it public Item_date_add_interval(THD * thd,Item * a,Item * b,interval_type type_arg,bool neg_arg)983 Item_date_add_interval(THD *thd, Item *a, Item *b, interval_type type_arg, 984 bool neg_arg): 985 Item_temporal_hybrid_func(thd, a, b),int_type(type_arg), 986 date_sub_interval(neg_arg) {} func_name()987 const char *func_name() const { return "date_add_interval"; } 988 bool fix_length_and_dec(); 989 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); 990 bool eq(const Item *item, bool binary_cmp) const; 991 void print(String *str, enum_query_type query_type); precedence()992 enum precedence precedence() const { return INTERVAL_PRECEDENCE; } need_parentheses_in_default()993 bool need_parentheses_in_default() { return true; } get_copy(THD * thd)994 Item *get_copy(THD *thd) 995 { return get_item_copy<Item_date_add_interval>(thd, this); } 996 }; 997 998 999 class Item_extract :public Item_int_func 1000 { 1001 bool date_value; set_date_length(uint32 length)1002 void set_date_length(uint32 length) 1003 { 1004 /* 1005 Although DATE components (e.g. YEAR, YEAR_MONTH, QUARTER, MONTH, WEEK) 1006 cannot have a sign, we should probably still add +1, 1007 because all around the code we assume that max_length is sign inclusive. 1008 Another options is to set unsigned_flag to "true". 1009 */ 1010 max_length= length; //QQ: see above 1011 date_value= true; 1012 } set_time_length(uint32 length)1013 void set_time_length(uint32 length) 1014 { 1015 max_length= length + 1/*sign*/; 1016 date_value= false; 1017 } 1018 public: 1019 const interval_type int_type; // keep it public Item_extract(THD * thd,interval_type type_arg,Item * a)1020 Item_extract(THD *thd, interval_type type_arg, Item *a): 1021 Item_int_func(thd, a), int_type(type_arg) {} type_handler()1022 const Type_handler *type_handler() const 1023 { 1024 switch (int_type) { 1025 case INTERVAL_YEAR: 1026 case INTERVAL_YEAR_MONTH: 1027 case INTERVAL_QUARTER: 1028 case INTERVAL_MONTH: 1029 case INTERVAL_WEEK: 1030 case INTERVAL_DAY: 1031 case INTERVAL_DAY_HOUR: 1032 case INTERVAL_DAY_MINUTE: 1033 case INTERVAL_DAY_SECOND: 1034 case INTERVAL_HOUR: 1035 case INTERVAL_HOUR_MINUTE: 1036 case INTERVAL_HOUR_SECOND: 1037 case INTERVAL_MINUTE: 1038 case INTERVAL_MINUTE_SECOND: 1039 case INTERVAL_SECOND: 1040 case INTERVAL_MICROSECOND: 1041 case INTERVAL_SECOND_MICROSECOND: 1042 return &type_handler_long; 1043 case INTERVAL_DAY_MICROSECOND: 1044 case INTERVAL_HOUR_MICROSECOND: 1045 case INTERVAL_MINUTE_MICROSECOND: 1046 return &type_handler_longlong; 1047 case INTERVAL_LAST: 1048 break; 1049 } 1050 DBUG_ASSERT(0); 1051 return &type_handler_longlong; 1052 } 1053 longlong val_int(); functype()1054 enum Functype functype() const { return EXTRACT_FUNC; } func_name()1055 const char *func_name() const { return "extract"; } 1056 bool fix_length_and_dec(); 1057 bool eq(const Item *item, bool binary_cmp) const; 1058 void print(String *str, enum_query_type query_type); check_partition_func_processor(void * int_arg)1059 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)1060 bool check_vcol_func_processor(void *arg) 1061 { 1062 if (int_type != INTERVAL_WEEK) 1063 return FALSE; 1064 return mark_unsupported_function(func_name(), "()", arg, VCOL_SESSION_FUNC); 1065 } check_valid_arguments_processor(void * int_arg)1066 bool check_valid_arguments_processor(void *int_arg) 1067 { 1068 switch (int_type) { 1069 case INTERVAL_YEAR: 1070 case INTERVAL_YEAR_MONTH: 1071 case INTERVAL_QUARTER: 1072 case INTERVAL_MONTH: 1073 /* case INTERVAL_WEEK: Not allowed as partitioning function, bug#57071 */ 1074 case INTERVAL_DAY: 1075 return !has_date_args(); 1076 case INTERVAL_DAY_HOUR: 1077 case INTERVAL_DAY_MINUTE: 1078 case INTERVAL_DAY_SECOND: 1079 case INTERVAL_DAY_MICROSECOND: 1080 return !has_datetime_args(); 1081 case INTERVAL_HOUR: 1082 case INTERVAL_HOUR_MINUTE: 1083 case INTERVAL_HOUR_SECOND: 1084 case INTERVAL_MINUTE: 1085 case INTERVAL_MINUTE_SECOND: 1086 case INTERVAL_SECOND: 1087 case INTERVAL_MICROSECOND: 1088 case INTERVAL_HOUR_MICROSECOND: 1089 case INTERVAL_MINUTE_MICROSECOND: 1090 case INTERVAL_SECOND_MICROSECOND: 1091 return !has_time_args(); 1092 default: 1093 /* 1094 INTERVAL_LAST is only an end marker, 1095 INTERVAL_WEEK depends on default_week_format which is a session 1096 variable and cannot be used for partitioning. See bug#57071. 1097 */ 1098 break; 1099 } 1100 return true; 1101 } get_copy(THD * thd)1102 Item *get_copy(THD *thd) 1103 { return get_item_copy<Item_extract>(thd, this); } 1104 }; 1105 1106 1107 class Item_char_typecast :public Item_str_func 1108 { 1109 uint cast_length; 1110 CHARSET_INFO *cast_cs, *from_cs; 1111 bool charset_conversion; 1112 String tmp_value; 1113 bool m_suppress_warning_to_error_escalation; has_explicit_length()1114 bool has_explicit_length() const { return cast_length != ~0U; } 1115 String *reuse(String *src, size_t length); 1116 String *copy(String *src, CHARSET_INFO *cs); 1117 uint adjusted_length_with_warn(uint length); 1118 void check_truncation_with_warn(String *src, size_t dstlen); 1119 void fix_length_and_dec_internal(CHARSET_INFO *fromcs); 1120 public: Item_char_typecast(THD * thd,Item * a,uint length_arg,CHARSET_INFO * cs_arg)1121 Item_char_typecast(THD *thd, Item *a, uint length_arg, CHARSET_INFO *cs_arg): 1122 Item_str_func(thd, a), cast_length(length_arg), cast_cs(cs_arg), 1123 m_suppress_warning_to_error_escalation(false) {} functype()1124 enum Functype functype() const { return CHAR_TYPECAST_FUNC; } 1125 bool eq(const Item *item, bool binary_cmp) const; func_name()1126 const char *func_name() const { return "cast_as_char"; } cast_charset()1127 CHARSET_INFO *cast_charset() const { return cast_cs; } 1128 String *val_str(String *a); 1129 void fix_length_and_dec_generic(); 1130 void fix_length_and_dec_numeric(); fix_length_and_dec_str()1131 void fix_length_and_dec_str() 1132 { 1133 fix_length_and_dec_generic(); 1134 m_suppress_warning_to_error_escalation= true; 1135 } fix_length_and_dec()1136 bool fix_length_and_dec() 1137 { 1138 return args[0]->type_handler()->Item_char_typecast_fix_length_and_dec(this); 1139 } 1140 void print(String *str, enum_query_type query_type); need_parentheses_in_default()1141 bool need_parentheses_in_default() { return true; } get_copy(THD * thd)1142 Item *get_copy(THD *thd) 1143 { return get_item_copy<Item_char_typecast>(thd, this); } 1144 }; 1145 1146 1147 class Item_temporal_typecast: public Item_temporal_func 1148 { 1149 public: Item_temporal_typecast(THD * thd,Item * a)1150 Item_temporal_typecast(THD *thd, Item *a): Item_temporal_func(thd, a) {} 1151 virtual const char *cast_type() const = 0; 1152 void print(String *str, enum_query_type query_type); 1153 }; 1154 1155 class Item_date_typecast :public Item_temporal_typecast 1156 { 1157 public: Item_date_typecast(THD * thd,Item * a)1158 Item_date_typecast(THD *thd, Item *a): Item_temporal_typecast(thd, a) {} func_name()1159 const char *func_name() const { return "cast_as_date"; } 1160 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); cast_type()1161 const char *cast_type() const { return "date"; } type_handler()1162 const Type_handler *type_handler() const { return &type_handler_newdate; } fix_length_and_dec()1163 bool fix_length_and_dec() 1164 { 1165 return args[0]->type_handler()->Item_date_typecast_fix_length_and_dec(this); 1166 } get_copy(THD * thd)1167 Item *get_copy(THD *thd) 1168 { return get_item_copy<Item_date_typecast>(thd, this); } 1169 }; 1170 1171 1172 class Item_time_typecast :public Item_temporal_typecast 1173 { 1174 public: Item_time_typecast(THD * thd,Item * a,uint dec_arg)1175 Item_time_typecast(THD *thd, Item *a, uint dec_arg): 1176 Item_temporal_typecast(thd, a) { decimals= dec_arg; } func_name()1177 const char *func_name() const { return "cast_as_time"; } 1178 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); cast_type()1179 const char *cast_type() const { return "time"; } type_handler()1180 const Type_handler *type_handler() const { return &type_handler_time2; } fix_length_and_dec()1181 bool fix_length_and_dec() 1182 { 1183 return args[0]->type_handler()-> 1184 Item_time_typecast_fix_length_and_dec(this); 1185 } get_copy(THD * thd)1186 Item *get_copy(THD *thd) 1187 { return get_item_copy<Item_time_typecast>(thd, this); } 1188 }; 1189 1190 1191 class Item_datetime_typecast :public Item_temporal_typecast 1192 { 1193 public: Item_datetime_typecast(THD * thd,Item * a,uint dec_arg)1194 Item_datetime_typecast(THD *thd, Item *a, uint dec_arg): 1195 Item_temporal_typecast(thd, a) { decimals= dec_arg; } func_name()1196 const char *func_name() const { return "cast_as_datetime"; } cast_type()1197 const char *cast_type() const { return "datetime"; } type_handler()1198 const Type_handler *type_handler() const { return &type_handler_datetime2; } 1199 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); fix_length_and_dec()1200 bool fix_length_and_dec() 1201 { 1202 return args[0]->type_handler()-> 1203 Item_datetime_typecast_fix_length_and_dec(this); 1204 } get_copy(THD * thd)1205 Item *get_copy(THD *thd) 1206 { return get_item_copy<Item_datetime_typecast>(thd, this); } 1207 }; 1208 1209 1210 class Item_func_makedate :public Item_datefunc 1211 { check_arguments()1212 bool check_arguments() const 1213 { return check_argument_types_can_return_int(0, arg_count); } 1214 public: Item_func_makedate(THD * thd,Item * a,Item * b)1215 Item_func_makedate(THD *thd, Item *a, Item *b): 1216 Item_datefunc(thd, a, b) {} func_name()1217 const char *func_name() const { return "makedate"; } 1218 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); get_copy(THD * thd)1219 Item *get_copy(THD *thd) 1220 { return get_item_copy<Item_func_makedate>(thd, this); } 1221 }; 1222 1223 1224 class Item_func_add_time :public Item_temporal_hybrid_func 1225 { 1226 const bool is_date; 1227 int sign; 1228 1229 public: Item_func_add_time(THD * thd,Item * a,Item * b,bool type_arg,bool neg_arg)1230 Item_func_add_time(THD *thd, Item *a, Item *b, bool type_arg, bool neg_arg): 1231 Item_temporal_hybrid_func(thd, a, b), is_date(type_arg) 1232 { sign= neg_arg ? -1 : 1; } 1233 bool fix_length_and_dec(); 1234 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); func_name()1235 const char *func_name() const 1236 { 1237 return is_date ? "timestamp" : sign > 0 ? "addtime" : "subtime"; 1238 } get_copy(THD * thd)1239 Item *get_copy(THD *thd) 1240 { return get_item_copy<Item_func_add_time>(thd, this); } 1241 }; 1242 1243 class Item_func_timediff :public Item_timefunc 1244 { check_arguments()1245 bool check_arguments() const 1246 { return check_argument_types_can_return_time(0, arg_count); } 1247 public: Item_func_timediff(THD * thd,Item * a,Item * b)1248 Item_func_timediff(THD *thd, Item *a, Item *b): Item_timefunc(thd, a, b) {} func_name()1249 const char *func_name() const { return "timediff"; } fix_length_and_dec()1250 bool fix_length_and_dec() 1251 { 1252 uint dec= MY_MAX(args[0]->time_precision(), args[1]->time_precision()); 1253 fix_attributes_time(dec); 1254 maybe_null= true; 1255 return FALSE; 1256 } 1257 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); get_copy(THD * thd)1258 Item *get_copy(THD *thd) 1259 { return get_item_copy<Item_func_timediff>(thd, this); } 1260 }; 1261 1262 class Item_func_maketime :public Item_timefunc 1263 { check_arguments()1264 bool check_arguments() const 1265 { 1266 return check_argument_types_can_return_int(0, 2) || 1267 args[2]->check_type_can_return_decimal(func_name()); 1268 } 1269 public: Item_func_maketime(THD * thd,Item * a,Item * b,Item * c)1270 Item_func_maketime(THD *thd, Item *a, Item *b, Item *c): 1271 Item_timefunc(thd, a, b, c) 1272 {} fix_length_and_dec()1273 bool fix_length_and_dec() 1274 { 1275 fix_attributes_time(args[2]->decimals); 1276 maybe_null= true; 1277 return FALSE; 1278 } func_name()1279 const char *func_name() const { return "maketime"; } 1280 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); get_copy(THD * thd)1281 Item *get_copy(THD *thd) 1282 { return get_item_copy<Item_func_maketime>(thd, this); } 1283 }; 1284 1285 1286 class Item_func_microsecond :public Item_long_func_time_field 1287 { 1288 public: Item_func_microsecond(THD * thd,Item * a)1289 Item_func_microsecond(THD *thd, Item *a): Item_long_func_time_field(thd, a) {} 1290 longlong val_int(); func_name()1291 const char *func_name() const { return "microsecond"; } fix_length_and_dec()1292 bool fix_length_and_dec() 1293 { 1294 decimals=0; 1295 maybe_null=1; 1296 fix_char_length(6); 1297 return FALSE; 1298 } check_partition_func_processor(void * int_arg)1299 bool check_partition_func_processor(void *int_arg) {return FALSE;} check_vcol_func_processor(void * arg)1300 bool check_vcol_func_processor(void *arg) { return FALSE;} check_valid_arguments_processor(void * int_arg)1301 bool check_valid_arguments_processor(void *int_arg) 1302 { 1303 return !has_time_args(); 1304 } get_copy(THD * thd)1305 Item *get_copy(THD *thd) 1306 { return get_item_copy<Item_func_microsecond>(thd, this); } 1307 }; 1308 1309 1310 class Item_func_timestamp_diff :public Item_longlong_func 1311 { check_arguments()1312 bool check_arguments() const 1313 { return check_argument_types_can_return_date(0, arg_count); } 1314 const interval_type int_type; 1315 public: Item_func_timestamp_diff(THD * thd,Item * a,Item * b,interval_type type_arg)1316 Item_func_timestamp_diff(THD *thd, Item *a, Item *b, interval_type type_arg): 1317 Item_longlong_func(thd, a, b), int_type(type_arg) {} func_name()1318 const char *func_name() const { return "timestampdiff"; } 1319 longlong val_int(); fix_length_and_dec()1320 bool fix_length_and_dec() 1321 { 1322 decimals=0; 1323 maybe_null=1; 1324 return FALSE; 1325 } 1326 virtual void print(String *str, enum_query_type query_type); get_copy(THD * thd)1327 Item *get_copy(THD *thd) 1328 { return get_item_copy<Item_func_timestamp_diff>(thd, this); } 1329 }; 1330 1331 1332 enum date_time_format 1333 { 1334 USA_FORMAT, JIS_FORMAT, ISO_FORMAT, EUR_FORMAT, INTERNAL_FORMAT 1335 }; 1336 1337 class Item_func_get_format :public Item_str_ascii_func 1338 { 1339 public: 1340 const timestamp_type type; // keep it public Item_func_get_format(THD * thd,timestamp_type type_arg,Item * a)1341 Item_func_get_format(THD *thd, timestamp_type type_arg, Item *a): 1342 Item_str_ascii_func(thd, a), type(type_arg) 1343 {} 1344 String *val_str_ascii(String *str); func_name()1345 const char *func_name() const { return "get_format"; } fix_length_and_dec()1346 bool fix_length_and_dec() 1347 { 1348 maybe_null= 1; 1349 decimals=0; 1350 fix_length_and_charset(17, default_charset()); 1351 return FALSE; 1352 } 1353 virtual void print(String *str, enum_query_type query_type); get_copy(THD * thd)1354 Item *get_copy(THD *thd) 1355 { return get_item_copy<Item_func_get_format>(thd, this); } 1356 }; 1357 1358 1359 class Item_func_str_to_date :public Item_temporal_hybrid_func 1360 { 1361 timestamp_type cached_timestamp_type; 1362 bool const_item; 1363 String subject_converter; 1364 String format_converter; 1365 CHARSET_INFO *internal_charset; 1366 public: Item_func_str_to_date(THD * thd,Item * a,Item * b)1367 Item_func_str_to_date(THD *thd, Item *a, Item *b): 1368 Item_temporal_hybrid_func(thd, a, b), const_item(false), 1369 internal_charset(NULL) 1370 {} 1371 bool get_date(MYSQL_TIME *ltime, ulonglong fuzzy_date); func_name()1372 const char *func_name() const { return "str_to_date"; } 1373 bool fix_length_and_dec(); get_copy(THD * thd)1374 Item *get_copy(THD *thd) 1375 { return get_item_copy<Item_func_str_to_date>(thd, this); } 1376 }; 1377 1378 1379 class Item_func_last_day :public Item_datefunc 1380 { check_arguments()1381 bool check_arguments() const 1382 { return args[0]->check_type_can_return_date(func_name()); } 1383 public: Item_func_last_day(THD * thd,Item * a)1384 Item_func_last_day(THD *thd, Item *a): Item_datefunc(thd, a) {} func_name()1385 const char *func_name() const { return "last_day"; } 1386 bool get_date(MYSQL_TIME *res, ulonglong fuzzy_date); get_copy(THD * thd)1387 Item *get_copy(THD *thd) 1388 { return get_item_copy<Item_func_last_day>(thd, this); } 1389 }; 1390 1391 #endif /* ITEM_TIMEFUNC_INCLUDED */ 1392