Commit cfde11fc authored by Igor Babaev's avatar Igor Babaev

Fixed bug mdev-503.

If a table is already in the table cache but without data from persistent
statistical tables then the function open_and_process_table should not
only allocate memory for this statistical data in the corresponding
TABLE_SHARE object, but also should copy the references to the data into
certain fields of the TABLE data structure: for each key of the table 
KEY::read_stats should be copied, and for each column of the table
Field::read_stats should be copied. 
parent 98f239a8
SET SESSION STORAGE_ENGINE='InnoDB';
select @@global.use_stat_tables;
@@global.use_stat_tables
NEVER
select @@session.use_stat_tables;
@@session.use_stat_tables
NEVER
set @save_use_stat_tables=@@use_stat_tables;
set use_stat_tables='preferably';
DROP DATABASE IF EXISTS dbt3_s001;
CREATE DATABASE dbt3_s001;
use dbt3_s001;
set @save_optimizer_switch=@@optimizer_switch;
set optimizer_switch='extended_keys=off';
#
# Bug mdev-503: optimizer ignores setting use_stat_tables='preferably'
#
flush tables
customer, lineitem, nation, orders, part, partsupp, region, supplier;
set use_stat_tables='never';
EXPLAIN select sql_calc_found_rows straight_join
l_orderkey, sum(l_extendedprice*(1-l_discount)) as revenue,
o_orderdate, o_shippriority
from orders, customer, lineitem
where c_mktsegment = 'BUILDING' and c_custkey = o_custkey
and l_orderkey = o_orderkey and o_orderdate < date '1995-03-15'
and l_shipdate > date '1995-03-15'
group by l_orderkey, o_orderdate, o_shippriority
order by revenue desc, o_orderdate
limit 10;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE orders ALL PRIMARY,i_o_orderdate,i_o_custkey NULL NULL NULL # Using where; Using temporary; Using filesort
1 SIMPLE customer eq_ref PRIMARY PRIMARY 4 dbt3_s001.orders.o_custkey # Using where
1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey # Using where
set use_stat_tables='preferably';
EXPLAIN select sql_calc_found_rows straight_join
l_orderkey, sum(l_extendedprice*(1-l_discount)) as revenue,
o_orderdate, o_shippriority
from orders, customer, lineitem
where c_mktsegment = 'BUILDING' and c_custkey = o_custkey
and l_orderkey = o_orderkey and o_orderdate < date '1995-03-15'
and l_shipdate > date '1995-03-15'
group by l_orderkey, o_orderdate, o_shippriority
order by revenue desc, o_orderdate
limit 10;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE orders ALL PRIMARY,i_o_orderdate,i_o_custkey NULL NULL NULL 1500 Using where; Using temporary; Using filesort
1 SIMPLE customer eq_ref PRIMARY PRIMARY 4 dbt3_s001.orders.o_custkey 1 Using where
1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 Using where
flush tables customer, orders, lineitem;
EXPLAIN select sql_calc_found_rows straight_join
l_orderkey, sum(l_extendedprice*(1-l_discount)) as revenue,
o_orderdate, o_shippriority
from orders, customer, lineitem
where c_mktsegment = 'BUILDING' and c_custkey = o_custkey
and l_orderkey = o_orderkey and o_orderdate < date '1995-03-15'
and l_shipdate > date '1995-03-15'
group by l_orderkey, o_orderdate, o_shippriority
order by revenue desc, o_orderdate
limit 10;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE orders ALL PRIMARY,i_o_orderdate,i_o_custkey NULL NULL NULL 1500 Using where; Using temporary; Using filesort
1 SIMPLE customer eq_ref PRIMARY PRIMARY 4 dbt3_s001.orders.o_custkey 1 Using where
1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 Using where
# End of the test case for mdev-503
set optimizer_switch=@save_optimizer_switch;
DROP DATABASE dbt3_s001;
use test;
set use_stat_tables=@save_use_stat_tables;
SET SESSION STORAGE_ENGINE=DEFAULT;
--source include/have_innodb.inc
SET SESSION STORAGE_ENGINE='InnoDB';
select @@global.use_stat_tables;
select @@session.use_stat_tables;
set @save_use_stat_tables=@@use_stat_tables;
set use_stat_tables='preferably';
--disable_warnings
DROP DATABASE IF EXISTS dbt3_s001;
--enable_warnings
CREATE DATABASE dbt3_s001;
use dbt3_s001;
set @save_optimizer_switch=@@optimizer_switch;
set optimizer_switch='extended_keys=off';
--disable_query_log
--disable_result_log
--disable_warnings
--source include/dbt3_s001.inc
delete from mysql.table_stat;
delete from mysql.column_stat;
delete from mysql.index_stat;
ANALYZE TABLE
customer, lineitem, nation, orders, part, partsupp, region, supplier;
--enable_warnings
--enable_result_log
--enable_query_log
--echo #
--echo # Bug mdev-503: optimizer ignores setting use_stat_tables='preferably'
--echo #
flush tables
customer, lineitem, nation, orders, part, partsupp, region, supplier;
let $Q3S=
select sql_calc_found_rows straight_join
l_orderkey, sum(l_extendedprice*(1-l_discount)) as revenue,
o_orderdate, o_shippriority
from orders, customer, lineitem
where c_mktsegment = 'BUILDING' and c_custkey = o_custkey
and l_orderkey = o_orderkey and o_orderdate < date '1995-03-15'
and l_shipdate > date '1995-03-15'
group by l_orderkey, o_orderdate, o_shippriority
order by revenue desc, o_orderdate
limit 10;
set use_stat_tables='never';
--replace_column 9 #
eval EXPLAIN $Q3S;
set use_stat_tables='preferably';
--replace_result 2 1
eval EXPLAIN $Q3S;
flush tables customer, orders, lineitem;
eval EXPLAIN $Q3S;
--echo # End of the test case for mdev-503
set optimizer_switch=@save_optimizer_switch;
DROP DATABASE dbt3_s001;
use test;
set use_stat_tables=@save_use_stat_tables;
SET SESSION STORAGE_ENGINE=DEFAULT;
......@@ -4653,7 +4653,19 @@ open_and_process_table(THD *thd, LEX *lex, TABLE_LIST *tables,
{
if (!table_share->stats_can_be_read &&
!alloc_statistics_for_table_share(thd, table_share, FALSE))
{
KEY *key_info= table_share->key_info;
KEY *key_info_end= key_info + table_share->keys;
KEY *table_key_info= tables->table->key_info;
for ( ; key_info < key_info_end; key_info++, table_key_info++)
table_key_info->read_stats= key_info->read_stats;
Field **field_ptr= table_share->field;
Field **table_field_ptr= tables->table->field;
for ( ; *field_ptr; field_ptr++, table_field_ptr++)
(*table_field_ptr)->read_stats= (*field_ptr)->read_stats;
table_share->stats_can_be_read= TRUE;
}
if (table_share->stats_can_be_read && !table_share->stats_is_read)
{
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment