mirror of
https://github.com/MariaDB/server.git
synced 2025-07-29 05:21:33 +03:00
MDEV-20516: Assertion `!lex->proc_list.first && !lex->result && !lex->param_list.elements' failed in mysql_create_view
Execution of the CREATE VIEW statement sent via binary protocol
where the flags of the COM_STMT_EXECUTE request a cursor to be opened
before running the statement results in an assert failure.
This assert fails since the data member thd->lex->result has not null
value pointing to an instance of the class Select_materialize.
The data member thd->lex->result is assigned a pointer to the class
Select_materialize in the function mysql_open_cursor() that invoked
in case the packet COM_STMT_EXECUTE requests a cursor to be opened.
After thd->lex->result is assigned a pointer to an instance of the
class Select_materialize the function mysql_create_view() is called
(indirectly via the function mysql_execute_statement()) and the assert
fails.
The assert
DBUG_ASSERT(!lex->proc_list.first && !lex->result &&
!lex->param_list.elements);
was added by the commit 591c06d4b7
.
Unfortunately , the condition
!lex->result
was specified incorrect. It was supposed that the thd->lex->result
is set only by parser on handling the clauses SELECT ... INTO
but indeed it is also set inside mysql_open_cursor() and
that fact was missed by the assert's condition.
So, the fix for this issue is to just remove the condition
!lex->result
from the failing assert.
This commit is contained in:
@ -408,8 +408,18 @@ bool mysql_create_view(THD *thd, TABLE_LIST *views,
|
|||||||
bool res= FALSE;
|
bool res= FALSE;
|
||||||
DBUG_ENTER("mysql_create_view");
|
DBUG_ENTER("mysql_create_view");
|
||||||
|
|
||||||
/* This is ensured in the parser. */
|
/*
|
||||||
DBUG_ASSERT(!lex->proc_list.first && !lex->result &&
|
This is ensured in the parser.
|
||||||
|
NOTE: Originally, the assert below contained the extra condition
|
||||||
|
&& !lex->result
|
||||||
|
but in this form the assert is failed in case CREATE VIEW run under
|
||||||
|
cursor (the case when the byte 'flags' in the COM_STMT_EXECUTE packet has
|
||||||
|
the flag CURSOR_TYPE_READ_ONLY set). For the cursor use case
|
||||||
|
thd->lex->result is assigned a pointer to the class Select_materialize
|
||||||
|
inside the function mysql_open_cursor() just before handling of a statement
|
||||||
|
will be started and the function mysql_create_view() called.
|
||||||
|
*/
|
||||||
|
DBUG_ASSERT(!lex->proc_list.first &&
|
||||||
!lex->param_list.elements);
|
!lex->param_list.elements);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -20013,6 +20013,39 @@ static void test_mdev24827()
|
|||||||
myquery(rc);
|
myquery(rc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void test_mdev_20516()
|
||||||
|
{
|
||||||
|
MYSQL_STMT *stmt;
|
||||||
|
int rc;
|
||||||
|
unsigned long cursor= CURSOR_TYPE_READ_ONLY;
|
||||||
|
|
||||||
|
myheader("test_mdev_20516");
|
||||||
|
|
||||||
|
rc= mysql_query(mysql, "DROP TABLE IF EXISTS t1");
|
||||||
|
myquery(rc);
|
||||||
|
|
||||||
|
rc= mysql_query(mysql, "CREATE TABLE t1(a INT)");
|
||||||
|
myquery(rc);
|
||||||
|
|
||||||
|
const char* query=
|
||||||
|
"CREATE VIEW v1 AS SELECT * FROM t1";
|
||||||
|
|
||||||
|
stmt= mysql_stmt_init(mysql);
|
||||||
|
check_stmt(stmt);
|
||||||
|
|
||||||
|
rc= mysql_stmt_prepare(stmt, query, strlen(query));
|
||||||
|
check_execute(stmt, rc);
|
||||||
|
|
||||||
|
rc= mysql_stmt_attr_set(stmt, STMT_ATTR_CURSOR_TYPE, &cursor);
|
||||||
|
check_execute(stmt, rc);
|
||||||
|
|
||||||
|
rc= mysql_stmt_execute(stmt);
|
||||||
|
check_execute(stmt, rc);
|
||||||
|
|
||||||
|
rc= mysql_query(mysql, "DROP TABLE t1");
|
||||||
|
myquery(rc);
|
||||||
|
}
|
||||||
|
|
||||||
#ifndef EMBEDDED_LIBRARY
|
#ifndef EMBEDDED_LIBRARY
|
||||||
#define MDEV19838_MAX_PARAM_COUNT 32
|
#define MDEV19838_MAX_PARAM_COUNT 32
|
||||||
#define MDEV19838_FIELDS_COUNT 17
|
#define MDEV19838_FIELDS_COUNT 17
|
||||||
@ -20163,6 +20196,7 @@ static void test_mdev19838()
|
|||||||
#endif // EMBEDDED_LIBRARY
|
#endif // EMBEDDED_LIBRARY
|
||||||
|
|
||||||
static struct my_tests_st my_tests[]= {
|
static struct my_tests_st my_tests[]= {
|
||||||
|
{ "test_mdev_20516", test_mdev_20516 },
|
||||||
{ "test_mdev24827", test_mdev24827 },
|
{ "test_mdev24827", test_mdev24827 },
|
||||||
{ "test_mdev_26145", test_mdev_26145 },
|
{ "test_mdev_26145", test_mdev_26145 },
|
||||||
{ "disable_query_logs", disable_query_logs },
|
{ "disable_query_logs", disable_query_logs },
|
||||||
|
Reference in New Issue
Block a user