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

Tests calling the udf spider_copy_tables fail with --view-protocol

Details

    Description

      When run with --view-protocol, these tests

      spider/bg.ha
      spider/bg.ha_part
      spider.ha
      spider/handler.ha
      spider.ha_part
      spider/handler.ha_part
      spider/bugfix.mdev_30649
      spider/bugfix.mdev_30727
      

      fail with

      mysqltest: At line 398: query '$MASTER_1_COPY_TABLES_2_1' failed: 12507: This UDF can't execute if other tables are opened 'thd->derived_tables'=0x52000002c128
       
      The result from queries just before the failure was:
      < snip >
      #  [... 19 lines elided]
      SELECT spider_copy_tables('ta_l', '0', '1');
      

      If we remove the corresponding check:

      modified   storage/spider/spd_copy_tables.cc
      @@ -753,16 +753,20 @@ long long spider_copy_tables_body(
               ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_STR_WITH_NUM, MYF(0),
               "thd->handler_tables_hash.records",
               (longlong) thd->handler_tables_hash.records);
      -    } else if (thd->derived_tables != 0)
      -    {
      -      my_printf_error(ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_NUM,
      -        ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_STR_WITH_PTR, MYF(0),
      -        "thd->derived_tables", thd->derived_tables);
      

      Then we get tripped at the next check of thd->lock.

      If we remove both checks:

      modified   storage/spider/spd_copy_tables.cc
      @@ -737,8 +737,10 @@ long long spider_copy_tables_body(
         if (
           thd->open_tables != 0 ||
           thd->handler_tables_hash.records != 0 ||
      -    thd->derived_tables != 0 ||
      -    thd->lock != 0 ||
           thd->locked_tables_list.locked_tables() ||
           thd->locked_tables_mode != LTM_NONE
         ) {
      @@ -753,16 +755,20 @@ long long spider_copy_tables_body(
               ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_STR_WITH_NUM, MYF(0),
               "thd->handler_tables_hash.records",
               (longlong) thd->handler_tables_hash.records);
      -    } else if (thd->derived_tables != 0)
      -    {
      -      my_printf_error(ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_NUM,
      -        ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_STR_WITH_PTR, MYF(0),
      -        "thd->derived_tables", thd->derived_tables);
      -    } else if (thd->lock != 0)
      -    {
      -      my_printf_error(ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_NUM,
      -        ER_SPIDER_UDF_CANT_USE_IF_OPEN_TABLE_STR_WITH_PTR, MYF(0),
      -        "thd->lock", thd->lock);
      

      then the errors disappear, the tests pass normally but crashes in view protocol

      Attachments

        Issue Links

          Activity

            ycp Yuchen Pei added a comment -

            Upon further analysis, I think the error reporting makes sense and we should disable view protocol for calls to this udf in spider tests.

            More specifically, consider the statement SELECT spider_copy_tables('t', '0', '1').

            Without view protocol, the query is simply SELECT spider_copy_tables('t', '0', '1'), and lock_tables() in the initial open-and-lock is a no-op because there are no tables involved (the server layer has no idea the string 't' refers to a table).

            // lock_tables:
              if (!tables && !thd->lex->requires_prelocking())
                DBUG_RETURN(0);

            With view protocol, the query is SELECT * FROM mysqltest_tmp_v, where mysqltest_tmp_v is a view created using the actual SELECT of the udf. So the initial lock_tables does lock tables:

            // lock_tables:
                if (! (thd->lock= mysql_lock_tables(thd, start, (uint) (ptr - start),
                                                    flags)))
                  DBUG_RETURN(TRUE);

            With or without view protocol, during the execution of the udf, to copy from one table at the data node to another, spider needs to open the spider table t to access its fields so that it can construct queries to select from the source table and insert into the destination table.

            // spider_copy_tables_body:
                if (
                  insert_ct->append_insert_str(SPIDER_DB_INSERT_IGNORE) ||
                  insert_ct->append_into_str() ||
                  insert_ct->append_table_name(0) ||
                  insert_ct->append_open_paren_str() ||
                  insert_ct->append_table_columns(table_share) ||
                  insert_ct->append_values_str()
                ) {
                  my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM);
                  goto error;
                }

            With view protocol, the attempt to lock t trips at an assertion failure:

            // lock_tables:
              if (! thd->locked_tables_mode)
              {
                DBUG_ASSERT(thd->lock == 0);	// You must lock everything at once

            BTW this is not a problem with other spider udfs such as spider_direct_sql, which simply passes the query to the data node without the need to lock any tables at the spider node.

            ycp Yuchen Pei added a comment - Upon further analysis, I think the error reporting makes sense and we should disable view protocol for calls to this udf in spider tests. More specifically, consider the statement SELECT spider_copy_tables('t', '0', '1') . Without view protocol, the query is simply SELECT spider_copy_tables('t', '0', '1') , and lock_tables() in the initial open-and-lock is a no-op because there are no tables involved (the server layer has no idea the string 't' refers to a table). // lock_tables: if (!tables && !thd->lex->requires_prelocking()) DBUG_RETURN(0); With view protocol, the query is SELECT * FROM mysqltest_tmp_v , where mysqltest_tmp_v is a view created using the actual SELECT of the udf. So the initial lock_tables does lock tables: // lock_tables: if (! (thd->lock= mysql_lock_tables(thd, start, (uint) (ptr - start), flags))) DBUG_RETURN(TRUE); With or without view protocol, during the execution of the udf, to copy from one table at the data node to another, spider needs to open the spider table t to access its fields so that it can construct queries to select from the source table and insert into the destination table. // spider_copy_tables_body: if ( insert_ct->append_insert_str(SPIDER_DB_INSERT_IGNORE) || insert_ct->append_into_str() || insert_ct->append_table_name(0) || insert_ct->append_open_paren_str() || insert_ct->append_table_columns(table_share) || insert_ct->append_values_str() ) { my_error(ER_OUT_OF_RESOURCES, MYF(0), HA_ERR_OUT_OF_MEM); goto error; } With view protocol, the attempt to lock t trips at an assertion failure: // lock_tables: if (! thd->locked_tables_mode) { DBUG_ASSERT(thd->lock == 0); // You must lock everything at once BTW this is not a problem with other spider udfs such as spider_direct_sql , which simply passes the query to the data node without the need to lock any tables at the spider node.

            People

              ycp Yuchen Pei
              ycp Yuchen Pei
              Votes:
              0 Vote for this issue
              Watchers:
              1 Start watching this issue

              Dates

                Created:
                Updated:

                Git Integration

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