[MDEV-16803] select on a view crash the server Created: 2018-07-23  Updated: 2018-08-27  Resolved: 2018-08-27

Status: Closed
Project: MariaDB Server
Component/s: Data Manipulation - Subquery
Affects Version/s: 10.2.16
Fix Version/s: 10.2.18

Type: Bug Priority: Major
Reporter: Marc Assignee: Galina Shalygina (Inactive)
Resolution: Fixed Votes: 1
Labels: None
Environment:

Linux version 2.6.32-754.2.1.el6.x86_64 (mockbuild@x86-031.build.eng.bos.redhat.com) (gcc version 4.4.7 20120313 (Red Hat 4.4.7-23) (GCC) ) #1 SMP Tue Jul 3 16:37:52 EDT 2018


Attachments: Text File backtrace_original.txt     Text File backtrace_testcase.txt    

 Description   

A select on a view crash the server 10.2.16. It works on 10.2.14.

The original query and view is more complex than the test case but backtraces are identical as you can see in files attached.

Test case:

CREATE TABLE `bug10_2_16` (
  `value1` int(11) DEFAULT NULL,
  `value2` int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
 
INSERT INTO bug10_2_16 (value1, value2) VALUES (3, 3);
INSERT INTO bug10_2_16 (value1, value2) VALUES (3, 2);
INSERT INTO bug10_2_16 (value1, value2) VALUES (3, 1);
INSERT INTO bug10_2_16 (value1, value2) VALUES (1, 1);
INSERT INTO bug10_2_16 (value1, value2) VALUES (2, 2);
INSERT INTO bug10_2_16 (value1, value2) VALUES (1, 3);
INSERT INTO bug10_2_16 (value1, value2) VALUES (2, 3);
INSERT INTO bug10_2_16 (value1, value2) VALUES (1, 2);
INSERT INTO bug10_2_16 (value1, value2) VALUES (2, 1);
 
create or replace view view_bug10_2_16 (id,val1,val2) 
as 
select 1 as id, value1 as val1, value2 as val2 from bug10_2_16 
union all 
select 2 as id, value1 as val1, value2 as val2 from bug10_2_16 ;
 
select id,val1,val2 from view_bug10_2_16
where ( (val1,val2) in ((1,-1),(2,2)));



 Comments   
Comment by Elena Stepanova [ 2018-07-23 ]

Thanks a lot for the report and test case.
Reproducible as described on 10.2.

10.2 9827c5e1031ca5ebe

#3  <signal handler called>
#4  0x0000558a593a46d8 in Item_func_in::cleanup (this=0x7f5ca8035928) at /data/src/10.2/sql/item_cmpfunc.h:1664
#5  0x0000558a5924f8d9 in Item::cleanup_processor (this=0x7f5ca8035928, arg=0x0) at /data/src/10.2/sql/item.cc:658
#6  0x0000558a58f01da6 in Item::cleanup_excluding_const_fields_processor (this=0x7f5ca8035928, arg=0x0) at /data/src/10.2/sql/item.h:1589
#7  0x0000558a58f641ed in Item_func_or_sum::walk (this=0x7f5ca8035928, processor=&virtual table offset 784, walk_subquery=false, arg=0x0) at /data/src/10.2/sql/item.h:4202
#8  0x0000558a58f97b2d in pushdown_cond_for_derived (thd=0x7f5ca8000b00, cond=0x7f5ca80136b8, derived=0x7f5ca8012900) at /data/src/10.2/sql/sql_derived.cc:1301
#9  0x0000558a59007ff0 in JOIN::optimize_inner (this=0x7f5ca80175d8) at /data/src/10.2/sql/sql_select.cc:1383
#10 0x0000558a5900715b in JOIN::optimize (this=0x7f5ca80175d8) at /data/src/10.2/sql/sql_select.cc:1115
#11 0x0000558a590103ea in mysql_select (thd=0x7f5ca8000b00, tables=0x7f5ca8012900, wild_num=0, fields=..., conds=0x7f5ca80136b8, og_num=0, order=0x0, group=0x0, having=0x0, proc_param=0x0, select_options=2147748608, result=0x7f5ca80175b8, unit=0x7f5ca80046d8, select_lex=0x7f5ca8004e10) at /data/src/10.2/sql/sql_select.cc:3776
#12 0x0000558a5900490f in handle_select (thd=0x7f5ca8000b00, lex=0x7f5ca8004610, result=0x7f5ca80175b8, setup_tables_done_option=0) at /data/src/10.2/sql/sql_select.cc:376
#13 0x0000558a58fd0101 in execute_sqlcom_select (thd=0x7f5ca8000b00, all_tables=0x7f5ca8012900) at /data/src/10.2/sql/sql_parse.cc:6474
#14 0x0000558a58fc6140 in mysql_execute_command (thd=0x7f5ca8000b00) at /data/src/10.2/sql/sql_parse.cc:3481
#15 0x0000558a58fd3ec1 in mysql_parse (thd=0x7f5ca8000b00, rawbuf=0x7f5ca8012478 "select id,val1,val2 from view_bug10_2_16\nwhere ( (val1,val2) in ((1,-1),(2,2)))", length=79, parser_state=0x7f5d0406a200, is_com_multi=false, is_next_command=false) at /data/src/10.2/sql/sql_parse.cc:7995
#16 0x0000558a58fc19e6 in dispatch_command (command=COM_QUERY, thd=0x7f5ca8000b00, packet=0x7f5ca8075a41 "select id,val1,val2 from view_bug10_2_16\nwhere ( (val1,val2) in ((1,-1),(2,2)))", packet_length=79, is_com_multi=false, is_next_command=false) at /data/src/10.2/sql/sql_parse.cc:1821
#17 0x0000558a58fc0349 in do_command (thd=0x7f5ca8000b00) at /data/src/10.2/sql/sql_parse.cc:1375
#18 0x0000558a5911160a in do_handle_one_connection (connect=0x558a5c393c20) at /data/src/10.2/sql/sql_connect.cc:1335
#19 0x0000558a59111397 in handle_one_connection (arg=0x558a5c393c20) at /data/src/10.2/sql/sql_connect.cc:1241
#20 0x0000558a59533690 in pfs_spawn_thread (arg=0x558a5c36e720) at /data/src/10.2/storage/perfschema/pfs.cc:1862
#21 0x00007f5d0beb0494 in start_thread (arg=0x7f5d0406b700) at pthread_create.c:333
#22 0x00007f5d0a29693f in clone () from /lib/x86_64-linux-gnu/libc.so.6

The problem appeared in 10.2 tree with this commit:

commit 6c0f3dd3414a97266912651fb169f630a36f2659
Author: Galina Shalygina
Date:   Sat May 12 20:32:16 2018 +0200
 
    MDEV-16090: Server crash in in Item_func_in::val_int or assertion `in_item'
                failure upon SELECT with impossible condition
    
    The problem appears because of a wrong implementation of the
    Item_func_in::build_clone() method. It didn't clone 'array' and 'cmp_fields'
    fields for the cloned IN predicate and this could cause crashes.
    The Item_func_in::fix_length_and_dec() method was refactored and a new method
    named Item_func_in::create_array() was created. It allowed to create 'array'
    for cloned IN predicates in a proper way.

Comment by Galina Shalygina (Inactive) [ 2018-08-01 ]

The bug appears in the cleanup process in the pushdown into the materialized view/derived table. The query above uses view that is defined with two SELECT statements.
"((val1,val2) in ((1,-1),(2,2)))" can be pushed into the view. It can be pushed into both SELECT statements. It is successfully pushed into the first SELECT and the server crashes while processing the second SELECT pushdown.

For each SELECT that defines derived table for the condition that can be pushed a clone is created. When first SELECT is processed the cleanup() method calls 'delete array' for the Item_func_in element. It empties 'comparators' array in the 'array' structure. The condition that can be pushed into the second SELECT has the same 'array' link. When cleanup() is called for this condition it tries to reach already lame 'array' and that causes a crash. So after the first cleanup() call this link becomes lame.

The bug occurs because of the wrong build_clone() method work for the Item_func_in items. To build the 'array' field for the clone Item_func_in::create_array() method is called there. It can be seen that for the case when the result type of the Item_func_in item is ROW_RESULT no 'array' is initialized in the create_array() method. It is implied that 'array' was created before the call of the create_array() method.

It can be seen that the only method where create_array() call occurs is Item_func_in::fix_length_and_dec(). In this method 'array' is created for the case when the result type is ROW_RESULT before the create_array() call. Also there 'cmp_items' array is filled with appropriate values. In Item_func_in::build_clone() method this array is filled with 0. Therefore it was also a mistake and in some cases that can cause a bug.

To make build_clone() method work right create_array() call should be changed on fix_length_and_dec() call.

Comment by Igor Babaev [ 2018-08-03 ]

Ok to push

Comment by Galina Shalygina (Inactive) [ 2018-08-27 ]

Pushed in 10.2

Generated at Thu Feb 08 08:31:40 UTC 2024 using Jira 8.20.16#820016-sha1:9d11dbea5f4be3d4cc21f03a88dd11d8c8687422.