Commit 849f56e8 authored by unknown's avatar unknown

MWL#89

- fixed incorrect query plans that resulted from emptying the
  keyuse array with the access methods of the non-modified query
  plan.
- fixed compiler warning.
parent 6a4ae290
...@@ -29,9 +29,9 @@ static TABLE_LIST *alloc_join_nest(THD *thd); ...@@ -29,9 +29,9 @@ static TABLE_LIST *alloc_join_nest(THD *thd);
static static
void fix_list_after_tbl_changes(SELECT_LEX *new_parent, List<TABLE_LIST> *tlist); void fix_list_after_tbl_changes(SELECT_LEX *new_parent, List<TABLE_LIST> *tlist);
static uint get_tmp_table_rec_length(List<Item> &items); static uint get_tmp_table_rec_length(List<Item> &items);
static double get_tmp_table_lookup_cost(THD *thd, ha_rows row_count, static double get_tmp_table_lookup_cost(THD *thd, double row_count,
uint row_size); uint row_size);
static double get_tmp_table_write_cost(THD *thd, ha_rows row_count, static double get_tmp_table_write_cost(THD *thd, double row_count,
uint row_size); uint row_size);
bool find_eq_ref_candidate(TABLE *table, table_map sj_inner_tables); bool find_eq_ref_candidate(TABLE *table, table_map sj_inner_tables);
static SJ_MATERIALIZATION_INFO * static SJ_MATERIALIZATION_INFO *
...@@ -1350,7 +1350,8 @@ static uint get_tmp_table_rec_length(List<Item> &items) ...@@ -1350,7 +1350,8 @@ static uint get_tmp_table_rec_length(List<Item> &items)
@return the cost of one lookup @return the cost of one lookup
*/ */
static double get_tmp_table_lookup_cost(THD *thd, ha_rows row_count, uint row_size) static double
get_tmp_table_lookup_cost(THD *thd, double row_count, uint row_size)
{ {
if (row_count * row_size > thd->variables.max_heap_table_size) if (row_count * row_size > thd->variables.max_heap_table_size)
return (double) DISK_TEMPTABLE_LOOKUP_COST; return (double) DISK_TEMPTABLE_LOOKUP_COST;
...@@ -1369,7 +1370,8 @@ static double get_tmp_table_lookup_cost(THD *thd, ha_rows row_count, uint row_si ...@@ -1369,7 +1370,8 @@ static double get_tmp_table_lookup_cost(THD *thd, ha_rows row_count, uint row_si
@return the cost of writing one row @return the cost of writing one row
*/ */
static double get_tmp_table_write_cost(THD *thd, ha_rows row_count, uint row_size) static double
get_tmp_table_write_cost(THD *thd, double row_count, uint row_size)
{ {
double lookup_cost= get_tmp_table_lookup_cost(thd, row_count, row_size); double lookup_cost= get_tmp_table_lookup_cost(thd, row_count, row_size);
/* /*
......
...@@ -19727,12 +19727,9 @@ void JOIN::save_query_plan(Query_plan_state *save_to) ...@@ -19727,12 +19727,9 @@ void JOIN::save_query_plan(Query_plan_state *save_to)
if (keyuse.elements) if (keyuse.elements)
{ {
DYNAMIC_ARRAY tmp_keyuse; DYNAMIC_ARRAY tmp_keyuse;
// TODO: isn't this allocated by update_ref_and_keys /* Swap the current and the backup keyuse internal arrays. */
//if (my_init_dynamic_array(save_keyuse, sizeof(KEYUSE), 20, 64))
// return 1;
/* Swap the current and the backup keyuse arrays. */
tmp_keyuse= keyuse; tmp_keyuse= keyuse;
keyuse= save_to->keyuse; keyuse= save_to->keyuse; /* keyuse is reset to an empty array. */
save_to->keyuse= tmp_keyuse; save_to->keyuse= tmp_keyuse;
for (uint i= 0; i < tables; i++) for (uint i= 0; i < tables; i++)
...@@ -19785,9 +19782,9 @@ void JOIN::restore_query_plan(Query_plan_state *restore_from) ...@@ -19785,9 +19782,9 @@ void JOIN::restore_query_plan(Query_plan_state *restore_from)
@param save_to If != NULL, save here the state of the current query plan @param save_to If != NULL, save here the state of the current query plan
@notes @notes
Given a query plan that already optimized taking into account some WHERE clause Given a query plan that was already optimized taking into account some WHERE
'C', reoptimize this plan with a new WHERE clause 'C AND added_where'. The clause 'C', reoptimize this plan with a new WHERE clause 'C AND added_where'.
reoptimization works as follows: The reoptimization works as follows:
1. Call update_ref_and_keys *only* for the new conditions 'added_where' 1. Call update_ref_and_keys *only* for the new conditions 'added_where'
that are about to be injected into the query. that are about to be injected into the query.
...@@ -19808,6 +19805,7 @@ JOIN::reoptimize(Item *added_where, table_map join_tables, ...@@ -19808,6 +19805,7 @@ JOIN::reoptimize(Item *added_where, table_map join_tables,
{ {
DYNAMIC_ARRAY added_keyuse; DYNAMIC_ARRAY added_keyuse;
SARGABLE_PARAM *sargables= 0; /* Used only as a dummy parameter. */ SARGABLE_PARAM *sargables= 0; /* Used only as a dummy parameter. */
uint org_keyuse_elements;
/* Re-run the REF optimizer to take into account the new conditions. */ /* Re-run the REF optimizer to take into account the new conditions. */
if (update_ref_and_keys(thd, &added_keyuse, join_tab, tables, added_where, if (update_ref_and_keys(thd, &added_keyuse, join_tab, tables, added_where,
...@@ -19826,18 +19824,32 @@ JOIN::reoptimize(Item *added_where, table_map join_tables, ...@@ -19826,18 +19824,32 @@ JOIN::reoptimize(Item *added_where, table_map join_tables,
if (save_to) if (save_to)
save_query_plan(save_to); save_query_plan(save_to);
/* Add the new access methods to the keyuse array. */
if (!keyuse.buffer && if (!keyuse.buffer &&
my_init_dynamic_array(&keyuse, sizeof(KEYUSE), 20, 64)) my_init_dynamic_array(&keyuse, sizeof(KEYUSE), 20, 64))
{ {
delete_dynamic(&added_keyuse); delete_dynamic(&added_keyuse);
return REOPT_ERROR; return REOPT_ERROR;
} }
allocate_dynamic(&keyuse, keyuse.elements + added_keyuse.elements);
org_keyuse_elements= save_to ? save_to->keyuse.elements : keyuse.elements;
allocate_dynamic(&keyuse, org_keyuse_elements + added_keyuse.elements);
/* If needed, add the access methods from the original query plan. */
if (save_to)
{
DBUG_ASSERT(!keyuse.elements);
memcpy(keyuse.buffer,
save_to->keyuse.buffer,
(size_t) save_to->keyuse.elements * keyuse.size_of_element);
keyuse.elements= save_to->keyuse.elements;
}
/* Add the new access methods to the keyuse array. */
memcpy(keyuse.buffer + keyuse.elements * keyuse.size_of_element, memcpy(keyuse.buffer + keyuse.elements * keyuse.size_of_element,
added_keyuse.buffer, added_keyuse.buffer,
(size_t) added_keyuse.elements * added_keyuse.size_of_element); (size_t) added_keyuse.elements * added_keyuse.size_of_element);
keyuse.elements+= added_keyuse.elements; keyuse.elements+= added_keyuse.elements;
/* added_keyuse contents is copied, and it is no longer needed. */
delete_dynamic(&added_keyuse); delete_dynamic(&added_keyuse);
if (sort_and_filter_keyuse(&keyuse)) if (sort_and_filter_keyuse(&keyuse))
......
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