Description:
If trying to opening a native partitioned innodb table by .frm when the table it self does not exists, it will assert.
How to repeat:
--echo # Test .frm out-of-sync
CREATE TABLE t1 (a int) ENGINE=InnoDB PARTITION BY HASH (a) PARTITIONS 2;
--copy_file $MYSQLD_DATADIR/test/t1.frm $MYSQLD_DATADIR/test/t2.frm
--error ER_GET_ERRNO
SELECT * FROM t2;
--remove_file $MYSQLD_DATADIR/test/t2.frm
DROP TABLE t1;
Suggested fix:
Tested and fixed on mysql-trunk based branch, but should be the same for mysql-5.7.
diff --git a/mysql-test/suite/innodb/r/partition.result b/mysql-test/suite/innodb/r/partition.result
index 7591097..a76e6fd 100644
--- a/mysql-test/suite/innodb/r/partition.result
+++ b/mysql-test/suite/innodb/r/partition.result
@@ -240,3 +240,8 @@ ALTER TABLE t1 TABLESPACE ts1;
ALTER TABLE t1 DROP PRIMARY KEY, ALGORITHM=DEFAULT;
DROP TABLE t1;
DROP TABLESPACE ts1;
+# Test .frm out-of-sync
+CREATE TABLE t1 (a int) ENGINE=InnoDB PARTITION BY HASH (a) PARTITIONS 2;
+SELECT * FROM t2;
+ERROR HY000: Got error 122 from storage engine
+DROP TABLE t1;
diff --git a/mysql-test/suite/innodb/t/partition.test b/mysql-test/suite/innodb/t/partition.test
index 694de8e..f319870 100644
--- a/mysql-test/suite/innodb/t/partition.test
+++ b/mysql-test/suite/innodb/t/partition.test
@@ -188,3 +188,13 @@ ALTER TABLE t1 TABLESPACE ts1;
ALTER TABLE t1 DROP PRIMARY KEY, ALGORITHM=DEFAULT;
DROP TABLE t1;
DROP TABLESPACE ts1;
+
+--echo # Test .frm out-of-sync
+CREATE TABLE t1 (a int) ENGINE=InnoDB PARTITION BY HASH (a) PARTITIONS 2;
+--copy_file $MYSQLD_DATADIR/test/t1.frm $MYSQLD_DATADIR/test/t2.frm
+--error ER_GET_ERRNO
+SELECT * FROM t2;
+--remove_file $MYSQLD_DATADIR/test/t2.frm
+DROP TABLE t1;
+
+
diff --git a/storage/innobase/handler/ha_innopart.cc b/storage/innobase/handler/ha_innopart.cc
index d96b24b..b96ff4a 100644
--- a/storage/innobase/handler/ha_innopart.cc
+++ b/storage/innobase/handler/ha_innopart.cc
@@ -220,13 +220,14 @@ Ha_innopart_share::open_table_parts(
}
ut_ad(m_ref_count == 1);
m_tot_parts = part_info->get_tot_partitions();
+ size_t table_parts_size = sizeof(dict_table_t*) * m_tot_parts;
m_table_parts = static_cast<dict_table_t**>
- (ut_malloc(sizeof(dict_table_t*) * m_tot_parts,
- mem_key_partitioning));
+ (ut_malloc(table_parts_size, mem_key_partitioning));
if (m_table_parts == NULL) {
m_ref_count--;
return(true);
}
+ memset(m_table_parts, 0, table_parts_size);
/* Set up the array over all table partitions. */
table_name_len = strlen(table_name);