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

Assertion `table->pos_in_locked_tables == __null || table->pos_in_locked_tables->table == table' failed in mark_used_tables_as_free_for_reuse

Details

    Description

      --source include/have_innodb.inc
       
      CREATE TABLE t1 (a INT);
      CREATE TABLE t2 (b INT);
       
      CREATE TABLE t3 (c INT);
      CREATE TABLE t4 (d INT);
      CREATE TABLE t5 (e INT);
       
      CREATE TRIGGER tr1 BEFORE INSERT ON t2 FOR EACH ROW INSERT INTO t4 VALUES ();
      CREATE TRIGGER tr2 BEFORE INSERT ON t3 FOR EACH ROW INSERT INTO t1 VALUES ();
      CREATE TRIGGER tr3 BEFORE INSERT ON t4 FOR EACH ROW INSERT INTO t3 SELECT * FROM t1;
      CREATE TRIGGER tr4 BEFORE INSERT ON t5 FOR EACH ROW INSERT INTO t4 VALUES ();
       
      --connect (con1,localhost,root,,test)
      LOCK TABLE t1 WRITE, t4 WRITE;
       
      --connection default
      --send
      	INSERT INTO t2 VALUES (1);
       
      --connection con1
      CREATE OR REPLACE TABLE t1 (i INT);
      UNLOCK TABLES;
       
      --connection default
      --reap
       
      # Cleanup
      --disconnect con1
      --connection default
      DROP TABLE t1, t2, t3, t4, t5;
      

      10.0 d8ccc61f76d5

      Version: '10.0.34-MariaDB-debug'  socket: '/data/bld/10.0/mysql-test/var/tmp/mysqld.1.sock'  port: 16000  Source distribution
      mysqld: /data/src/10.0/sql/sql_base.cc:746: void mark_used_tables_as_free_for_reuse(THD*, TABLE*): Assertion `table->pos_in_locked_tables == __null || table->pos_in_locked_tables->table == table' failed.
      171123 13:47:23 [ERROR] mysqld got signal 6 ;
       
      #7  0x00007f2facbadee2 in __assert_fail () from /lib/x86_64-linux-gnu/libc.so.6
      #8  0x00000000005e88d0 in mark_used_tables_as_free_for_reuse (thd=0x7f2fa0f69070, table=0x7f2f98c88870) at /data/src/10.0/sql/sql_base.cc:745
      #11 0x000000000097c6dc in sp_instr_stmt::exec_core (this=0x7f2f98cd0d88, thd=0x7f2fa0f69070, nextp=0x7f2faec712d8) at /data/src/10.0/sql/sp_head.cc:3210
      #12 0x000000000097bdeb in sp_lex_keeper::reset_lex_and_exec_core (this=0x7f2f98cd0dc8, thd=0x7f2fa0f69070, nextp=0x7f2faec712d8, open_tables=false, instr=0x7f2f98cd0d88) at /data/src/10.0/sql/sp_head.cc:2977
      #13 0x000000000097c3a6 in sp_instr_stmt::execute (this=0x7f2f98cd0d88, thd=0x7f2fa0f69070, nextp=0x7f2faec712d8) at /data/src/10.0/sql/sp_head.cc:3126
      #14 0x0000000000978177 in sp_head::execute (this=0x7f2f98ccd088, thd=0x7f2fa0f69070, merge_da_on_success=false) at /data/src/10.0/sql/sp_head.cc:1369
      #15 0x0000000000978c31 in sp_head::execute_trigger (this=0x7f2f98ccd088, thd=0x7f2fa0f69070, db_name=0x7f2f98c351d8, table_name=0x7f2f98c351e8, grant_info=0x7f2f98cb9138) at /data/src/10.0/sql/sp_head.cc:1697
      #16 0x000000000070eb58 in Table_triggers_list::process_triggers (this=0x7f2f98cb9088, thd=0x7f2fa0f69070, event=TRG_EVENT_INSERT, time_type=TRG_ACTION_BEFORE, old_row_is_record1=true) at /data/src/10.0/sql/sql_trigger.cc:2103
      #17 0x00000000005f84c2 in fill_record_n_invoke_before_triggers (thd=0x7f2fa0f69070, table=0x7f2f98c88870, fields=..., values=..., ignore_errors=false, event=TRG_EVENT_INSERT) at /data/src/10.0/sql/sql_base.cc:8766
      #18 0x000000000062e6c8 in mysql_insert (thd=0x7f2fa0f69070, table_list=0x7f2f98a03088, fields=..., values_list=..., update_fields=..., update_values=..., duplic=DUP_ERROR, ignore=false) at /data/src/10.0/sql/sql_insert.cc:880
      #19 0x000000000064e89f in mysql_execute_command (thd=0x7f2fa0f69070) at /data/src/10.0/sql/sql_parse.cc:3449
      #20 0x000000000097c6dc in sp_instr_stmt::exec_core (this=0x7f2f98a03668, thd=0x7f2fa0f69070, nextp=0x7f2faec72628) at /data/src/10.0/sql/sp_head.cc:3210
      #21 0x000000000097bdeb in sp_lex_keeper::reset_lex_and_exec_core (this=0x7f2f98a036a8, thd=0x7f2fa0f69070, nextp=0x7f2faec72628, open_tables=false, instr=0x7f2f98a03668) at /data/src/10.0/sql/sp_head.cc:2977
      #22 0x000000000097c3a6 in sp_instr_stmt::execute (this=0x7f2f98a03668, thd=0x7f2fa0f69070, nextp=0x7f2faec72628) at /data/src/10.0/sql/sp_head.cc:3126
      #23 0x0000000000978177 in sp_head::execute (this=0x7f2f98a00088, thd=0x7f2fa0f69070, merge_da_on_success=false) at /data/src/10.0/sql/sp_head.cc:1369
      #24 0x0000000000978c31 in sp_head::execute_trigger (this=0x7f2f98a00088, thd=0x7f2fa0f69070, db_name=0x7f2f98860fd8, table_name=0x7f2f98860fe8, grant_info=0x7f2f98952338) at /data/src/10.0/sql/sp_head.cc:1697
      #25 0x000000000070eb58 in Table_triggers_list::process_triggers (this=0x7f2f98952288, thd=0x7f2fa0f69070, event=TRG_EVENT_INSERT, time_type=TRG_ACTION_BEFORE, old_row_is_record1=true) at /data/src/10.0/sql/sql_trigger.cc:2103
      #26 0x00000000005f8a21 in fill_record_n_invoke_before_triggers (thd=0x7f2fa0f69070, table=0x7f2f9889e470, ptr=0x7f2f98828998, values=..., ignore_errors=false, event=TRG_EVENT_INSERT) at /data/src/10.0/sql/sql_base.cc:8910
      #27 0x000000000062e818 in mysql_insert (thd=0x7f2fa0f69070, table_list=0x7f2f989a4168, fields=..., values_list=..., update_fields=..., update_values=..., duplic=DUP_ERROR, ignore=false) at /data/src/10.0/sql/sql_insert.cc:924
      #28 0x000000000064e89f in mysql_execute_command (thd=0x7f2fa0f69070) at /data/src/10.0/sql/sql_parse.cc:3449
      #29 0x0000000000656dc2 in mysql_parse (thd=0x7f2fa0f69070, rawbuf=0x7f2f989a4088 "INSERT INTO t2 VALUES (1)", length=25, parser_state=0x7f2faec73640) at /data/src/10.0/sql/sql_parse.cc:6569
      #30 0x0000000000649901 in dispatch_command (command=COM_QUERY, thd=0x7f2fa0f69070, packet=0x7f2fa69ef071 "INSERT INTO t2 VALUES (1)", packet_length=25) at /data/src/10.0/sql/sql_parse.cc:1296
      #31 0x0000000000648c01 in do_command (thd=0x7f2fa0f69070) at /data/src/10.0/sql/sql_parse.cc:999
      #32 0x0000000000768ab8 in do_handle_one_connection (thd_arg=0x7f2fa0f69070) at /data/src/10.0/sql/sql_connect.cc:1377
      #33 0x000000000076882a in handle_one_connection (arg=0x7f2fa0f69070) at /data/src/10.0/sql/sql_connect.cc:1292
      #34 0x0000000000ac9564 in pfs_spawn_thread (arg=0x7f2fa0f19670) at /data/src/10.0/storage/perfschema/pfs.cc:1861
      #35 0x00007f2fae8b1494 in start_thread (arg=0x7f2faec74700) at pthread_create.c:333
      #36 0x00007f2facc6a93f in clone () from /lib/x86_64-linux-gnu/libc.so.6
      

      Reproducible on 10.0 - 10.3 with MyISAM, InnoDB, Aria. Not applicable to 5.5 or MySQL because of CREATE OR REPLACE.

      Attachments

        Issue Links

          Activity

            Still reproducible on current bulds (at least 10.0 ada54101a71, 10.3 141a5b2484).

            elenst Elena Stepanova added a comment - Still reproducible on current bulds (at least 10.0 ada54101a71, 10.3 141a5b2484).

            Simplified test case:

            CREATE TABLE t1 (a INT);
            CREATE TABLE t2 (b INT);
            CREATE TABLE t3 (c INT);
             
            CREATE TRIGGER tr1 BEFORE INSERT ON t3 FOR EACH ROW INSERT INTO t1 VALUES ();
            CREATE TRIGGER tr2 BEFORE INSERT ON t2 FOR EACH ROW INSERT INTO t3 SELECT * FROM t1;
             
            LOCK TABLE t1 WRITE, t2 WRITE;
            CREATE OR REPLACE TABLE t1 (i INT);
            UNLOCK TABLES;
            INSERT INTO t2 VALUES (1);
             
            # Cleanup
            DROP TABLE t1, t2, t3;
            

            svoj Sergey Vojtovich added a comment - Simplified test case: CREATE TABLE t1 (a INT); CREATE TABLE t2 (b INT); CREATE TABLE t3 (c INT);   CREATE TRIGGER tr1 BEFORE INSERT ON t3 FOR EACH ROW INSERT INTO t1 VALUES (); CREATE TRIGGER tr2 BEFORE INSERT ON t2 FOR EACH ROW INSERT INTO t3 SELECT * FROM t1;   LOCK TABLE t1 WRITE, t2 WRITE; CREATE OR REPLACE TABLE t1 (i INT); UNLOCK TABLES; INSERT INTO t2 VALUES (1);   # Cleanup DROP TABLE t1, t2, t3;

            Apparently it was broken in 2012 by b1485a4780808cd95cbc37c1f59024b39d542584, specifically this hunk:

            @@ -1412,10 +1415,13 @@ close_all_tables_for_name(THD *thd, TABLE_SHARE *share,
                 {
                   thd->locked_tables_list.unlink_from_list(thd,
                                                            table->pos_in_locked_tables,
            -                                               extra != HA_EXTRA_NORMAL);
            -      /* Inform handler that there is a drop table or rename going on */
            -      if (extra != HA_EXTRA_NORMAL && table->db_stat)
            +                                               extra != HA_EXTRA_NOT_USED);
            +      /* Inform handler that there is a drop table or a rename going on */
            +      if (extra != HA_EXTRA_NOT_USED && table->db_stat)
            +      {
                     table->file->extra(extra);
            +        extra= HA_EXTRA_NOT_USED;               // Call extra once!
            +      }
             
                   /*
                     Does nothing if the table is not locked.
            

            In other words it would remove only first instance of a table from m_locked_tables list (previously removed all) due to "extra= HA_EXTRA_NOT_USED" reset. This eventually breaks m_locked_tables list when still-in-the-list instance is added back to the list again using thd->locked_tables_list.add_back_last_deleted_lock(pos_in_locked_tables);

            svoj Sergey Vojtovich added a comment - Apparently it was broken in 2012 by b1485a4780808cd95cbc37c1f59024b39d542584, specifically this hunk: @@ -1412,10 +1415,13 @@ close_all_tables_for_name(THD *thd, TABLE_SHARE *share, { thd->locked_tables_list.unlink_from_list(thd, table->pos_in_locked_tables, - extra != HA_EXTRA_NORMAL); - /* Inform handler that there is a drop table or rename going on */ - if (extra != HA_EXTRA_NORMAL && table->db_stat) + extra != HA_EXTRA_NOT_USED); + /* Inform handler that there is a drop table or a rename going on */ + if (extra != HA_EXTRA_NOT_USED && table->db_stat) + { table->file->extra(extra); + extra= HA_EXTRA_NOT_USED; // Call extra once! + }   /* Does nothing if the table is not locked. In other words it would remove only first instance of a table from m_locked_tables list (previously removed all) due to "extra= HA_EXTRA_NOT_USED" reset. This eventually breaks m_locked_tables list when still-in-the-list instance is added back to the list again using thd->locked_tables_list.add_back_last_deleted_lock(pos_in_locked_tables);
            svoj Sergey Vojtovich added a comment - - edited serg , please review fix for this bug. https://github.com/mariadb/server/commit/01bd1917e458f7c1bd52584b3ff15c968ed9034d

            ok to push!

            serg Sergei Golubchik added a comment - ok to push!

            People

              serg Sergei Golubchik
              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.