Uploaded image for project: 'MariaDB Server'
  1. MariaDB Server
  2. MDEV-7820

Server crashes in in my_strcasecmp_utf8 on subquery in ORDER BY clause of GROUP_CONCAT

Details

    Description

      CREATE TABLE t1 (f1 VARCHAR(10)) ENGINE=MyISAM;
      INSERT INTO t1 VALUES ('a'),('b');
       
      CREATE TABLE t2 (f2 VARCHAR(10)) ENGINE=MyISAM;
      INSERT INTO t2 VALUES ('c');
       
      CREATE TABLE t3 (f3 VARCHAR(10)) ENGINE=MyISAM;
      INSERT INTO t3 VALUES ('d'),('e');
       
      SELECT GROUP_CONCAT( f2 ORDER BY ( f2 IN ( SELECT f1 FROM t1 WHERE f1 <= f2 ) ) ) AS field 
      FROM ( SELECT * FROM t2 ) AS sq2, t3 
      ORDER BY field;

      Stack trace from 5.5 commit 86f46a3da4a6d82cb510dc4c270d46cfd6a8965b

      #3  <signal handler called>
      #4  0x0000000000d1a83f in my_strcasecmp_utf8 (cs=0x1551240, s=0x7fa0ef9309e0 "f2", t=0x0) at 5.5/strings/ctype-utf8.c:2836
      #5  0x00000000005e0400 in find_item_in_list (find=0x7fa0ef938ea8, items=..., counter=0x7fa0f03b42f4, report_error=REPORT_EXCEPT_NOT_FOUND, resolution=0x7fa0f03b42f0) at 5.5/sql/sql_base.cc:7260
      #6  0x0000000000696089 in find_order_in_list (thd=0x7fa0f0950060, ref_pointer_array=0x7fa0efa88fc8, tables=0x7fa0ef92f078, order=0x7fa0efa88b30, fields=..., all_fields=..., is_group_field=false) at 5.5/sql/sql_select.cc:20475
      #7  0x000000000069646d in setup_order (thd=0x7fa0f0950060, ref_pointer_array=0x7fa0efa88fc8, tables=0x7fa0ef92f078, fields=..., all_fields=..., order=0x7fa0efa88b30) at 5.5/sql/sql_select.cc:20585
      #8  0x0000000000896e6f in Item_func_group_concat::setup (this=0x7fa0efa88b90, thd=0x7fa0f0950060) at 5.5/sql/item_sum.cc:3506
      #9  0x0000000000897bb2 in Aggregator_simple::setup (this=0x7fa0ef938fa8, thd=0x7fa0f0950060) at 5.5/sql/item_sum.h:668
      #10 0x00000000006a1424 in Item_sum::aggregator_setup (this=0x7fa0efa88b90, thd=0x7fa0f0950060) at 5.5/sql/item_sum.h:507
      #11 0x0000000000698d1d in setup_sum_funcs (thd=0x7fa0f0950060, func_ptr=0x7fa0ef931008) at 5.5/sql/sql_select.cc:21636
      #12 0x00000000006683cf in JOIN::init_execution (this=0x7fa0ef92fce0) at 5.5/sql/sql_select.cc:1899
      #13 0x0000000000669ffd in JOIN::exec (this=0x7fa0ef92fce0) at 5.5/sql/sql_select.cc:2402
      #14 0x000000000066c4ed in mysql_select (thd=0x7fa0f0950060, rref_pointer_array=0x7fa0f0953cd0, tables=0x7fa0ef92f078, wild_num=0, fields=..., conds=0x0, og_num=1, order=0x7fa0ef96aff8, group=0x0, having=0x0, proc_param=0x0, select_options=2147748608, result=0x7fa0ef92fcc0, unit=0x7fa0f0953380, select_lex=0x7fa0f0953a60) at 5.5/sql/sql_select.cc:3094
      #15 0x0000000000662fbd in handle_select (thd=0x7fa0f0950060, lex=0x7fa0f09532d0, result=0x7fa0ef92fcc0, setup_tables_done_option=0) at 5.5/sql/sql_select.cc:319
      #16 0x000000000063c1fc in execute_sqlcom_select (thd=0x7fa0f0950060, all_tables=0x7fa0ef92f078) at 5.5/sql/sql_parse.cc:4689
      #17 0x00000000006353de in mysql_execute_command (thd=0x7fa0f0950060) at 5.5/sql/sql_parse.cc:2234
      #18 0x000000000063ece2 in mysql_parse (thd=0x7fa0f0950060, rawbuf=0x7fa0efa87078 "SELECT GROUP_CONCAT( f2 ORDER BY ( f2 IN ( SELECT f1 FROM t1 WHERE f1 <= f2 ) ) ) AS field \nFROM ( SELECT * FROM t2 ) AS sq2, t3 \nORDER BY field", length=144, parser_state=0x7fa0f03b5620) at 5.5/sql/sql_parse.cc:5909
      #19 0x0000000000632925 in dispatch_command (command=COM_QUERY, thd=0x7fa0f0950060, packet=0x7fa0f0a09061 "SELECT GROUP_CONCAT( f2 ORDER BY ( f2 IN ( SELECT f1 FROM t1 WHERE f1 <= f2 ) ) ) AS field \nFROM ( SELECT * FROM t2 ) AS sq2, t3 \nORDER BY field", packet_length=144) at 5.5/sql/sql_parse.cc:1079
      #20 0x0000000000631ab1 in do_command (thd=0x7fa0f0950060) at 5.5/sql/sql_parse.cc:793
      #21 0x0000000000734122 in do_handle_one_connection (thd_arg=0x7fa0f0950060) at 5.5/sql/sql_connect.cc:1266
      #22 0x0000000000733be1 in handle_one_connection (arg=0x7fa0f0950060) at 5.5/sql/sql_connect.cc:1181
      #23 0x0000000000b6c629 in pfs_spawn_thread (arg=0x7fa0f0971fc0) at 5.5/storage/perfschema/pfs.cc:1015
      #24 0x00007fa0f6de1b50 in start_thread (arg=<optimized out>) at pthread_create.c:304
      #25 0x00007fa0f509770d in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:112

      The problem goes far back in time, it was introduced in 5.3.3 (I can't point at the exact revision).

      Attachments

        Activity

          The cause of the crash seems to be the combination of having an Item of type FIELD_ITEM, with a null field name. Being a FIELD_ITEM means that we search for it by name. Subsequently we try and compare all known items' field names with the null field name.

          This code is part of sql_base.cc: Item *find_item_in_list(), which is called during GROUP_CONCAT item setup().

            if (is_ref_by_name)
            {
              field_name= ((Item_ident*) find)->field_name; // This is 0x0
              table_name= ((Item_ident*) find)->table_name; // This is ""
              db_name=    ((Item_ident*) find)->db_name; // This is ""
            }
          // Later, field_name is compared to item field names.

          At first glance it seems that we forget to set the field_name to be empty_string instead of null.

          By doing:

            if (is_ref_by_name)
            {
              field_name= ((Item_ident*) find)->field_name;
              // TMP HACK
              if (!field_name)
                field_name = "";
              table_name= ((Item_ident*) find)->table_name;
              db_name=    ((Item_ident*) find)->db_name;
            }

          The test case passes correctly.

          cvicentiu Vicențiu Ciorbaru added a comment - The cause of the crash seems to be the combination of having an Item of type FIELD_ITEM, with a null field name. Being a FIELD_ITEM means that we search for it by name. Subsequently we try and compare all known items' field names with the null field name. This code is part of sql_base.cc: Item *find_item_in_list(), which is called during GROUP_CONCAT item setup(). if (is_ref_by_name) { field_name= ((Item_ident*) find)->field_name; // This is 0x0 table_name= ((Item_ident*) find)->table_name; // This is "" db_name= ((Item_ident*) find)->db_name; // This is "" } // Later, field_name is compared to item field names. At first glance it seems that we forget to set the field_name to be empty_string instead of null. By doing: if (is_ref_by_name) { field_name= ((Item_ident*) find)->field_name; // TMP HACK if (!field_name) field_name = ""; table_name= ((Item_ident*) find)->table_name; db_name= ((Item_ident*) find)->db_name; } The test case passes correctly.

          Further analysis in how the query gets executed:

          • We first parse the GROUP_CONCAT and create a Item_func_group_concat with the order parameter an Item_in_subselect.
          • Subsequently the data from the subselect is placed inside a temporary table.
          • Afterwards, the Item_in_subselect from the is replaced with an Item_field associated with the column from the temporary table.
          • The Item_field has no name since it belongs to the temporary table.
          • We then proceed to perform a strcmp with existing fields, f2 only in this case. Comparing f2 to NULL causes the crash.
          cvicentiu Vicențiu Ciorbaru added a comment - Further analysis in how the query gets executed: We first parse the GROUP_CONCAT and create a Item_func_group_concat with the order parameter an Item_in_subselect. Subsequently the data from the subselect is placed inside a temporary table. Afterwards, the Item_in_subselect from the is replaced with an Item_field associated with the column from the temporary table. The Item_field has no name since it belongs to the temporary table. We then proceed to perform a strcmp with existing fields, f2 only in this case. Comparing f2 to NULL causes the crash.
          cvicentiu Vicențiu Ciorbaru added a comment - Please review the fix for this patch: https://github.com/MariaDB/server/compare/5.5...5.5-MDEV-7820

          OK to push.

          sanja Oleksandr Byelkin added a comment - OK to push.
          cvicentiu Vicențiu Ciorbaru added a comment - Fixed with: https://github.com/MariaDB/server/commit/eb47b226d268e7820a9153672798cf991a8fd0fa

          People

            cvicentiu Vicențiu Ciorbaru
            elenst Elena Stepanova
            Votes:
            0 Vote for this issue
            Watchers:
            3 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved:

              Git Integration

                Error rendering 'com.xiplink.jira.git.jira_git_plugin:git-issue-webpanel'. Please contact your Jira administrators.