Commit 58b4f52a authored by Sergey Petrunya's avatar Sergey Petrunya

Merge

parents 1e1a8a7f a8341dfd
This diff is collapsed.
......@@ -149,3 +149,41 @@ set @@join_cache_level= @save_join_cache_level;
set storage_engine=@save_storage_engine;
set optimizer_switch=@innodb_mrr_cpk_tmp;
drop table t0;
#
# MDEV-6878: Use of uninitialized saved_primary_key in Mrr_ordered_index_reader::resume_read()
#
create table t0(a int);
insert into t0 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9);
create table t1 (
pk varchar(32) character set utf8 primary key,
kp1 char(32) not null,
col1 varchar(32),
key (kp1)
) engine=innodb;
insert into t1
select
concat('pk-', 1000 +A.a),
concat('kp1-', 1000 +A.a),
concat('val-', 1000 +A.a)
from test.t0 A ;
create table t2 as select kp1 as a from t1;
set join_cache_level=8;
set optimizer_switch='mrr=on,mrr_sort_keys=on';
explain
select * from t2 straight_join t1 force index(kp1) where t1.kp1=t2.a;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE t2 ALL NULL NULL NULL NULL 10
1 SIMPLE t1 ref kp1 kp1 32 test.t2.a 1 Using join buffer (flat, BKAH join); Key-ordered Rowid-ordered scan
select * from t2 straight_join t1 force index(kp1) where t1.kp1=t2.a;
a pk kp1 col1
kp1-1000 pk-1000 kp1-1000 val-1000
kp1-1001 pk-1001 kp1-1001 val-1001
kp1-1002 pk-1002 kp1-1002 val-1002
kp1-1003 pk-1003 kp1-1003 val-1003
kp1-1004 pk-1004 kp1-1004 val-1004
kp1-1005 pk-1005 kp1-1005 val-1005
kp1-1006 pk-1006 kp1-1006 val-1006
kp1-1007 pk-1007 kp1-1007 val-1007
kp1-1008 pk-1008 kp1-1008 val-1008
kp1-1009 pk-1009 kp1-1009 val-1009
drop table t0,t1,t2;
......@@ -498,8 +498,8 @@ CountryLanguage.Percentage > 50 AND
LENGTH(Language) < LENGTH(City.Name) - 2;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE Country ALL NULL NULL NULL NULL 239 Using where
1 SIMPLE City ALL NULL NULL NULL NULL 4079 Using where; Using join buffer (flat, BNL join)
1 SIMPLE CountryLanguage ALL NULL NULL NULL NULL 984 Using where; Using join buffer (flat, BNL join)
1 SIMPLE City ALL NULL NULL NULL NULL 4079 Using where; Using join buffer (flat, BNL join)
SELECT City.Name, Country.Name, CountryLanguage.Language
FROM City,Country,CountryLanguage
WHERE City.Country=Country.Code AND
......@@ -576,8 +576,8 @@ CountryLanguage.Percentage > 50 AND
LENGTH(Language) < LENGTH(City.Name) - 2;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE Country ALL NULL NULL NULL NULL 239 Using where
1 SIMPLE City ALL NULL NULL NULL NULL 4079 Using where; Using join buffer (flat, BNL join)
1 SIMPLE CountryLanguage ALL NULL NULL NULL NULL 984 Using where; Using join buffer (incremental, BNL join)
1 SIMPLE CountryLanguage ALL NULL NULL NULL NULL 984 Using where; Using join buffer (flat, BNL join)
1 SIMPLE City ALL NULL NULL NULL NULL 4079 Using where; Using join buffer (incremental, BNL join)
SELECT City.Name, Country.Name, CountryLanguage.Language
FROM City,Country,CountryLanguage
WHERE City.Country=Country.Code AND
......@@ -654,8 +654,8 @@ CountryLanguage.Percentage > 50 AND
LENGTH(Language) < LENGTH(City.Name) - 2;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE Country ALL NULL NULL NULL NULL 239 Using where
1 SIMPLE City hash_ALL NULL #hash#$hj 3 world.Country.Code 4079 Using where; Using join buffer (flat, BNLH join)
1 SIMPLE CountryLanguage hash_ALL NULL #hash#$hj 3 world.Country.Code 984 Using where; Using join buffer (flat, BNLH join)
1 SIMPLE City hash_ALL NULL #hash#$hj 3 world.Country.Code 4079 Using where; Using join buffer (flat, BNLH join)
SELECT City.Name, Country.Name, CountryLanguage.Language
FROM City,Country,CountryLanguage
WHERE City.Country=Country.Code AND
......@@ -732,8 +732,8 @@ CountryLanguage.Percentage > 50 AND
LENGTH(Language) < LENGTH(City.Name) - 2;
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE Country ALL NULL NULL NULL NULL 239 Using where
1 SIMPLE City hash_ALL NULL #hash#$hj 3 world.Country.Code 4079 Using where; Using join buffer (flat, BNLH join)
1 SIMPLE CountryLanguage hash_ALL NULL #hash#$hj 3 world.Country.Code 984 Using where; Using join buffer (incremental, BNLH join)
1 SIMPLE CountryLanguage hash_ALL NULL #hash#$hj 3 world.Country.Code 984 Using where; Using join buffer (flat, BNLH join)
1 SIMPLE City hash_ALL NULL #hash#$hj 3 world.Country.Code 4079 Using where; Using join buffer (incremental, BNLH join)
SELECT City.Name, Country.Name, CountryLanguage.Language
FROM City,Country,CountryLanguage
WHERE City.Country=Country.Code AND
......
# Initialize
--disable_warnings
drop table if exists t1,t2,t3;
drop table if exists t0,t1,t2,t3;
drop database if exists test1;
--enable_warnings
set @exit_optimizer_switch=@@optimizer_switch;
......@@ -272,5 +273,95 @@ limit 10;
drop table t1, t2, t3, t4;
--echo #
--echo # MDEV-6888: Query spends a long time in best_extension_by_limited_search with mrr enabled
--echo #
create database test1;
use test1;
set @tmp_jcl= @@join_cache_level;
set @tmp_os= @@optimizer_switch;
set join_cache_level=8;
set optimizer_switch='mrr=on,mrr_sort_keys=on';
CREATE TABLE t0 (
f1 bigint(20) DEFAULT NULL,
f2 char(50) DEFAULT NULL
) ENGINE=MEMORY DEFAULT CHARSET=latin1;
INSERT INTO t0 VALUES (NULL,'numeric column is NULL'),(0,NULL),(5,'five'),(1,'one'),(2,'two');
CREATE TABLE t1 (
f1 decimal(64,30) DEFAULT NULL,
f2 varchar(50) DEFAULT NULL
) ENGINE=MEMORY DEFAULT CHARSET=latin1;
INSERT INTO t1 VALUES
(NULL,'numeric column is NULL'),
(0.000000000000000000000000000000,NULL),
(5.000000000000000000000000000000,'five'),
(1.000000000000000000000000000000,'one'),
(3.000000000000000000000000000000,'three');
CREATE TABLE t2 (
f1 double DEFAULT NULL,
f2 varbinary(50) DEFAULT NULL
) ENGINE=MEMORY DEFAULT CHARSET=latin1;
INSERT INTO t2 VALUES (NULL,'numeric column is NULL'),(0,NULL),(5,'five'),(2,'two'),(3,'three');
create VIEW v0 AS select f1,f2 from t1 ;
let $cnt= 27;
while ($cnt)
{
# i runs from 1 to 27
let $i= `select 28 - $cnt`;
let $prev=`select $i - 1`;
# rem = i mod 3
let $rem= `select MOD($i, 3)`;
# view uses $i, $prev and $rem:
eval create VIEW v$i AS select tab1_v$i.f1,tab1_v$i.f2 from t$rem tab1_v$i join v$prev tab2 on tab1_v$i.f1 = tab2.f1 and tab1_v$i.f2 = tab2.f2;
dec $cnt;
}
EXPLAIN SELECT CAST(f1 AS SIGNED INTEGER) AS f1, CAST(f2 AS CHAR) AS f2 FROM v27;
--echo # This used to hang forever:
EXPLAIN SELECT CAST(f1 AS SIGNED INTEGER) AS f1, CAST(f2 AS CHAR) AS f2 FROM v27;
use test;
drop database test1;
set join_cache_level=@tmp_jcl;
set optimizer_switch=@tmp_os;
--echo #
--echo # MDEV-6879: Dereference of NULL primary_file->table in DsMrr_impl::get_disk_sweep_mrr_cost()
--echo #
create table t1(a int);
insert into t1 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9);
create table t2 (a int, b int, c text);
insert into t2
select
A.a + B.a* 10,
A.a + B.a* 10,
'blob-data'
from t1 A, t1 B;
set @tmp_jcl= @@join_cache_level;
set @tmp_os= @@optimizer_switch;
set join_cache_level=6;
set @@optimizer_switch='derived_merge=on,derived_with_keys=on,mrr=on';
explain
select * from
t1 join
(select * from t2 order by a limit 1000) as D1
where
D1.a= t1.a;
set join_cache_level=@tmp_jcl;
set optimizer_switch=@tmp_os;
drop table t1, t2;
# The following command must be the last one the file
set optimizer_switch=@exit_optimizer_switch;
......@@ -139,3 +139,32 @@ set storage_engine=@save_storage_engine;
set optimizer_switch=@innodb_mrr_cpk_tmp;
drop table t0;
--echo #
--echo # MDEV-6878: Use of uninitialized saved_primary_key in Mrr_ordered_index_reader::resume_read()
--echo #
create table t0(a int);
insert into t0 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9);
create table t1 (
pk varchar(32) character set utf8 primary key,
kp1 char(32) not null,
col1 varchar(32),
key (kp1)
) engine=innodb;
insert into t1
select
concat('pk-', 1000 +A.a),
concat('kp1-', 1000 +A.a),
concat('val-', 1000 +A.a)
from test.t0 A ;
create table t2 as select kp1 as a from t1;
set join_cache_level=8;
set optimizer_switch='mrr=on,mrr_sort_keys=on';
explain
select * from t2 straight_join t1 force index(kp1) where t1.kp1=t2.a;
select * from t2 straight_join t1 force index(kp1) where t1.kp1=t2.a;
drop table t0,t1,t2;
......@@ -410,6 +410,7 @@ bool Mrr_ordered_index_reader::set_interruption_temp_buffer(uint rowid_length,
*space_start += key_len;
have_saved_rowid= FALSE;
read_was_interrupted= FALSE;
return FALSE;
}
......@@ -418,6 +419,7 @@ void Mrr_ordered_index_reader::set_no_interruption_temp_buffer()
support_scan_interruptions= FALSE;
saved_key_tuple= saved_rowid= saved_primary_key= NULL; /* safety */
have_saved_rowid= FALSE;
read_was_interrupted= FALSE;
}
void Mrr_ordered_index_reader::interrupt_read()
......@@ -435,6 +437,7 @@ void Mrr_ordered_index_reader::interrupt_read()
&table->key_info[table->s->primary_key],
table->key_info[table->s->primary_key].key_length);
}
read_was_interrupted= TRUE;
/* Save the last rowid */
memcpy(saved_rowid, file->ref, file->ref_length);
......@@ -452,6 +455,10 @@ void Mrr_ordered_index_reader::position()
void Mrr_ordered_index_reader::resume_read()
{
TABLE *table= file->get_table();
if (!read_was_interrupted)
return;
KEY *used_index= &table->key_info[file->active_index];
key_restore(table->record[0], saved_key_tuple,
used_index, used_index->key_length);
......@@ -541,8 +548,7 @@ int Mrr_ordered_index_reader::init(handler *h_arg, RANGE_SEQ_IF *seq_funcs,
is_mrr_assoc= !test(mode & HA_MRR_NO_ASSOCIATION);
mrr_funcs= *seq_funcs;
source_exhausted= FALSE;
if (support_scan_interruptions)
bzero(saved_key_tuple, key_info->key_length);
read_was_interrupted= false;
have_saved_rowid= FALSE;
return 0;
}
......
......@@ -324,6 +324,12 @@ class Mrr_ordered_index_reader : public Mrr_index_reader
uchar *saved_key_tuple; /* Saved current key tuple */
uchar *saved_primary_key; /* Saved current primary key tuple */
/*
TRUE<=> saved_key_tuple (and saved_primary_key when applicable) have
valid values.
*/
bool read_was_interrupted;
static int compare_keys(void* arg, uchar* key1, uchar* key2);
static int compare_keys_reverse(void* arg, uchar* key1, uchar* key2);
......
......@@ -9663,6 +9663,19 @@ uint check_join_cache_usage(JOIN_TAB *tab,
cache_level--;
}
/*
Don't use BKA for materialized tables. We could actually have a
meaningful use of BKA when linked join buffers are used.
The problem is, the temp.table is not filled (actually not even opened
properly) yet, and this doesn't let us call
handler->multi_range_read_info(). It is possible to come up with
estimates, etc. without acessing the table, but it seems not to worth the
effort now.
*/
if (tab->table->pos_in_table_list->is_materialized_derived())
no_bka_cache= true;
/*
Don't use join buffering if we're dictated not to by no_jbuf_after
(This is not meaningfully used currently)
......@@ -9729,7 +9742,7 @@ uint check_join_cache_usage(JOIN_TAB *tab,
if (tab->ref.is_access_triggered())
goto no_join_cache;
if (!tab->is_ref_for_hash_join())
if (!tab->is_ref_for_hash_join() && !no_bka_cache)
{
flags= HA_MRR_NO_NULL_ENDPOINTS | HA_MRR_SINGLE_POINT;
if (tab->table->covering_keys.is_set(tab->ref.key))
......
......@@ -5401,7 +5401,6 @@ void TABLE::create_key_part_by_field(KEY *keyinfo,
KEY_PART_INFO *key_part_info,
Field *field, uint fieldnr)
{
field->flags|= PART_KEY_FLAG;
key_part_info->null_bit= field->null_bit;
key_part_info->null_offset= (uint) (field->null_ptr -
(uchar*) record[0]);
......@@ -5552,6 +5551,7 @@ bool TABLE::add_tmp_key(uint key, uint key_parts,
(*reg_field)->key_start.set_bit(key);
(*reg_field)->part_of_key.set_bit(key);
create_key_part_by_field(keyinfo, key_part_info, *reg_field, fld_idx+1);
(*reg_field)->flags|= PART_KEY_FLAG;
key_start= FALSE;
key_part_info++;
}
......
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