1
0
mirror of https://github.com/MariaDB/server.git synced 2025-07-30 16:24:05 +03:00

Manual merge from the mysql-5.1-bugteam.

This commit is contained in:
Alexey Kopytov
2009-11-24 11:19:06 +03:00
28 changed files with 761 additions and 219 deletions

View File

@ -985,14 +985,20 @@ JOIN::optimize()
DBUG_RETURN(1);
}
if (select_lex->olap == ROLLUP_TYPE && rollup_process_const_fields())
if (rollup.state != ROLLUP::STATE_NONE)
{
DBUG_PRINT("error", ("Error: rollup_process_fields() failed"));
DBUG_RETURN(1);
if (rollup_process_const_fields())
{
DBUG_PRINT("error", ("Error: rollup_process_fields() failed"));
DBUG_RETURN(1);
}
}
else
{
/* Remove distinct if only const tables */
select_distinct= select_distinct && (const_tables != tables);
}
/* Remove distinct if only const tables */
select_distinct= select_distinct && (const_tables != tables);
thd_proc_info(thd, "preparing");
if (result->initialize_tables(this))
{
@ -1291,11 +1297,14 @@ JOIN::optimize()
- We are using an ORDER BY or GROUP BY on fields not in the first table
- We are using different ORDER BY and GROUP BY orders
- The user wants us to buffer the result.
When the WITH ROLLUP modifier is present, we cannot skip temporary table
creation for the DISTINCT clause just because there are only const tables.
*/
need_tmp= (const_tables != tables &&
need_tmp= ((const_tables != tables &&
((select_distinct || !simple_order || !simple_group) ||
(group_list && order) ||
test(select_options & OPTION_BUFFER_RESULT)));
test(select_options & OPTION_BUFFER_RESULT))) ||
rollup.state != ROLLUP::STATE_NONE && select_distinct);
// No cache for MATCH
make_join_readinfo(this,
@ -6481,6 +6490,56 @@ void rr_unlock_row(st_join_table *tab)
/**
Pick the appropriate access method functions
Sets the functions for the selected table access method
@param tab Table reference to put access method
*/
static void
pick_table_access_method(JOIN_TAB *tab)
{
switch (tab->type)
{
case JT_REF:
tab->read_first_record= join_read_always_key;
tab->read_record.read_record= join_read_next_same;
break;
case JT_REF_OR_NULL:
tab->read_first_record= join_read_always_key_or_null;
tab->read_record.read_record= join_read_next_same_or_null;
break;
case JT_CONST:
tab->read_first_record= join_read_const;
tab->read_record.read_record= join_no_more_records;
break;
case JT_EQ_REF:
tab->read_first_record= join_read_key;
tab->read_record.read_record= join_no_more_records;
break;
case JT_FT:
tab->read_first_record= join_ft_read_first;
tab->read_record.read_record= join_ft_read_next;
break;
case JT_SYSTEM:
tab->read_first_record= join_read_system;
tab->read_record.read_record= join_no_more_records;
break;
/* keep gcc happy */
default:
break;
}
}
static void
make_join_readinfo(JOIN *join, ulonglong options)
{
@ -6515,45 +6574,15 @@ make_join_readinfo(JOIN *join, ulonglong options)
tab->sorted= sorted;
sorted= 0; // only first must be sorted
table->status=STATUS_NO_RECORD;
pick_table_access_method (tab);
switch (tab->type) {
case JT_SYSTEM: // Only happens with left join
table->status=STATUS_NO_RECORD;
tab->read_first_record= join_read_system;
tab->read_record.read_record= join_no_more_records;
break;
case JT_CONST: // Only happens with left join
table->status=STATUS_NO_RECORD;
tab->read_first_record= join_read_const;
tab->read_record.read_record= join_no_more_records;
if (table->covering_keys.is_set(tab->ref.key) &&
!table->no_keyread)
{
table->key_read=1;
table->file->extra(HA_EXTRA_KEYREAD);
}
break;
case JT_EQ_REF:
table->status=STATUS_NO_RECORD;
if (tab->select)
{
delete tab->select->quick;
tab->select->quick=0;
}
delete tab->quick;
tab->quick=0;
tab->read_first_record= join_read_key;
tab->read_record.unlock_row= join_read_key_unlock_row;
tab->read_record.read_record= join_no_more_records;
if (table->covering_keys.is_set(tab->ref.key) &&
!table->no_keyread)
{
table->key_read=1;
table->file->extra(HA_EXTRA_KEYREAD);
}
break;
/* fall through */
case JT_REF_OR_NULL:
case JT_REF:
table->status=STATUS_NO_RECORD;
if (tab->select)
{
delete tab->select->quick;
@ -6561,34 +6590,20 @@ make_join_readinfo(JOIN *join, ulonglong options)
}
delete tab->quick;
tab->quick=0;
/* fall through */
case JT_CONST: // Only happens with left join
if (table->covering_keys.is_set(tab->ref.key) &&
!table->no_keyread)
{
table->key_read=1;
table->file->extra(HA_EXTRA_KEYREAD);
}
if (tab->type == JT_REF)
{
tab->read_first_record= join_read_always_key;
tab->read_record.read_record= join_read_next_same;
}
else
{
tab->read_first_record= join_read_always_key_or_null;
tab->read_record.read_record= join_read_next_same_or_null;
}
break;
case JT_FT:
table->status=STATUS_NO_RECORD;
tab->read_first_record= join_ft_read_first;
tab->read_record.read_record= join_ft_read_next;
break;
case JT_ALL:
/*
If previous table use cache
If the incoming data set is already sorted don't use cache.
*/
table->status=STATUS_NO_RECORD;
if (i != join->const_tables && !(options & SELECT_NO_JOIN_CACHE) &&
tab->use_quick != 2 && !tab->first_inner && !ordered_set)
{
@ -6668,6 +6683,9 @@ make_join_readinfo(JOIN *join, ulonglong options)
}
}
break;
case JT_FT:
case JT_SYSTEM:
break;
default:
DBUG_PRINT("error",("Table type %d found",tab->type)); /* purecov: deadcode */
break; /* purecov: deadcode */
@ -7819,12 +7837,12 @@ static COND *build_equal_items_for_cond(THD *thd, COND *cond,
{
item_equal->fix_length_and_dec();
item_equal->update_used_tables();
set_if_bigger(thd->lex->current_select->max_equal_elems,
item_equal->members());
return item_equal;
}
else
item_equal= (Item_equal *) eq_list.pop();
set_if_bigger(thd->lex->current_select->max_equal_elems,
item_equal->members());
return item_equal;
return eq_list.pop();
}
else
{
@ -13189,6 +13207,8 @@ test_if_skip_sort_order(JOIN_TAB *tab,ORDER *order,ha_rows select_limit,
if (create_ref_for_key(tab->join, tab, keyuse,
tab->join->const_table_map))
DBUG_RETURN(0);
pick_table_access_method(tab);
}
else
{