1
0
mirror of https://github.com/MariaDB/server.git synced 2025-08-08 11:22:35 +03:00

5.5 merge

This commit is contained in:
Sergei Golubchik
2013-06-06 17:51:28 +02:00
464 changed files with 7741 additions and 3075 deletions

View File

@@ -7689,6 +7689,14 @@ static SEL_TREE *get_full_func_mm_tree(RANGE_OPT_PARAM *param,
param->current_table);
DBUG_ENTER("get_full_func_mm_tree");
#ifdef HAVE_SPATIAL
if (field_item->field->type() == MYSQL_TYPE_GEOMETRY)
{
/* We have to be able to store all sorts of spatial features here */
((Field_geom*) field_item->field)->geom_type= Field::GEOM_GEOMETRY;
}
#endif /*HAVE_SPATIAL*/
for (uint i= 0; i < cond_func->arg_count; i++)
{
Item *arg= cond_func->arguments()[i]->real_item();
@@ -11248,9 +11256,13 @@ int QUICK_ROR_INTERSECT_SELECT::get_next()
do
{
DBUG_EXECUTE_IF("innodb_quick_report_deadlock",
DBUG_SET("+d,innodb_report_deadlock"););
if ((error= quick->get_next()))
{
quick_with_last_rowid->file->unlock_row();
/* On certain errors like deadlock, trx might be rolled back.*/
if (!current_thd->transaction_rollback_request)
quick_with_last_rowid->file->unlock_row();
DBUG_RETURN(error);
}
quick->file->position(quick->record);
@@ -11276,7 +11288,9 @@ int QUICK_ROR_INTERSECT_SELECT::get_next()
quick->file->unlock_row(); /* row not in range; unlock */
if ((error= quick->get_next()))
{
quick_with_last_rowid->file->unlock_row();
/* On certain errors like deadlock, trx might be rolled back.*/
if (!current_thd->transaction_rollback_request)
quick_with_last_rowid->file->unlock_row();
DBUG_RETURN(error);
}
}
@@ -12161,13 +12175,15 @@ cost_group_min_max(TABLE* table, KEY *index_info, uint used_key_parts,
NGA1.If in the index I there is a gap between the last GROUP attribute G_k,
and the MIN/MAX attribute C, then NGA must consist of exactly the
index attributes that constitute the gap. As a result there is a
permutation of NGA that coincides with the gap in the index
<B_1, ..., B_m>.
permutation of NGA, BA=<B_1,...,B_m>, that coincides with the gap
in the index.
NGA2.If BA <> {}, then the WHERE clause must contain a conjunction EQ of
equality conditions for all NG_i of the form (NG_i = const) or
(const = NG_i), such that each NG_i is referenced in exactly one
conjunct. Informally, the predicates provide constants to fill the
gap in the index.
NGA3.If BA <> {}, there can only be one range. TODO: This is a code
limitation and is not strictly needed. See BUG#15947433
WA1. There are no other attributes in the WHERE clause except the ones
referenced in predicates RNG, PA, PC, EQ defined above. Therefore
WA is subset of (GA union NGA union C) for GA,NGA,C that pass the
@@ -12909,6 +12925,74 @@ check_group_min_max_predicates(Item *cond, Item_field *min_max_arg_item,
}
/*
Get SEL_ARG tree, if any, for the keypart covering non grouping
attribute (NGA) field 'nga_field'.
This function enforces the NGA3 test: If 'keypart_tree' contains a
condition for 'nga_field', there can only be one range. In the
opposite case, this function returns with error and 'cur_range'
should not be used.
Note that the NGA1 and NGA2 requirements, like whether or not the
range predicate for 'nga_field' is equality, is not tested by this
function.
@param[in] nga_field The NGA field we want the SEL_ARG tree for
@param[in] keypart_tree Root node of the SEL_ARG* tree for the index
@param[out] cur_range The SEL_ARG tree, if any, for the keypart
covering field 'keypart_field'
@retval true 'keypart_tree' contained a predicate for 'nga_field' but
multiple ranges exists. 'cur_range' should not be used.
@retval false otherwise
*/
static bool
get_sel_arg_for_keypart(Field *nga_field,
SEL_ARG *keypart_tree,
SEL_ARG **cur_range)
{
if(keypart_tree == NULL)
return false;
if(keypart_tree->field->eq(nga_field))
{
/*
Enforce NGA3: If a condition for nga_field has been found, only
a single range is allowed.
*/
if (keypart_tree->prev || keypart_tree->next)
return true; // There are multiple ranges
*cur_range= keypart_tree;
return false;
}
SEL_ARG *found_tree= NULL;
SEL_ARG *first_kp= keypart_tree->first();
for (SEL_ARG *cur_kp= first_kp; cur_kp && !found_tree;
cur_kp= cur_kp->next)
{
if (cur_kp->next_key_part)
{
if (get_sel_arg_for_keypart(nga_field,
cur_kp->next_key_part,
&found_tree))
return true;
}
/*
Enforce NGA3: If a condition for nga_field has been found,only
a single range is allowed.
*/
if (found_tree && first_kp->next)
return true; // There are multiple ranges
}
*cur_range= found_tree;
return false;
}
/*
Extract a sequence of constants from a conjunction of equality predicates.
@@ -12923,12 +13007,13 @@ check_group_min_max_predicates(Item *cond, Item_field *min_max_arg_item,
key_infix [out] Infix of constants to be used for index lookup
key_infix_len [out] Lenghth of the infix
first_non_infix_part [out] The first keypart after the infix (if any)
DESCRIPTION
Test conditions (NGA1, NGA2) from get_best_group_min_max(). Namely,
for each keypart field NGF_i not in GROUP-BY, check that there is a
constant equality predicate among conds with the form (NGF_i = const_ci) or
(const_ci = NGF_i).
Test conditions (NGA1, NGA2, NGA3) from get_best_group_min_max(). Namely,
for each keypart field NG_i not in GROUP-BY, check that there is exactly one
constant equality predicate among conds with the form (NG_i = const_ci) or
(const_ci = NG_i).. In addition, there can only be one range when there is
such a gap.
Thus all the NGF_i attributes must fill the 'gap' between the last group-by
attribute and the MIN/MAX attribute in the index (if present). If these
conditions hold, copy each constant from its corresponding predicate into
@@ -12957,17 +13042,14 @@ get_constant_key_infix(KEY *index_info, SEL_ARG *index_range_tree,
uchar *key_ptr= key_infix;
for (cur_part= first_non_group_part; cur_part != end_part; cur_part++)
{
cur_range= NULL;
/*
Find the range tree for the current keypart. We assume that
index_range_tree points to the leftmost keypart in the index.
index_range_tree points to the first keypart in the index.
*/
for (cur_range= index_range_tree;
cur_range && cur_range->type == SEL_ARG::KEY_RANGE;
cur_range= cur_range->next_key_part)
{
if (cur_range->field->eq(cur_part->field))
break;
}
if(get_sel_arg_for_keypart(cur_part->field, index_range_tree, &cur_range))
return false;
if (!cur_range || cur_range->type != SEL_ARG::KEY_RANGE)
{
if (min_max_arg_part)
@@ -12979,9 +13061,6 @@ get_constant_key_infix(KEY *index_info, SEL_ARG *index_range_tree,
}
}
/* Check that the current range tree is a single point interval. */
if (cur_range->prev || cur_range->next)
return FALSE; /* This is not the only range predicate for the field. */
if ((cur_range->min_flag & NO_MIN_RANGE) ||
(cur_range->max_flag & NO_MAX_RANGE) ||
(cur_range->min_flag & NEAR_MIN) || (cur_range->max_flag & NEAR_MAX))