forked from facebook/mysql-5.6
-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add locking when reading index cardinality in InnoDB
Summary: When updating index cardinality in InnoDB, the stats are first zero'd out via `dict_stats_empty_index` and then populated. Although there is locking on the write path, when updating index stats, it looks like we usually do not have locking on the read path in innodb. This can lead to bad plans, as we would return bad index stats. The fix is to take a shared lock on the read paths. https://bugs.mysql.com/bug.php?id=103210 Reviewed By: luqun, yizhang82 Differential Revision: D27545419
- Loading branch information
Showing
6 changed files
with
182 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
set global innodb_stats_locked_reads = on; | ||
CREATE TABLE t (a int, | ||
b int, | ||
c int, | ||
d int, | ||
e int, | ||
PRIMARY KEY(a), | ||
KEY innodb_index_lock_test (b, c, d)) ENGINE=InnoDB; | ||
insert into t values (1, 1, 1, 1, 1), (2, 2, 2, 2, 2), (3, 3, 3, 3, 3), (4, 4, 4, 4, 4); | ||
insert into t select a+4, b+4, c, d, e from t; | ||
insert into t select a+8, b+8, c, d, e from t; | ||
insert into t select a+16, b+16, c, d, e from t; | ||
insert into t select a+32, b+32, c, d, e from t; | ||
insert into t select a+64, b+64, c, d, e from t; | ||
insert into t select a+128, b+128, c, d, e from t; | ||
insert into t select a+256, b+256, c, d, e from t; | ||
insert into t select a+512, b+512, c, d, e from t; | ||
insert into t select a+1024, b+1024, c, d, e from t; | ||
analyze table t; | ||
Table Op Msg_type Msg_text | ||
test.t analyze status OK | ||
flush tables; | ||
show indexes in t; | ||
Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment Index_comment Visible Expression | ||
t 0 PRIMARY 1 a A 2048 NULL NULL BTREE YES NULL | ||
t 1 innodb_index_lock_test 1 b A 2048 NULL NULL YES BTREE YES NULL | ||
t 1 innodb_index_lock_test 2 c A 2048 NULL NULL YES BTREE YES NULL | ||
t 1 innodb_index_lock_test 3 d A 2048 NULL NULL YES BTREE YES NULL | ||
set information_schema_stats_expiry = 0; | ||
set innodb_stats_on_metadata = on; | ||
set debug_sync = "after_empty_index SIGNAL parked WAIT_FOR go"; | ||
select * from information_schema.tables where table_name = 't'; | ||
set information_schema_stats_expiry = 0; | ||
set debug_sync='now WAIT_FOR parked'; | ||
show indexes in t; | ||
set debug_sync='now SIGNAL go'; | ||
Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment Index_comment Visible Expression | ||
t 0 PRIMARY 1 a A 2048 NULL NULL BTREE YES NULL | ||
t 1 innodb_index_lock_test 1 b A 2048 NULL NULL YES BTREE YES NULL | ||
t 1 innodb_index_lock_test 2 c A 2048 NULL NULL YES BTREE YES NULL | ||
t 1 innodb_index_lock_test 3 d A 2048 NULL NULL YES BTREE YES NULL | ||
drop table t; | ||
set debug_sync = 'RESET'; | ||
set global innodb_stats_locked_reads = default; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
--source include/have_debug_sync.inc | ||
--source include/count_sessions.inc | ||
|
||
set global innodb_stats_locked_reads = on; | ||
|
||
CREATE TABLE t (a int, | ||
b int, | ||
c int, | ||
d int, | ||
e int, | ||
PRIMARY KEY(a), | ||
KEY innodb_index_lock_test (b, c, d)) ENGINE=InnoDB; | ||
|
||
insert into t values (1, 1, 1, 1, 1), (2, 2, 2, 2, 2), (3, 3, 3, 3, 3), (4, 4, 4, 4, 4); | ||
insert into t select a+4, b+4, c, d, e from t; | ||
insert into t select a+8, b+8, c, d, e from t; | ||
insert into t select a+16, b+16, c, d, e from t; | ||
insert into t select a+32, b+32, c, d, e from t; | ||
insert into t select a+64, b+64, c, d, e from t; | ||
insert into t select a+128, b+128, c, d, e from t; | ||
insert into t select a+256, b+256, c, d, e from t; | ||
insert into t select a+512, b+512, c, d, e from t; | ||
insert into t select a+1024, b+1024, c, d, e from t; | ||
|
||
analyze table t; | ||
flush tables; | ||
|
||
show indexes in t; | ||
|
||
set information_schema_stats_expiry = 0; | ||
|
||
set innodb_stats_on_metadata = on; | ||
set debug_sync = "after_empty_index SIGNAL parked WAIT_FOR go"; | ||
send select * from information_schema.tables where table_name = 't'; | ||
|
||
connect (con1,localhost,root,,); | ||
set information_schema_stats_expiry = 0; | ||
set debug_sync='now WAIT_FOR parked'; | ||
send show indexes in t; | ||
|
||
connect (con2,localhost,root,,); | ||
set debug_sync='now SIGNAL go'; | ||
disconnect con2; | ||
|
||
connection con1; | ||
reap; | ||
|
||
disconnect con1; | ||
|
||
connection default; | ||
--disable_result_log | ||
reap; | ||
--enable_result_log | ||
|
||
drop table t; | ||
set debug_sync = 'RESET'; | ||
|
||
set global innodb_stats_locked_reads = default; | ||
|
||
--source include/wait_until_count_sessions.inc |
24 changes: 24 additions & 0 deletions
24
mysql-test/suite/sys_vars/r/innodb_stats_locked_reads_basic.result
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
SELECT @@innodb_stats_locked_reads; | ||
@@innodb_stats_locked_reads | ||
0 | ||
SET GLOBAL innodb_stats_locked_reads=ON; | ||
SELECT @@innodb_stats_locked_reads; | ||
@@innodb_stats_locked_reads | ||
1 | ||
SET GLOBAL innodb_stats_locked_reads=OFF; | ||
SELECT @@innodb_stats_locked_reads; | ||
@@innodb_stats_locked_reads | ||
0 | ||
SET GLOBAL innodb_stats_locked_reads=1; | ||
SELECT @@innodb_stats_locked_reads; | ||
@@innodb_stats_locked_reads | ||
1 | ||
SET GLOBAL innodb_stats_locked_reads=0; | ||
SELECT @@innodb_stats_locked_reads; | ||
@@innodb_stats_locked_reads | ||
0 | ||
SET GLOBAL innodb_stats_locked_reads=123; | ||
ERROR 42000: Variable 'innodb_stats_locked_reads' can't be set to the value of '123' | ||
SET GLOBAL innodb_stats_locked_reads='foo'; | ||
ERROR 42000: Variable 'innodb_stats_locked_reads' can't be set to the value of 'foo' | ||
SET GLOBAL innodb_stats_locked_reads=default; |
30 changes: 30 additions & 0 deletions
30
mysql-test/suite/sys_vars/t/innodb_stats_locked_reads_basic.test
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
# | ||
# innodb_stats_locked_reads | ||
# | ||
|
||
|
||
# show the default value | ||
SELECT @@innodb_stats_locked_reads; | ||
|
||
# check that it is writeable | ||
SET GLOBAL innodb_stats_locked_reads=ON; | ||
SELECT @@innodb_stats_locked_reads; | ||
|
||
SET GLOBAL innodb_stats_locked_reads=OFF; | ||
SELECT @@innodb_stats_locked_reads; | ||
|
||
SET GLOBAL innodb_stats_locked_reads=1; | ||
SELECT @@innodb_stats_locked_reads; | ||
|
||
SET GLOBAL innodb_stats_locked_reads=0; | ||
SELECT @@innodb_stats_locked_reads; | ||
|
||
# should be a boolean | ||
-- error ER_WRONG_VALUE_FOR_VAR | ||
SET GLOBAL innodb_stats_locked_reads=123; | ||
|
||
-- error ER_WRONG_VALUE_FOR_VAR | ||
SET GLOBAL innodb_stats_locked_reads='foo'; | ||
|
||
# restore the environment | ||
SET GLOBAL innodb_stats_locked_reads=default; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters