Valgrind warning happens due to missing NULL value check in
Item::get_date. The fix is to add this check.
mysql-test/r/func_time.result:
test case
mysql-test/t/func_time.test:
test case
sql/item.cc:
added check for NULL value
Analysis:
A query with implicit grouping is one with aggregate functions and
no GROUP BY clause. MariaDB inherits from MySQL an SQL extenstion
that allows mixing aggregate functions with non-aggregate fields.
If a query with such mixed select clause produces an empty result
set, the meaning of aggregate functions is well defined - either
NULL (MIN, MAX, etc.), or 0 (count(*)). However the non-aggregated
fields must also have some value, and the only reasonable value in
the case of empty result is NULL.
The cause of the many wrong results was that if a field is declared
as non-nullable (e.g. because it is a PK or NOT NULL), the semantic
analysis and the optimization phases treat this field as non-nullable,
and generate all related query plan elements based on this assumption.
Later during execution, these incorrectly configured/generated query
plan elements result in a wrong result because the selected fields
are not null due to the not-null assumption during optimization.
Solution:
Detect before the context analysys phase that a query uses implicit
grouping with mixed aggregates/non-aggregates, and set all fields
as nullable. The parser already walks the SELECT clause, and
already sets Item::with_sum_func for Items that reference aggreagate
functions. The patch adds a symmetric Item::with_field so that all
Items that reference an Item_field are marked during their
construction at parse time in the same way as with aggregate function
use.
and a different fix for lp:736370
cache temporal expression in Item_cache_int, not in Item_string.
invoke get_datetime_value() to create a correct Item_cache_int.
Implement Item_cache_int::clone, as it's a proper constant
of service in prepared statements).
sql/sql_prepare.cc:
At mysql_stmt_get_longdata(): instead of pushing an internal
error handler (as done in 5.1-tree) we save, set and restore
the statement's diagnostics area and warning info.
The problem was that server didn't check resulting size of prepared
statement argument which was set using mysql_send_long_data() API.
By calling mysql_send_long_data() several times it was possible
to create overly big string and thus force server to allocate
memory for it. There was no way to limit this allocation.
The solution is to add check for size of result string against
value of max_long_data_size start-up parameter. When intermediate
string exceeds max_long_data_size value an appropriate error message
is emitted.
We can't use existing max_allowed_packet parameter for this purpose
since its value is limited by 1GB and therefore using it as a limit
for data set through mysql_send_long_data() API would have been an
incompatible change. Newly introduced max_long_data_size parameter
gets value from max_allowed_packet parameter unless its value is
specified explicitly. This new parameter is marked as deprecated
and will be eventually replaced by max_allowed_packet parameter.
Value of max_long_data_size parameter can be set only at server
startup.
mysql-test/t/variables.test:
Added checking for new start-up parameter max_long_data_size.
sql/item.cc:
Added call to my_message() when accumulated string exceeds
max_long_data_size value. my_message() calls error handler
that was installed in mysql_stmt_get_longdata before call
to Item_param::set_longdata.
The error handler then sets state, last_error and last_errno
fields for current statement to values which correspond to
error which was caught.
sql/mysql_priv.h:
Added max_long_data_size variable declaration.
sql/mysqld.cc:
Added support for start-up parameter 'max_long_data_size'.
This parameter limits size of data which can be sent from
client to server using mysql_send_long_data() API.
sql/set_var.cc:
Added variable 'max_long_data_size' into list of variables
displayed by command 'show variables'.
sql/sql_prepare.cc:
Added error handler class Set_longdata_error_handler.
This handler is used to catch any errors that can be
generated during execution of Item_param::set_longdata().
Source code snippet that makes checking for statement's state
during statement execution is moved from Prepared_statement::execute()
to Prepared_statement::execute_loop() in order not to call
set_parameters() when statement has failed during
set_long_data() execution. If this hadn't been done
the call to set_parameters() would have failed.
tests/mysql_client_test.c:
A testcase for the bug #56976 was added.
@ mysql-test/r/ctype_latin1.result
@ mysql-test/r/ctype_utf8.result
@ mysql-test/t/ctype_latin1.test
@ mysql-test/t/ctype_utf8.test
Adding tests
@ sql/mysqld.h
@ sql/item.cc
@ sql/sql_parse.cc
@ sql/sql_view.cc
Refactoring (thanks to Guilhem for the idea):
Item_string::print() was hard to understand because of the different
QT_ constants: in "query_type==QT_x", QT_x is explicitely included
but the other two QT_ are implicitely excluded. The combinations
with '||' and '&&' make this even harder.
- logic is now more "explicit" by changing QT_ constants to a bitmap of flags:
QT_ORDINARY: no change,
QT_IS -> QT_TO_SYSTEM_CHARSET | QT_WITHOUT_INTRODUCERS,
QT_EXPLAIN -> QT_TO_SYSTEM_CHARSET
(QT_EXPLAIN was introduced in the first version of the Bug#57341 patch)
- Item_string::print() is rewritten using those flags
Bugfix itself:
When QT_TO_SYSTEM_CHARSET is used alone (with no QT_WITHOUT_INTRODUCERS),
we print string literals as follows:
- display introducers if they were in the original query
- print ASCII characters as is
- print non-ASCII characters using hex-escape
Note: as "EXPLAIN" output is only for human readability purposes
and does not need to be a pasrable SQL, so using hex-escape is Ok.
ErrConvString class perfectly suites for hex escaping purposes.
and collateral changes.
* introduce my_hrtime_t, my_timediff_t, and conversion macros
* inroduce TIME_RESULT, but it can only be returned from Item::cmp_type(),
never from Item::result_type()
* pack_time/unpack_time function for "packed" representation of
MYSQL_TIME in a longlong that can be compared
* ADDTIME()/SUBTIME()/+- INTERVAL now work with TIME values
* numbers aren't quoted in EXPLAIN EXTENDED
* new column I_S.COLUMNS.DATETIME_PRECISION
* date/time values are compares to anything as date/time, not as strings or numbers.
* old timestamp(X) is no longer supported
* MYSQL_TIME to string conversion functions take precision as an argument
* unified the warnings from Field_timestamp/datetime/time/date/newdate store methods
* Field_timestamp_hires, Field_datetime_hires, Field_time_hires
* Field_temporal
* Lazy_string class to pass a value (string, number, time) polymorphically down the stack
* make_truncated_value_warning and Field::set_datetime_warning use Lazy_string as an argument, removed char*/int/double variants
* removed Field::can_be_compared_as_longlong(). Use Field::cmp_type() == INT_RESULT instead
* introduced Item::cmp_result() instead of Item::is_datetime() and Item::result_as_longlong()
* in many cases date/time types are treated like other types, not as special cases
* greatly simplified Arg_comparator (regarding date/time/year code)
* SEC_TO_TIME is real function, not integer.
* microsecond precision in NOW, CURTIME, etc
* Item_temporal. All items derived from it only provide get_date, but no val* methods
* replication of NOW(6)
* Protocol::store(time) now takes the precision as an argument
* @@TIMESTAMP is a double
client/mysqlbinlog.cc:
remove unneded casts
include/my_sys.h:
introduce my_hrtime_t, my_timediff_t, and conversion macros
include/my_time.h:
pack_time/unpack_time, etc.
convenience functions to work with MYSQL_TIME::second_part
libmysql/libmysql.c:
str_to_time() is gone. str_to_datetime() does it now.
my_TIME_to_str() takes the precision as an argument
mysql-test/include/ps_conv.inc:
time is not equal to datetime anymore
mysql-test/r/distinct.result:
a test for an old MySQL bug
mysql-test/r/explain.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/func_default.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/func_sapdb.result:
when decimals=NOT_FIXED_DEC it means "not fixed" indeed
mysql-test/r/func_test.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/func_time.result:
ADDTIME()/SUBTIME()/+- INTERVAL now work with TIME values
mysql-test/r/having.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/information_schema.result:
new column I_S.COLUMNS.DATETIME_PRECISION
mysql-test/r/join_outer.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/metadata.result:
TIMESTAMP no longer has zerofill flag
mysql-test/r/range.result:
invalid datetime is not compared with as a string
mysql-test/r/select.result:
NO_ZERO_IN_DATE, etc only affect storage - according to the manual
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/subselect.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/sysdate_is_now.result:
when decimals=NOT_FIXED_DEC it means "not fixed" indeed
mysql-test/r/type_blob.result:
TIMESTAMP(N) is not deprecated
mysql-test/r/type_timestamp.result:
old TIMESTAMP(X) semantics is not supported anymore
mysql-test/r/union.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/r/varbinary.result:
numbers aren't quoted in EXPLAIN EXTENDED
mysql-test/t/distinct.test:
test for an old MySQL bug
mysql-test/t/func_time.test:
+- INTERVAL now works with TIME values
mysql-test/t/select.test:
typo
mysql-test/t/subselect.test:
only one error per statement, please
mysql-test/t/system_mysql_db_fix40123.test:
old timestamp(X) is no longer supported
mysql-test/t/system_mysql_db_fix50030.test:
old timestamp(X) is no longer supported
mysql-test/t/system_mysql_db_fix50117.test:
old timestamp(X) is no longer supported
mysql-test/t/type_blob.test:
old timestamp(X) is no longer supported
mysql-test/t/type_timestamp.test:
old timestamp(X) is no longer supported
mysys/my_getsystime.c:
functions to get the time with microsecond precision
mysys/my_init.c:
move the my_getsystime.c initialization code to my_getsystime.c
mysys/my_static.c:
no need to make these variables extern
mysys/my_static.h:
no need to make these variables extern
scripts/mysql_system_tables.sql:
old timestamp(X) is no longer supported
scripts/mysql_system_tables_fix.sql:
old timestamp(X) is no longer supported
scripts/mysqlhotcopy.sh:
old timestamp(X) is no longer supported
sql-common/my_time.c:
* call str_to_time from str_to_datetime, as appropriate
* date/time to string conversions take precision as an argument
* number_to_time()
* TIME_to_double()
* pack_time() and unpack_time()
sql/event_data_objects.cc:
cast is not needed
my_datetime_to_str() takes precision as an argument
sql/event_db_repository.cc:
avoid dangerous downcast (because the pointer is
not always Field_timestamp, see events_1.test)
sql/event_queue.cc:
avoid silly double-work for cond_wait
(having an endpoint of wait, subtract the current time to get the timeout,
and use set_timespec() macro to fill in struct timespec, by adding the current
time to the timeout)
sql/field.cc:
* remove virtual Field::get_time(), everyone should use only Field::get_date()
* remove lots of #ifdef WORDS_BIGENDIAN
* unified the warnings from Field_timestamp/datetime/time/date/newdate store methods
* Field_timestamp_hires, Field_datetime_hires, Field_time_hires
* Field_temporal
* make_truncated_value_warning and Field::set_datetime_warning use Lazy_string as an argument, removed char*/int/double variants
sql/field.h:
* remove virtual Field::get_time(), everyone should use only Field::get_date()
* remove lots of #ifdef WORDS_BIGENDIAN
* unified the warnings from Field_timestamp/datetime/time/date/newdate store methods
* Field_timestamp_hires, Field_datetime_hires, Field_time_hires
* Field_temporal
* make_truncated_value_warning and Field::set_datetime_warning use Lazy_string as an argument, removed char*/int/double variants
* removed Field::can_be_compared_as_longlong(). Use Field::cmp_type() == INT_RESULT instead
sql/filesort.cc:
TIME_RESULT, cmp_time()
sql/item.cc:
* numbers aren't quoted in EXPLAIN EXTENDED
* Item::cmp_result() instead of Item::is_datetime() and Item::result_as_longlong()
* virtual Item::get_time() is gone
* Item_param::field_type() is set correctly
* Item_datetime, for a datetime constant
* time to anything is compared as a time
* Item_cache::print() prints the value is available
* bug fixed in Item_cache_int::val_str()
sql/item.h:
* Item::print_value(), to be used from Item_xxx::print() when needed
* Item::cmp_result() instead of Item::is_datetime() and Item::result_as_longlong()
* virtual Item::get_time() is gone
* Item_datetime, for a datetime constant
* better default for cast_to_int_type()
* Item_cache objects now *always* have the field_type() set
sql/item_cmpfunc.cc:
* get_year_value, get_time_value are gone. get_datetime_value does it all
* get_value_a_func, get_value_b_func are gone
* can_compare_as_dates() is gone too, TIME_RESULT is used instead
* cmp_type() instead or result_type() when doing a comparison
* compare_datetime and compate_e_datetime in the comparator_matrix, is_nulls_eq is gone
* Item::cmp_result() instead of Item::is_datetime() and Item::result_as_longlong()
sql/item_cmpfunc.h:
greatly simplified Arg_comparator
sql/item_create.cc:
* fix a bug in error messages in CAST
sql/item_func.cc:
Item::cmp_result() instead of Item::is_datetime() and Item::result_as_longlong()
mention all possibitiles in switch over Item_result values, or use default:
sql/item_row.h:
overwrite the default cmp_type() for Item_row,
as no MYSQL_TYPE_xxx value corresponds to ROW_RESULT
sql/item_timefunc.cc:
rewrite make_datetime to support precision argument
SEC_TO_TIME is real function, not integer.
many functions that returned temporal values had duplicate code in val_* methods,
some of them did not have get_date() which resulted in unnecessary date->str->date conversions.
Now they all are derived from Item_temporal_func and *only* provide get_date, not val* methods.
many fixes to set decimals (datetime precision) correctly.
sql/item_timefunc.h:
SEC_TO_TIME is real function, not integer.
many functions that returned temporal values had duplicate code in val_* methods,
some of them did not have get_date() which resulted in unnecessary date->str->date conversions.
Now they all are derived from Item_temporal_func and *only* provide get_date, not val* methods.
many fixes to set decimals (datetime precision) correctly.
sql/log_event.cc:
replication of NOW(6)
sql/log_event.h:
replication of NOW(6)
sql/mysql_priv.h:
Lazy_string class to pass a value (string, number, time) polymorphically down the stack.
make_truncated_value_warning() that uses it.
sql/mysqld.cc:
datetime in Arg_comparator::comparator_matrix
sql/opt_range.cc:
cleanup: don't disable warnings before calling save_in_field_no_warnings()
sql/protocol.cc:
Protocol::store(time) now takes the precision as an argument
sql/protocol.h:
Protocol::store(time) now takes the precision as an argument
sql/rpl_rli.cc:
small cleanup
sql/set_var.cc:
SET TIMESTAMP=double
sql/set_var.h:
@@TIMESTAMP is a double
sql/share/errmsg.txt:
precision and scale are unsigned
sql/slave.cc:
replication of NOW(6)
sql/sp_head.cc:
cleanup
sql/sql_class.cc:
support for NOW(6)
sql/sql_class.h:
support for NOW(6)
sql/sql_insert.cc:
support for NOW(6)
sql/sql_select.cc:
use item->cmp_type().
move a comment where it belongs
sql/sql_show.cc:
new column I_S.COLUMNS.DATETIME_PRECISION
sql/sql_yacc.yy:
TIME(X), DATETIME(X), cast, NOW(X), CURTIME(X), etc
sql/time.cc:
fix date_add_interval() to support MYSQL_TIMESTAMP_TIME argument
storage/myisam/ha_myisam.cc:
TIMESTAMP no longer carries ZEROFIELD flag, still we keep MYI file compatible.
strings/my_vsnprintf.c:
warnings
tests/mysql_client_test.c:
old timestamp(X) does not work anymore
datetime is no longer equal to time
Changed some String.ptr() -> String.c_ptr() for String that are not guaranteed to end with \0
Removed some c_ptr() usage from parameters to functions that takes ptr & length
Use preallocate buffers to avoid calling malloc() for most operations.
sql/event_db_repository.cc:
alias is now a String
sql/event_scheduler.cc:
c_ptr -> c_ptr_safe() to avoid warnings from valgrind.
sql/events.cc:
c_ptr -> c_ptr_safe() to avoid warnings from valgrind.
c_ptr -> ptr() as function takes ptr & length
sql/field.cc:
alias is now a String
sql/field.h:
alias is now a String
sql/ha_partition.cc:
alias is now a String
sql/handler.cc:
alias is now a String
ptr() -> c_ptr() as string is not guaranteed to be \0 terminated
sql/item.cc:
Store error parameter in separarte buffer to ensure correct error message
sql/item_func.cc:
ptr() -> c_ptr_safe() as string is not guaranteed to be \0 terminated
sql/item_sum.h:
Use my_strtod() instead of my_atof() to not have to make string \0 terminated
sql/lock.cc:
alias is now a String
sql/log.cc:
c_ptr() -> ptr() as function takes ptr & length
sql/log_event.cc:
c_ptr_quick() -> ptr() as we only want to get the pointer to String buffer
sql/opt_range.cc:
ptr() -> c_ptr() as string is not guaranteed to be \0 terminated
sql/opt_table_elimination.cc:
alias is now a String
sql/set_var.cc:
ptr() -> c_ptr() as string is not guaranteed to be \0 terminated
c_ptr() -> c_ptr_safe() to avoid warnings from valgrind.
c_ptr() -> ptr() as function takes ptr & length
Simplify some code.
sql/sp.cc:
c_ptr() -> ptr() as function takes ptr & length
sql/sp_rcontext.cc:
alias is now a String
sql/sql_base.cc:
alias is now a String.
Here we win a realloc() for most alias usage.
sql/sql_class.cc:
Use size descriptor for printf() to avoid accessing bytes outside of buffer
sql/sql_insert.cc:
Change allocation of TABLE as it's now contains a String
_ptr() -> ptr() as function takes ptr & length
sql/sql_load.cc:
Use preallocate buffers to avoid calling malloc() for most operations.
sql/sql_parse.cc:
Use c_ptr_safe() to ensure string is \0 terminated.
sql/sql_plugin.cc:
c_ptr_quick() -> ptr() as function takes ptr & length
sql/sql_select.cc:
alias is now a String
sql/sql_show.cc:
alias is now a String
sql/sql_string.h:
Added move() function to change who owns the string (owner does the free)
sql/sql_table.cc:
alias is now a String
c_ptr() -> c_ptr_safe() to avoid warnings from valgrind.
sql/sql_test.cc:
c_ptr() -> c_ptr_safe() to avoid warnings from valgrind.
alias is now a String
sql/sql_trigger.cc:
c_ptr() -> c_ptr_safe() to avoid warnings from valgrind.
Use field->init() to setup pointers to alias.
sql/sql_update.cc:
alias is now a String
sql/sql_view.cc:
ptr() -> c_ptr_safe() as string is not guaranteed to be \0 terminated
sql/sql_yacc.yy:
r() -> c_ptr() as string is not guaranteed to be \0 terminated
sql/table.cc:
alias is now a String
sql/table.h:
alias is now a String
storage/federatedx/ha_federatedx.cc:
Remove extra 1 byte alloc that is automaticly done by strmake()
Ensure that error message ends with \0
storage/maria/ha_maria.cc:
alias is now a String
storage/myisam/ha_myisam.cc:
alias is now a String
- Fixed some issues with partitions and connection_string, which also fixed lp:716890 "Pre- and post-recovery crash in Aria"
- Fixed wrong assert in Aria
Now need to merge with latest xtradb before pushing
sql/ha_partition.cc:
Ensure that m_ordered_rec_buffer is not freed before close.
sql/mysqld.cc:
Changed to use opt_stack_trace instead of opt_pstack.
Removed references to pstack
sql/partition_element.h:
Ensure that connect_string is initialized
storage/maria/ma_key_recover.c:
Fixed wrong assert
This assumption in Item_cache_datetime::cache_value_int
was wrong:
- /* Assume here that the underlying item will do correct conversion.*/
- int_value= example->val_int_result();
mysql-test/r/subselect_innodb.result:
New test case.
mysql-test/t/subselect_innodb.test:
New test case.
sql/item.cc:
In Item_cache_datetime::cache_value_int()
- call get_time() or get_date() depending on desired type
- convert the returned MYSQL_TIME value to longlong depending on desired type
sql/item.h:
The cached int_value in Item_cache_datetime should not be unsigned:
- it is used mostly in signed context
- it can actually have negative value (for TIME data type)
sql/item_cmpfunc.cc:
Add comment on Bug#59685
sql/item_subselect.cc:
Add some DBUG_TRACE for easier bug-hunting.
The patch fixed the following optimizer defect: when performing
substitution for best equal fields into where conditions to be
able to do their evaluations as soon as possible the optimizer
skipped conditions over views. That could lead to suboptimal
execution of queries that used views.
Slightly changed the test case to demonstrate the performance
improvements if this fix.
sql/item.cc:
Wrapper added.
sql/item.h:
Wrapper added.
sql/mysql_priv.h:
Wrap function added.
sql/sql_base.cc:
Wrap function added.
Fix of problem with WHERE consist of alone outer reference field by wrapping it.
sql/sql_select.cc:
Fix of problem with HAVING consist of alone outer reference field by wrapping it.
Made sure that the optimal fields are used by TABLE_REF objects
when building index access keys to joined tables.
Fixed a bug in the template function that sorts the elements of
a list using the bubble sort algorithm. The bug caused poor
performance of the function. Also added an optimization that
skips comparison with the most heavy elements that has been
already properly placed in the list.
Made the comparison of the fields belonging to the same Item_equal
more granular: fields belonging to the same table are also ordered
according to some rules.
TIMESTAMP.
Item_cache::get_cache wasn't treating TIMESTAMP as a DATETIME value thus
returning string cache for items with TIMESTAMP type. This led to incorrect
TIMESTAMP -> INT conversion and to a wrong query result.
Fixed by using Item::is_datetime function to check for DATETIME type group.
mysql-test/r/type_timestamp.result:
Added a test case for the bug#59330.
mysql-test/t/type_timestamp.test:
Added a test case for the bug#59330.
sql/item.cc:
Bug#59330: Incorrect result when comparing an aggregate function with
TIMESTAMP.
Item_cache::get_cache now uses is_datetime member function to detect DATETIME
type group.
Item_sum_max/Item_sum_min incorrectly set null_value flag and
attempt to get result in parent functions leads to crash.
This happens due to double evaluation of the function argumet.
First evaluation happens in the comparator and second one
happens in Item_cache::cache_value().
The fix is to introduce new Item_cache object which
holds result of the argument and use this cached value
as an argument of the comparator.
mysql-test/r/func_group.result:
test case
mysql-test/t/func_group.test:
test case
sql/item.cc:
added assertion that ether we have some result or result is NULL.
sql/item_sum.cc:
introduce new Item_cache object which
holds result of the argument and use this cached value
as an argument of the comparator.
sql/item_sum.h:
introduce new Item_cache object which
holds result of the argument and use this cached value
as an argument of the comparator.
--Bug#52157 various crashes and assertions with multi-table update, stored function
--Bug#54475 improper error handling causes cascading crashing failures in innodb/ndb
--Bug#57703 create view cause Assertion failed: 0, file .\item_subselect.cc, line 846
--Bug#57352 valgrind warnings when creating view
--Recently discovered problem when a nested materialized derived table is used
before being populated and it leads to incorrect result
We have several modes when we should disable subquery evaluation.
The reasons for disabling are different. It could be
uselessness of the evaluation as in case of 'CREATE VIEW'
or 'PREPARE stmt', or we should disable subquery evaluation
if tables are not locked yet as it happens in bug#54475, or
too early evaluation of subqueries can lead to wrong result
as it happened in Bug#19077.
Main problem is that if subquery items are treated as const
they are evaluated in ::fix_fields(), ::fix_length_and_dec()
of the parental items as a lot of these methods have
Item::val_...() calls inside.
We have to make subqueries non-const to prevent unnecessary
subquery evaluation. At the moment we have different methods
for this. Here is a list of these modes:
1. PREPARE stmt;
We use UNCACHEABLE_PREPARE flag.
It is set during parsing in sql_parse.cc, mysql_new_select() for
each SELECT_LEX object and cleared at the end of PREPARE in
sql_prepare.cc, init_stmt_after_parse(). If this flag is set
subquery becomes non-const and evaluation does not happen.
2. CREATE|ALTER VIEW, SHOW CREATE VIEW, I_S tables which
process FRM files
We use LEX::view_prepare_mode field. We set it before
view preparation and check this flag in
::fix_fields(), ::fix_length_and_dec().
Some bugs are fixed using this approach,
some are not(Bug#57352, Bug#57703). The problem here is
that we have a lot of ::fix_fields(), ::fix_length_and_dec()
where we use Item::val_...() calls for const items.
3. Derived tables with subquery = wrong result(Bug19077)
The reason of this bug is too early subquery evaluation.
It was fixed by adding Item::with_subselect field
The check of this field in appropriate places prevents
const item evaluation if the item have subquery.
The fix for Bug19077 fixes only the problem with
convert_constant_item() function and does not cover
other places(::fix_fields(), ::fix_length_and_dec() again)
where subqueries could be evaluated.
Example:
CREATE TABLE t1 (i INT, j BIGINT);
INSERT INTO t1 VALUES (1, 2), (2, 2), (3, 2);
SELECT * FROM (SELECT MIN(i) FROM t1
WHERE j = SUBSTRING('12', (SELECT * FROM (SELECT MIN(j) FROM t1) t2))) t3;
DROP TABLE t1;
4. Derived tables with subquery where subquery
is evaluated before table locking(Bug#54475, Bug#52157)
Suggested solution is following:
-Introduce new field LEX::context_analysis_only with the following
possible flags:
#define CONTEXT_ANALYSIS_ONLY_PREPARE 1
#define CONTEXT_ANALYSIS_ONLY_VIEW 2
#define CONTEXT_ANALYSIS_ONLY_DERIVED 4
-Set/clean these flags when we perform
context analysis operation
-Item_subselect::const_item() returns
result depending on LEX::context_analysis_only.
If context_analysis_only is set then we return
FALSE that means that subquery is non-const.
As all subquery types are wrapped by Item_subselect
it allow as to make subquery non-const when
it's necessary.
mysql-test/r/derived.result:
test case
mysql-test/r/multi_update.result:
test case
mysql-test/r/view.result:
test case
mysql-test/suite/innodb/r/innodb_multi_update.result:
test case
mysql-test/suite/innodb/t/innodb_multi_update.test:
test case
mysql-test/suite/innodb_plugin/r/innodb_multi_update.result:
test case
mysql-test/suite/innodb_plugin/t/innodb_multi_update.test:
test case
mysql-test/t/derived.test:
test case
mysql-test/t/multi_update.test:
test case
mysql-test/t/view.test:
test case
sql/item.cc:
--removed unnecessary code
sql/item_cmpfunc.cc:
--removed unnecessary checks
--THD::is_context_analysis_only() is replaced with LEX::is_ps_or_view_context_analysis()
sql/item_func.cc:
--refactored context analysis checks
sql/item_row.cc:
--removed unnecessary checks
sql/item_subselect.cc:
--removed unnecessary code
--added DBUG_ASSERT into Item_subselect::exec()
which asserts that subquery execution can not happen
if LEX::context_analysis_only is set, i.e. at context
analysis stage.
--Item_subselect::const_item()
Return FALSE if LEX::context_analysis_only is set.
It prevents subquery evaluation in ::fix_fields &
::fix_length_and_dec at context analysis stage.
sql/item_subselect.h:
--removed unnecessary code
sql/mysql_priv.h:
--Added new set of flags.
sql/sql_class.h:
--removed unnecessary code
sql/sql_derived.cc:
--added LEX::context_analysis_only analysis intialization/cleanup
sql/sql_lex.cc:
--init LEX::context_analysis_only field
sql/sql_lex.h:
--New LEX::context_analysis_only field
sql/sql_parse.cc:
--removed unnecessary code
sql/sql_prepare.cc:
--removed unnecessary code
--added LEX::context_analysis_only analysis intialization/cleanup
sql/sql_select.cc:
--refactored context analysis checks
sql/sql_show.cc:
--added LEX::context_analysis_only analysis intialization/cleanup
sql/sql_view.cc:
--added LEX::context_analysis_only analysis intialization/cleanup
- Fixed problem with oqgraph and 'make dist'
Note that after this merge we have a problem show in join_outer where we examine too many rows in one specific case (related to BUG#57024).
This will be fixed when mwl#128 is merged into 5.3.
- Changed TABLE->alias to String to get fewer reallocs when alias are used.
- Preallocate some buffers
Changed some String->c_ptr() -> String->ptr() when \0 is not needed.
Fixed wrong usage of String->ptr() when we need a \0 terminated string.
Use my_strtod() instead of my_atof() to avoid having to add \0 to string.
c_ptr() -> c_ptr_safe() to avoid warnings from valgrind.
zr
sql/event_db_repository.cc:
Update usage of TABLE->alias
sql/event_scheduler.cc:
c_ptr() -> c_ptr_safe()
sql/events.cc:
c_ptr() -> ptr() as \0 was not needed
sql/field.cc:
Update usage of TABLE->alias
sql/field.h:
Update usage of TABLE->alias
sql/ha_partition.cc:
Update usage of TABLE->alias
sql/handler.cc:
Update usage of TABLE->alias
Fixed wrong usage of str.ptr()
sql/item.cc:
Fixed error where code wrongly assumed string was \0 terminated.
sql/item_func.cc:
c_ptr() -> c_ptr_safe()
Update usage of TABLE->alias
sql/item_sum.h:
Use my_strtod() instead of my_atof() to avoid having to add \0 to string
sql/lock.cc:
Update usage of TABLE->alias
sql/log.cc:
c_ptr() -> ptr() as \0 was not needed
sql/log_event.cc:
c_ptr_quick() -> ptr() as \0 was not needed
sql/opt_range.cc:
ptr() -> c_ptr() as \0 is needed
sql/opt_subselect.cc:
Update usage of TABLE->alias
sql/opt_table_elimination.cc:
Update usage of TABLE->alias
sql/set_var.cc:
ptr() -> c_ptr() as \0 is needed
c_ptr() -> c_ptr_safe()
sql/sp.cc:
c_ptr() -> ptr() as \0 was not needed
sql/sp_rcontext.cc:
Update usage of TABLE->alias
sql/sql_base.cc:
Preallocate buffers
Update usage of TABLE->alias
sql/sql_class.cc:
Fix arguments to sprintf() to work even if string is not \0 terminated
sql/sql_insert.cc:
Update usage of TABLE->alias
c_ptr() -> ptr() as \0 was not needed
sql/sql_load.cc:
Preallocate buffers
Trivial optimizations
sql/sql_parse.cc:
Trivial optimization
sql/sql_plugin.cc:
c_ptr() -> ptr() as \0 was not needed
sql/sql_select.cc:
Update usage of TABLE->alias
sql/sql_show.cc:
Update usage of TABLE->alias
sql/sql_string.h:
Added move() function to move allocated memory from one object to another.
sql/sql_table.cc:
Update usage of TABLE->alias
c_ptr() -> c_ptr_safe()
sql/sql_test.cc:
ptr() -> c_ptr_safe()
sql/sql_trigger.cc:
Update usage of TABLE->alias
c_ptr() -> c_ptr_safe()
sql/sql_update.cc:
Update usage of TABLE->alias
sql/sql_view.cc:
ptr() -> c_ptr_safe()
sql/sql_yacc.yy:
ptr() -> c_ptr()
sql/table.cc:
Update usage of TABLE->alias
sql/table.h:
Changed TABLE->alias to String to get fewer reallocs when alias are used.
storage/federatedx/ha_federatedx.cc:
Use c_ptr_safe() to ensure strings are \0 terminated.
storage/maria/ha_maria.cc:
Update usage of TABLE->alias
storage/myisam/ha_myisam.cc:
Update usage of TABLE->alias
storage/xtradb/row/row0sel.c:
Ensure that null bits in record are properly reset.
(Old code didn't work as row_search_for_mysql() can be called twice while reading fields from one row.
Problem:
nr_of_decimals could read behind the end of the buffer
in case of a non-null-terminated string, which caused
valgring warnings.
Fix:
fixing nr_of_decimals not to read behind the "end" pointer.
modified:
@ mysql-test/r/xml.result
@ mysql-test/t/xml.test
@ sql/item.cc
Problem: crash in Item_float constructor on DBUG_ASSERT due
to not null-terminated string parameter.
Fix: making Item_float::Item_float non-null-termintated parameter safe:
- Using temporary buffer when generating error
modified:
@ mysql-test/r/xml.result
@ mysql-test/t/xml.test
@ sql/item.cc
structure buffer).
This is a follow-up for WL#4435. The bug actually existed not only
MYSQL_TYPE_DATETIME type. The problem was that Item_param::set_value()
was written in an assumption that it's working with expressions, i.e.
with basic data types.
There are two different quick fixes here:
a) Change Item_param::make_field() -- remove setting of
Send_field::length, Send_field::charsetnr, Send_field::flags and
Send_field::type.
That would lead to marshalling all data using basic types to the client
(MYSQL_TYPE_LONGLONG, MYSQL_TYPE_DOUBLE, MYSQL_TYPE_STRING and
MYSQL_TYPE_NEWDECIMAL). In particular, that means, DATETIME would be
sent as MYSQL_TYPE_STRING, TINYINT -- as MYSQL_TYPE_LONGLONG, etc.
That could be Ok for the client, because the client library does
reverse conversion automatically (the client program would see DATETIME
as MYSQL_TIME object). However, there is a problem with metadata --
the metadata would be wrong (misleading): it would say that DATETIME is
marshaled as MYSQL_TYPE_DATETIME, not as MYSQL_TYPE_STRING.
b) Set Item_param::param_type properly to actual underlying field type.
That would lead to double conversion inside the server: for example,
MYSQL_TIME-object would be converted into STRING-object
(in Item_param::set_value()), and then converted back to MYSQL_TIME-object
(in Item_param::send()).
The data however would be marshalled more properly, and also metadata would
be correct.
This patch implements b).
There is also a possibility to avoid double conversion either by clonning
the data field, or by storing a reference to it and using it on Item::send()
time. That requires more work and might be done later.
MySQL officially supports DATE values starting from 1000-01-01. This is
enforced for int values, but not for string values, thus one
could easily insert '0001-01-01' value. Int values are checked by
number_to_datetime function and Item_cache_datetime::val_str uses it
to fill MYSQL_TIME struct out of cached int value. This leads to the
scenario where Item_cache_datetime caches a non-null datetime value and when
it tries to convert it from int to string number_to_datetime function
treats the value as out-of-range and returns an error and
Item_cache_datetime::val_str returns NULL for a non-null value. Due to this
inconsistency server crashes.
Now number_to_datetime allows DATE values below 1000-01-01 if the
TIME_FUZZY_DATE flag is set. Better NULL handling for Item_cache_datetime.
Added the Item_cache_datetime::store function to reset str_value_cached flag
when an item is stored.
mysql-test/r/type_date.result:
Added a test case for the bug#57278.
mysql-test/t/type_date.test:
Added a test case for the bug#57278.
sql-common/my_time.c:
Bug#57278: Crash on min/max + with date out of range.
Now number_to_datetime allows DATE values below 1000-01-01 if the
TIME_FUZZY_DATE flag is set.
sql/item.cc:
Bug#57278: Crash on min/max + with date out of range.
Item_cache_datetime::val_str now better handles
null_value.
Assertion `fixed == 1' failed
(also fixes duplicate bug 57515)
agg_item_set_converter() (item.cc) handles conversion of
character sets by creating a new Item. fix_fields() is then
called on this newly created item. Prior to this patch, it was
not checked whether fix_fields() was successful or not. Thus,
agg_item_set_converter() would return success even when an
error occured. This patch makes it return error (TRUE) if
fix_fields() fails.
mysql-test/r/errors.result:
Add test for BUG#57882
mysql-test/t/errors.test:
Add test for BUG#57882
sql/item.cc:
Make agg_item_set_converter() return with error if fix_fields()
on the newly created converted item fails.
Bug#55744 GROUP_CONCAT + CASE + ucs return garbage
revealed problems in how character set aggregation
code works with prepared statements.
This patch fixes (hopefully) the problems.
The coalesce function returned DATETIME type due to a DATETIME argument, but
since it's not a date/time function it can't return correct int value for
it. Nevertheless Item_datetime_cache was chosen to cache coalesce's result
and that led to a wrong result.
Now Item_datetime_cache is used only for those function that could return
correct int representation of DATETIME values.
mysql-test/r/type_datetime.result:
Added a test case for the bug#57095.
mysql-test/t/type_datetime.test:
Added a test case for the bug#57095.
sql/item.cc:
Bug#57095: Wrongly chosen expression cache type led to a wrong result.
Now Item_datetime_cache is used only for those function that could return
correct int representation of DATETIME values.