Details
-
Bug
-
Status: Closed (View Workflow)
-
Major
-
Resolution: Fixed
-
5.6.1, 6.1.1
-
None
Description
I create an MTR test file I_S.test with this content:
--source ../include/have_columnstore.inc
|
--disable_warnings
|
DROP TABLE IF EXISTS t1;
|
--enable_warnings
|
CREATE TABLE t1 (x DECIMAL(38)) ENGINE=ColumnStore;
|
SELECT * FROM INFORMATION_SCHEMA.COLUMNSTORE_TABLES WHERE TABLE_NAME='t1';
|
DROP TABLE t1;
|
Now I run mtr either:
./mtr columnstore/basic.I_S
|
or
./mtr --extern=user=root \
|
--extern=password='C0lumnStore!' \
|
--extern=socket=/var/lib/mysql/mysql.sock \
|
columnstore/basic.I_S
|
It produces the following outout:
TEST RESULT TIME (ms) or COMMENT
|
--------------------------------------------------------------------------
|
|
worker[1] Using MTR_BUILD_THREAD 300, with reserved ports 16000..16019
|
DROP TABLE IF EXISTS t1;
|
CREATE TABLE t1 (x DECIMAL(38)) ENGINE=ColumnStore;
|
SELECT * FROM INFORMATION_SCHEMA.COLUMNSTORE_TABLES WHERE TABLE_NAME='t1';
|
TABLE_SCHEMA TABLE_NAME OBJECT_ID CREATION_DATE COLUMN_COUNT AUTOINCREMENT
|
DROP TABLE t1;
|
columnstore/basic.I_S [ pass ] 1255
|
--------------------------------------------------------------------------
|
Notice, the SELECT query returned no rows.
Now I send the same script to "mariadb" client:
$ mariadb --verbose --socket=/var/lib/mysql/mysql.sock test <I_S.test
|
--------------
|
DROP TABLE IF EXISTS t1
|
--------------
|
|
--------------
|
CREATE TABLE t1 (x DECIMAL(38)) ENGINE=ColumnStore
|
--------------
|
|
--------------
|
SELECT * FROM INFORMATION_SCHEMA.COLUMNSTORE_TABLES WHERE TABLE_NAME='t1'
|
--------------
|
|
TABLE_SCHEMA TABLE_NAME OBJECT_ID CREATION_DATE COLUMN_COUNT AUTOINCREMENT
|
test t1 14505 2021-06-10 00:00:00 1 NULL
|
--------------
|
DROP TABLE t1
|
--------------
|
Notice, the SELECT query returned one record.
The problem happens because of this code in is_columnstore_tables_fill() in is_columnstore_tables.cpp:
if (db_name) |
{
|
if ((*it).second.schema.compare(db_name->ptr()) != 0) |
{
|
continue; |
}
|
}
|
|
if (table_name) |
{
|
if ((*it).second.table.compare(table_name->ptr()) != 0) |
{
|
continue; |
}
|
}
|
That looks wrong. String::ptr() returns a pointer to a buffer which is not necessary 0x00-terminated (String DOES NOT guarantee to provide a 0x00-terminated array). So the result of compare() depends on the random byte value beyond the valid buffer size.